Một trong những tính năng thú vị của IPython là các hàm ma thuật - các hàm trợ giúp được tích hợp trong IPython. Chúng có thể giúp bạn dễ dàng bắt đầu trình gỡ lỗi tương tác, tạo macro, chạy câu lệnh thông qua trình lược tả mã hoặc đo thời gian thực thi của nó và thực hiện nhiều việc phổ biến khác
Đừng nhầm các hàm ma thuật IPython với các hàm ma thuật Python [các hàm có dấu gạch dưới kép ở đầu và cuối, ví dụ như
In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
6 hoặc In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
7] - đó là những thứ hoàn toàn khác nhau. Trong phần này và các phần tiếp theo của bài viết, bất cứ khi nào bạn thấy một hàm ma thuật - đó là hàm ma thuật IPythonHơn nữa, bạn có thể tạo các chức năng kỳ diệu của riêng mình. Có 2 loại chức năng ma thuật khác nhau.
Loại đầu tiên - được gọi là dòng ma thuật - có tiền tố là
In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
0 và hoạt động giống như một lệnh được nhập trong thiết bị đầu cuối của bạn. Bạn bắt đầu với tên của hàm và sau đó truyền một số đối số, chẳng hạn. In [1]: %timeit range[1000]
255 ns ± 10.3 ns per loop [mean ± std. dev. of 7 runs, 1000000 loops each]
Cái tôi thích nhất là chức năng %debug. Hãy tưởng tượng bạn chạy một số mã và nó ném ra một ngoại lệ. Nhưng do bạn chưa chuẩn bị cho trường hợp ngoại lệ, nên bạn đã không chạy nó thông qua trình gỡ lỗi. Bây giờ, để có thể gỡ lỗi, bạn thường phải quay lại, đặt một số điểm dừng và chạy lại cùng mã. May mắn thay, nếu bạn đang sử dụng IPython, có một cách tốt hơn. Bạn có thể chạy
In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
1 ngay sau khi ngoại lệ xảy ra và IPython sẽ bắt đầu trình gỡ lỗi tương tác cho ngoại lệ đó. Nó được gọi là gỡ lỗi sau khi chết và tôi hoàn toàn thích nóLoại hàm ma thuật thứ hai là ma thuật ô và chúng hoạt động trên một khối mã, không phải trên một dòng. Chúng có tiền tố là
In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
2. Để đóng một khối mã, khi bạn đang ở trong một chức năng ma thuật của ô, hãy nhấn In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
3 hai lần. Đây là một ví dụ về hàm In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
4 hoạt động trên một khối mãIn [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
Cả ma thuật dòng và ma thuật ô đều có thể được tạo bằng cách trang trí một hàm Python. Một cách khác là viết một lớp kế thừa từ lớp
In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
5. Tôi sẽ đề cập đến phương pháp thứ hai này trong một bài viết khácTạo chức năng ma thuật dòng #
Đó là tất cả lý thuyết. Bây giờ, hãy viết hàm ma thuật đầu tiên của chúng ta. Chúng ta sẽ bắt đầu với một
In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
6 và trong phần thứ hai của hướng dẫn này, chúng ta sẽ tạo một In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
7Loại chức năng kỳ diệu nào chúng ta sẽ tạo ra? . Tôi đến từ Ba Lan và ở Ba Lan, chúng tôi sử dụng ký hiệu tiếng Ba Lan để viết các phép toán. Vì vậy, thay vì viết
In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
8, chúng tôi viết In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
9. Và thay vì viết In [1]: %timeit range[1000]
255 ns ± 10.3 ns per loop [mean ± std. dev. of 7 runs, 1000000 loops each]
20, chúng tôi viết In [1]: %timeit range[1000]
255 ns ± 10.3 ns per loop [mean ± std. dev. of 7 runs, 1000000 loops each]
21[1]Hãy viết một trình thông dịch ký hiệu tiếng Ba Lan đơn giản. Nó sẽ lấy một biểu thức bằng ký hiệu tiếng Ba Lan làm đầu vào và đưa ra câu trả lời đúng. Để giữ cho ví dụ này ngắn gọn, tôi sẽ giới hạn nó chỉ trong các phép tính số học cơ bản.
In [1]: %timeit range[1000]
255 ns ± 10.3 ns per loop [mean ± std. dev. of 7 runs, 1000000 loops each]
22, In [1]: %timeit range[1000]
255 ns ± 10.3 ns per loop [mean ± std. dev. of 7 runs, 1000000 loops each]
23, In [1]: %timeit range[1000]
255 ns ± 10.3 ns per loop [mean ± std. dev. of 7 runs, 1000000 loops each]
24 và In [1]: %timeit range[1000]
255 ns ± 10.3 ns per loop [mean ± std. dev. of 7 runs, 1000000 loops each]
25Đây là mã giải thích ký hiệu tiếng Ba Lan
In [1]: %timeit range[1000]
255 ns ± 10.3 ns per loop [mean ± std. dev. of 7 runs, 1000000 loops each]
2Tiếp theo, chúng ta sẽ tạo một hàm ma thuật
In [1]: %timeit range[1000]
255 ns ± 10.3 ns per loop [mean ± std. dev. of 7 runs, 1000000 loops each]
26 sẽ sử dụng đoạn mã trên để diễn giải ký hiệu tiếng Ba LanIn [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
0Và đó là nó. Trình trang trí
In [1]: %timeit range[1000]
255 ns ± 10.3 ns per loop [mean ± std. dev. of 7 runs, 1000000 loops each]
27 biến chức năng In [1]: %timeit range[1000]
255 ns ± 10.3 ns per loop [mean ± std. dev. of 7 runs, 1000000 loops each]
28 của chúng ta thành một chức năng ma thuật In [1]: %timeit range[1000]
255 ns ± 10.3 ns per loop [mean ± std. dev. of 7 runs, 1000000 loops each]
26. Tham số In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
00 chứa bất cứ thứ gì được truyền cho hàm ma thuật. Nếu chúng ta gọi nó theo cách sau. In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
01, In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
00 sẽ chứa In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
03Để đảm bảo rằng IPython tải chức năng ma thuật của chúng tôi khi khởi động, hãy sao chép tất cả mã mà chúng tôi vừa viết [bạn có thể tìm thấy toàn bộ tệp trên GitHub] vào một tệp bên trong thư mục khởi động IPython. Bạn có thể đọc thêm về thư mục này trong bài đăng tệp khởi động IPython. Trong trường hợp của tôi, tôi đang lưu nó trong một tệp có tên
In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
8[tên của tệp không quan trọng, nhưng thư mục bạn đặt nó mới quan trọng]
Ok, đã đến lúc kiểm tra nó. Bắt đầu IPython và hãy làm một số phép toán Ba Lan
In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
9Hoàn hảo, nó hoạt động. Tất nhiên, nó khá thô sơ - nó chỉ hỗ trợ 4 toán tử, nó không xử lý tốt các trường hợp ngoại lệ và do nó sử dụng đệ quy nên nó có thể bị lỗi đối với các biểu thức rất dài. Ngoài ra, mô-đun
In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
04 và hàm In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
05 hiện sẽ có sẵn trong các phiên IPython của bạn, vì bất kỳ mã nào bạn đặt trong tệp In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
06 sẽ được chạy khi khởi động IPython. Nhưng, bạn vừa viết hàm ma thuật đầu tiên của mình. Và nó không quá khó.
Tại thời điểm này, có lẽ bạn đang tự hỏi - Tại sao chúng ta không viết một hàm Python tiêu chuẩn?
In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
3hoặc thậm chí
In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
4Như tôi đã nói lúc đầu, các hàm ma thuật thường là các hàm trợ giúp. Ưu điểm chính của chúng là khi ai đó nhìn thấy các hàm có tiền tố
In [2]: %%timeit elements = range[1000]
...: x = min[elements]
...: y = max[elements]
...:
...:
52.8 µs ± 4.37 µs per loop [mean ± std. dev. of 7 runs, 10000 loops each]
0, thì rõ ràng đó là một hàm ma thuật từ IPython, không phải là một hàm được xác định ở đâu đó trong mã hoặc tích hợp sẵn. Ngoài ra, không có nguy cơ tên của chúng xung đột với các chức năng từ các mô-đun PythonPhần kết luận #
Tôi hy vọng bạn thích hướng dẫn ngắn này và nếu bạn có thắc mắc hoặc nếu bạn có một chức năng kỳ diệu thú vị mà bạn muốn chia sẻ - hãy gửi email cho tôi hoặc ping tôi trên Twitter
Hãy theo dõi các phần tiếp theo. Chúng ta vẫn cần đề cập đến các chức năng ma thuật ô, chức năng ma thuật dòng VÀ ô và các lớp ma thuật