2012-05-02 45 views
16

Nó ngăn cản tôi làm thế nào tôi không thể tìm thấy một lời giải thích rõ ràng về điều này bất cứ nơi nào. Tại sao và khi nào bạn cần gọi phương thức của lớp cơ sở bên trong cùng một phương thức tên của lớp con?Thừa kế Python - gọi các phương thức lớp cơ sở bên trong lớp con?

class Child(Base): 
    def __init__(self): 
     Base.__init__(self) 

    def somefunc(self): 
     Base.somefunc(self) 

Tôi đoán bạn làm điều này khi bạn không muốn ghi đè hoàn toàn phương thức trong lớp cơ sở. đó thực sự là tất cả với nó?

Trả lời

2

Nó hoàn toàn phụ thuộc vào lớp và phương pháp.

Nếu bạn chỉ muốn làm điều gì đó trước/sau khi phương thức cơ sở chạy hoặc gọi nó với các đối số khác nhau, bạn rõ ràng gọi phương thức cơ sở trong phương thức của lớp con.

Nếu bạn muốn thay thế toàn bộ phương pháp, bạn rõ ràng không gọi nó.

+0

Tuy nhiên, bạn nên luôn gọi lớp cha ''__init__'. – Amber

13

Thông thường, bạn làm điều này khi bạn muốn mở rộng chức năng bằng cách sửa đổi, nhưng không thay thế hoàn toàn phương thức lớp cơ sở. defaultdict là một ví dụ tốt về điều này:

class DefaultDict(dict): 
    def __init__(self, default): 
     self.default = default 
     dict.__init__(self) 

    def __getitem__(self, key): 
     try: 
      return dict.__getitem__(self, key) 
     except KeyError: 
      result = self[key] = self.default() 
      return result 

Lưu ý rằng cách thích hợp để làm điều này là để use super instead of directly calling the base class. Giống như vậy:

class BlahBlah(someObject, someOtherObject): 
    def __init__(self, *args, **kwargs): 
     #do custom stuff 
     super(BlahBlah, self).__init__(*args, **kwargs) # now call the parent class(es) 
+0

Có gì tuyệt vời về chức năng "siêu" này? – user1369281

+5

@ user1369281: Vâng, chúng không phải lúc nào cũng tuyệt vời. Tuy nhiên, nếu bạn sử dụng chúng một cách nhất quán, chúng sẽ làm cho cây thừa kế dễ dàng hơn nhiều khi làm việc. Điều gì sẽ xảy ra nếu, ví dụ, tôi muốn thay đổi 'defaultdict' thành mặc định _ordered_ dict. Nếu tôi sử dụng 'super()', điều _only_ tôi sẽ phải thay đổi trong mã của tôi sẽ là định nghĩa lớp. Tất cả những gì 'super' tự động tham chiếu đến bất cứ lớp cơ sở nào mà lớp hiện tại của tôi được kế thừa từ đó. Nó tạo điều kiện cho lập trình hộp đen. –

+0

Tôi thích điều này vì nó nhắc bạn (hoặc dạy) rằng lớp của bạn có thể kế thừa nhiều lớp. Vì vậy, nếu lớp cha của bạn là từ một lib bạn không thể sửa đổi và không kế thừa đối tượng đã có, bạn chỉ có thể thêm 'đối tượng' vào lớp của bạn. – casey

Các vấn đề liên quan