Giá trị mặc định được đánh giá khi chức năng được xác định, không phải khi nó được gọi. Điều này có thể có vấn đề khi sử dụng các loại có thể thay đổi [e. g. từ điển hoặc danh sách] và sửa đổi chúng trong thân hàm, vì các sửa đổi sẽ được duy trì trong các lần gọi hàm
Sử dụng một loại bất biến trong một đối số từ khóa
In [124]: bigx = 10 In [125]: def double_it[x=bigx]: .....: return x * 2 .....: In [126]: bigx = 1e9 # Now really big In [128]: double_it[] Out[128]: 20
Sử dụng loại có thể thay đổi trong đối số từ khóa [và sửa đổi nó bên trong thân hàm]
In [2]: def add_to_dict[args={'a': 1, 'b': 2}]: ...: for i in args.keys[]: ...: args[i] += 1 ...: print[args] ...: In [3]: add_to_dict Out[3]: In [4]: add_to_dict[] {'a': 2, 'b': 3} In [5]: add_to_dict[] {'a': 3, 'b': 4} In [6]: add_to_dict[] {'a': 4, 'b': 5}
Mẹo
Ví dụ liên quan hơn khi thực hiện cắt lát của python
In [98]: def slicer[seq, start=None, stop=None, step=None]: ....: """Implement basic python slicing.""" ....: return seq[start:stop:step] ....: In [101]: rhyme = 'one fish, two fish, red fish, blue fish'.split[] In [102]: rhyme Out[102]: ['one', 'fish,', 'two', 'fish,', 'red', 'fish,', 'blue', 'fish'] In [103]: slicer[rhyme] Out[103]: ['one', 'fish,', 'two', 'fish,', 'red', 'fish,', 'blue', 'fish'] In [104]: slicer[rhyme, step=2] Out[104]: ['one', 'two', 'red', 'blue'] In [105]: slicer[rhyme, 1, step=2] Out[105]: ['fish,', 'fish,', 'fish,', 'fish'] In [106]: slicer[rhyme, start=1, stop=4, step=2] Out[106]: ['fish,', 'fish,']
Thứ tự của các đối số từ khóa không quan trọng
In [107]: slicer[rhyme, step=2, start=1, stop=4] Out[107]: ['fish,', 'fish,']
nhưng cách tốt nhất là sử dụng thứ tự giống như định nghĩa của hàm
Đối số từ khóa là một tính năng rất thuận tiện để xác định các hàm có số lượng đối số thay đổi, đặc biệt khi các giá trị mặc định được sử dụng trong hầu hết các lệnh gọi hàm
1. 2. 4. 4. Truyền theo giá trị
Mẹo
Bạn có thể sửa đổi giá trị của một biến bên trong một hàm không? . Trong Python, sự phân biệt như vậy hơi giả tạo và hơi khó hiểu liệu các biến của bạn có bị sửa đổi hay không. May mắn thay, có tồn tại các quy tắc rõ ràng
Các tham số cho các hàm là các tham chiếu đến các đối tượng, được truyền theo giá trị. Khi bạn chuyển một biến cho một hàm, python sẽ chuyển tham chiếu đến đối tượng mà biến đó đề cập đến [giá trị]. Không phải bản thân biến
Nếu giá trị được truyền vào một hàm là bất biến, thì hàm đó không sửa đổi biến của người gọi. Nếu giá trị có thể thay đổi, hàm có thể sửa đổi biến của người gọi tại chỗ
>>> def try_to_modify[x, y, z]: .. x = 23 .. y.append[42] .. z = [99] # new reference .. print[x] .. print[y] .. print[z] ... >>> a = 77 # immutable variable >>> b = [99] # mutable variable >>> c = [28] >>> try_to_modify[a, b, c] 23 [99, 42] [99] >>> print[a] 77 >>> print[b] [99, 42] >>> print[c] [28]
Các hàm có một bảng biến cục bộ được gọi là không gian tên cục bộ
Biến
In [6]: def disk_area[radius]: ...: return 3.14 * radius * radius ...: In [8]: disk_area[1.5] Out[8]: 7.06499999999999959 chỉ tồn tại trong hàm
In [81]: def double_it[x]: ....: return x * 2 ....: In [82]: double_it[3] Out[82]: 6 In [83]: double_it[] --------------------------------------------------------------------------- Traceback [most recent call last]: File "", line 1, in TypeError: double_it[] takes exactly 1 argument [0 given]0
1. 2. 4. 5. biến toàn cầu
Các biến được khai báo bên ngoài hàm có thể được tham chiếu bên trong hàm
In [114]: x = 5 In [115]: def addx[y]: .....: return x + y .....: In [116]: addx[10] Out[116]: 15
Nhưng các biến "toàn cầu" này không thể được sửa đổi trong hàm, trừ khi được khai báo toàn cục trong hàm
Điều này không hoạt động
In [6]: def disk_area[radius]: ...: return 3.14 * radius * radius ...: In [8]: disk_area[1.5] Out[8]: 7.06499999999999950
Những công việc này
In [6]: def disk_area[radius]: ...: return 3.14 * radius * radius ...: In [8]: disk_area[1.5] Out[8]: 7.06499999999999951
1. 2. 4. 6. Số tham số biến
Các dạng tham số đặc biệtIn [81]: def double_it[x]: ....: return x * 2 ....: In [82]: double_it[3] Out[82]: 6 In [83]: double_it[] --------------------------------------------------------------------------- Traceback [most recent call last]: File "", line 1, in TypeError: double_it[] takes exactly 1 argument [0 given]
1. bất kỳ số lượng đối số vị trí nào được đóng gói vào một bộ dữ liệuIn [81]: def double_it[x]: ....: return x * 2 ....: In [82]: double_it[3] Out[82]: 6 In [83]: double_it[] --------------------------------------------------------------------------- Traceback [most recent call last]: File "", line 1, in TypeError: double_it[] takes exactly 1 argument [0 given]
2. bất kỳ số lượng đối số từ khóa nào được đóng gói trong một từ điển
In [6]: def disk_area[radius]: ...: return 3.14 * radius * radius ...: In [8]: disk_area[1.5] Out[8]: 7.06499999999999952
1. 2. 4. 7. tài liệu
Tài liệu về những gì chức năng làm và các tham số của nó. quy ước chung
In [6]: def disk_area[radius]: ...: return 3.14 * radius * radius ...: In [8]: disk_area[1.5] Out[8]: 7.06499999999999953
Ghi chú
Hướng dẫn chuỗi tài liệu
Vì mục đích tiêu chuẩn hóa, trang web Quy ước về chuỗi tài liệu ghi lại ngữ nghĩa và quy ước liên quan đến chuỗi tài liệu Python
Ngoài ra, các mô-đun Numpy và Scipy đã xác định một tiêu chuẩn chính xác để ghi lại các chức năng khoa học mà bạn có thể muốn tuân theo cho các chức năng của riêng mình, với phần
In [81]: def double_it[x]: ....: return x * 2 ....: In [82]: double_it[3] Out[82]: 6 In [83]: double_it[] --------------------------------------------------------------------------- Traceback [most recent call last]: File "", line 1, in TypeError: double_it[] takes exactly 1 argument [0 given]3, phần
In [81]: def double_it[x]: ....: return x * 2 ....: In [82]: double_it[3] Out[82]: 6 In [83]: double_it[] --------------------------------------------------------------------------- Traceback [most recent call last]: File "", line 1, in TypeError: double_it[] takes exactly 1 argument [0 given]4, v.v. Nhìn thấy
1. 2. 4. 8. Chức năng là đối tượng
Các chức năng là các đối tượng hạng nhất, có nghĩa là chúng có thể- gán cho một biến
- một mục trong danh sách [hoặc bất kỳ bộ sưu tập nào]
- được truyền dưới dạng đối số cho hàm khác
In [6]: def disk_area[radius]: ...: return 3.14 * radius * radius ...: In [8]: disk_area[1.5] Out[8]: 7.06499999999999954
1. 2. 4. 9. phương pháp
Phương thức là các chức năng gắn liền với các đối tượng. Bạn đã thấy những điều này trong các ví dụ của chúng tôi về danh sách, từ điển, chuỗi, v.v…