Gọi cùng chức năng bên trong hàm Python

Các hàm là một trong những "công dân hạng nhất" của Python, có nghĩa là các hàm ở cùng cấp độ với các đối tượng Python khác như số nguyên, chuỗi, mô-đun, v.v. Chúng có thể được tạo và hủy một cách linh hoạt, được chuyển đến các hàm khác, được trả về dưới dạng giá trị, v.v.

Python hỗ trợ khái niệm "hàm lồng nhau" hoặc "hàm bên trong", đơn giản là một hàm được định nghĩa bên trong một hàm khác. Trong phần còn lại của bài viết, chúng ta sẽ sử dụng thay thế cho từ "hàm bên trong" và "hàm lồng nhau"

Có nhiều lý do giải thích tại sao người ta muốn tạo một chức năng bên trong một chức năng khác. Hàm bên trong có thể truy cập các biến trong phạm vi kèm theo. Trong bài viết này, chúng ta sẽ khám phá các khía cạnh khác nhau của các hàm bên trong Python

Xác định một chức năng bên trong

Để xác định một hàm bên trong Python, chúng ta chỉ cần tạo một hàm bên trong một hàm khác bằng cách sử dụng từ khóa

def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
5 của Python. Đây là một ví dụ

đầu ra

Hello from outer function
Hello from inner function

Trong ví dụ trên,

def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
0 đã được xác định bên trong
def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
1, khiến nó trở thành một hàm bên trong. Để gọi
def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
0, trước tiên chúng ta phải gọi
def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
1. Sau đó,
def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
1 sẽ tiếp tục và gọi
def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
0 vì nó đã được xác định bên trong nó

Điều quan trọng cần đề cập là chức năng bên ngoài phải được gọi để chức năng bên trong thực thi. Nếu chức năng bên ngoài không được gọi, chức năng bên trong sẽ không bao giờ thực thi. Để chứng minh điều này, hãy sửa đổi đoạn mã trên thành đoạn mã sau và chạy nó

Mã sẽ không trả lại gì khi được thực thi

Đây là một ví dụ khác

def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))

đầu ra

________số 8

Mã trả về phép nhân của hai số, nghĩa là 10 và 5. Ví dụ cho thấy một hàm bên trong có thể truy cập các biến có thể truy cập trong hàm bên ngoài

Đến đây, bạn đã thấy rằng chúng ta có thể truy cập các biến của hàm bên ngoài bên trong hàm bên trong. Điều gì sẽ xảy ra nếu chúng ta cố gắng thay đổi các biến của hàm bên ngoài từ bên trong hàm bên trong?

đầu ra

2
9

Đầu ra cho thấy rằng chúng ta có thể hiển thị giá trị của một biến được xác định trong hàm bên ngoài từ hàm bên trong, nhưng không thể thay đổi nó. Câu lệnh

def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
6 đã giúp chúng ta tạo một biến mới
def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
7 bên trong hàm bên trong
def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
0 thay vì thay đổi giá trị của biến
def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
7 được xác định trong hàm bên ngoài
def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
1

Trong phần tiếp theo, chúng ta sẽ thảo luận về những lý do chính tại sao chúng ta sử dụng các hàm bên trong Python

Tại sao nên sử dụng Hàm bên trong?

đóng gói

Một chức năng có thể được tạo như một chức năng bên trong để bảo vệ nó khỏi mọi thứ đang xảy ra bên ngoài chức năng. Trong trường hợp đó, chức năng sẽ bị ẩn khỏi phạm vi toàn cầu. Đây là một ví dụ

Hãy xem hướng dẫn thực hành, thực tế của chúng tôi để học Git, với các phương pháp hay nhất, tiêu chuẩn được ngành chấp nhận và bao gồm bảng gian lận. Dừng các lệnh Git trên Google và thực sự tìm hiểu nó

đầu ra

def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
5

Trong đoạn mã trên, chúng tôi đang cố gắng gọi hàm

50
1, nhưng thay vào đó chúng tôi gặp lỗi

Bây giờ, hãy ghi chú cuộc gọi tới

50
1 và bỏ ghi chú cuộc gọi tới
50
3 như hình bên dưới

đầu ra

def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
9

Đoạn script trên cho thấy rằng hàm bên trong, tức là,

50
1 được bảo vệ khỏi những gì đang xảy ra bên ngoài vì biến
def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
7 bên trong hàm
50
6 không bị ảnh hưởng bởi giá trị được truyền cho tham số
def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
7 của hàm bên ngoài. Nói cách khác, các biến bên trong hàm bên trong không thể truy cập bên ngoài nó. Có một lợi thế lớn với một mẫu thiết kế như vậy. Sau khi kiểm tra tất cả các đối số trong hàm bên ngoài, chúng ta có thể bỏ qua việc kiểm tra lỗi trong hàm bên trong một cách an toàn

Chức năng đóng cửa và nhà máy

Tất cả các ví dụ chúng ta đã thấy cho đến bây giờ chỉ chứa các hàm thông thường đã được lồng vào bên trong các hàm khác. Chúng ta có thể viết các hàm như vậy theo cách khác thay vì lồng chúng vào bên trong các hàm khác. Chúng tôi không có lý do cụ thể là tại sao chúng tôi nên lồng chúng vào nhau

Tuy nhiên, đối với trường hợp bao đóng, người ta phải sử dụng các hàm lồng nhau

Chúng ta có thể liên kết/truyền dữ liệu cho một hàm mà không nhất thiết phải truyền dữ liệu cho hàm thông qua các tham số. Điều này được thực hiện bằng cách sử dụng một bao đóng. Nó là một đối tượng chức năng có thể nhớ các giá trị trong phạm vi kèm theo ngay cả khi chúng không có sẵn trong bộ nhớ. Điều này có nghĩa là chúng ta có một bao đóng khi một hàm lồng nhau tham chiếu đến một giá trị nằm trong phạm vi bao quanh của nó

Mục đích của bao đóng là làm cho hàm bên trong ghi nhớ trạng thái của môi trường khi nó được gọi, ngay cả khi nó không có trong bộ nhớ. Một đóng cửa được gây ra bởi một chức năng bên trong, nhưng nó không phải là chức năng bên trong. Việc đóng hoạt động bằng cách đóng biến cục bộ trên ngăn xếp, biến này sẽ tồn tại sau khi quá trình tạo ngăn xếp kết thúc

Sau đây là các điều kiện bắt buộc phải đáp ứng để tạo bao đóng trong Python

  • Phải có một chức năng lồng nhau
  • Hàm bên trong phải tham chiếu đến một giá trị được xác định trong phạm vi kèm theo
  • Hàm kèm theo phải trả về hàm lồng nhau

Xem xét ví dụ sau

def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
4

đầu ra

def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
5

Đoạn mã trên chứng minh rằng với bao đóng, chúng ta có thể tạo và gọi một hàm từ bên ngoài phạm vi của nó thông qua hàm truyền. Phạm vi của

def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
0 chỉ bên trong
def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
1. Tuy nhiên, với việc sử dụng các bao đóng, chúng tôi có thể mở rộng phạm vi này và gọi nó từ bên ngoài phạm vi của nó

Các hàm bên trong giúp chúng ta xác định các hàm của nhà máy. Hàm xuất xưởng là hàm tạo một đối tượng khác. Ví dụ

đầu ra

def num1(x):
   def num2(y):
      return x * y
   return num2
res = num1(10)

print(res(5))
8

Trong đoạn script trên, từ hàm

2
9
0, chúng ta đã tạo thêm 2 đối tượng khác là
2
9
1 và
2
9
2. Điều này làm cho
2
9
0 trở thành một hàm xuất xưởng vì nó tạo ra các hàm
2
9
1 và
2
9
2 cho chúng ta bằng cách sử dụng tham số mà chúng ta truyền cho nó

Sự kết luận

Một hàm bên trong chỉ đơn giản là một hàm được định nghĩa bên trong một hàm khác. Hàm bên trong có thể truy cập các biến đã được xác định trong phạm vi của hàm bên ngoài, nhưng nó không thể thay đổi chúng. Có một số lý do là tại sao chúng ta có thể cần tạo một hàm bên trong. Chẳng hạn, một chức năng bên trong được bảo vệ khỏi những gì xảy ra bên ngoài nó. Các hàm bên trong cũng là một cách hay để tạo các bao đóng trong Python

Tôi có thể gọi cùng một hàm trong một hàm trong Python không?

Python cũng chấp nhận đệ quy hàm, nghĩa là một hàm đã xác định có thể gọi chính nó . Đệ quy là một khái niệm toán học và lập trình phổ biến. Nó có nghĩa là một chức năng gọi chính nó. Điều này có lợi là bạn có thể lặp qua dữ liệu để đạt được kết quả.

Điều gì đang gọi một chức năng bên trong cùng một chức năng?

Việc gọi một hàm bên trong chính nó được gọi là đệ quy .

Các chức năng có thể thực hiện cuộc gọi đến các chức năng khác trong cùng một chương trình không?

Điều quan trọng là phải hiểu rằng mỗi hàm chúng ta viết có thể được sử dụng và gọi từ các hàm khác mà chúng ta viết. Đây là một trong những cách quan trọng nhất mà các nhà khoa học máy tính xử lý một vấn đề lớn và chia nhỏ nó thành một nhóm các vấn đề nhỏ hơn.