2013-03-05 37 views
9

tôi mới lập trình và đang cố gắng tính toán độ sâu của cây trăn. Tôi tin rằng lỗi của tôi là bởi vì chiều sâu là một phương thức của lớp Node và không phải là một hàm bình thường. Tôi đang cố gắng tìm hiểu oop và hy vọng sẽ sử dụng một phương pháp. Đây có thể là một lỗi ong mới ... Đây là mã của tôi:độ sâu của một cây trăn cây

class Node: 

    def __init__(self, item, left=None, right=None): 
     """(Node, object, Node, Node) -> NoneType 
     Initialize this node to store item and have children left and right. 
     """ 
     self.item = item 
     self.left = left 
     self.right = right 

    def depth(self): 
     if self.left == None and self.right == None: 
      return 1 

     return max(depth(self.left), depth(self.right)) + 1 

i receive this error: 

>>>b = Node(100) 

>>>b.depth() 

1 

>>>a = Node(1, Node(2), Node(3)) 

>>>a.depth() 

Traceback (most recent call last): 
    File "C:\Program Files\Wing IDE 101 4.1\src\debug\tserver\_sandbox.py", line 1, in <module> 
    # Used internally for debug sandbox under external interpreter 
    File "C:\Program Files\Wing IDE 101 4.1\src\debug\tserver\_sandbox.py", line 15, in depth 
builtins.NameError: global name 'depth' is not defined 
+0

+1 để trực tiếp khắc phục sự cố của bạn. –

+1

Để tham khảo trong tương lai, tôi tin rằng 'ong mới' được viết là' newbie', nếu tôi không nhầm. –

+0

Trực giác là một phần chính xác (gọi 'depth()' là một phương thức giải quyết vấn đề), nhưng phần nào không đầy đủ. Nguyên nhân gốc giải thích tại sao bạn không thể truy cập phương thức từ bên trong chính nó nhưng bạn có thể với một hàm bình thường là một chi tiết liên quan đến cách thức phạm vi và lớp định nghĩa hoạt động trong Python. Khi bạn gọi một hàm mức mô-đun thông thường, phạm vi "toàn cục" sẽ là mô-đun được định nghĩa trong đó, chứa hàm này. Tuy nhiên, phạm vi mà các phương thức được định nghĩa có thể được coi là bị loại bỏ sau khi đối tượng kiểu được tạo. – millimoose

Trả lời

7
def depth(self): 
    if self.left == None and self.right == None: 
     return 1 

    return max(depth(self.left), depth(self.right)) + 1 

nên

def depth(self): 
    return max(self.left.depth() if self.left else 0, self.right.depth() if self.right else 0) + 1 

Một phiên bản dễ đọc hơn:

def depth(self): 
    left_depth = self.left.depth() if self.left else 0 
    right_depth = self.right.depth() if self.right else 0 
    return max(left_depth, right_depth) + 1 

Vấn đề là rằng không có chức năng depth. Đó là một phương thức của đối tượng Node, vì vậy bạn sẽ cần phải gọi nó từ chính đối tượng đó (trái và phải). Tôi rút ngắn mã thành self.left.depth() if self.left else 0self.right.depth() if self.right else 0 để xóa các kiểm tra bạn đã có trước đây (chúng ẩn) vì tôi tin rằng hoàn toàn có thể là bên trái là None trong khi bên phải là Node hoặc ngược lại, điều này sẽ gây ra mã gốc để ném một số AttributeError từ None không có phương thức depth.

Sửa

Để đối phó với những câu hỏi về <something> if <some condition> else <otherwise> khối:

Dòng cho <something> nếu <some condition> là đúng-y (coi là true), và <otherwise> nếu <some condition> là sai-y (được coi là sai)

+0

Tôi tin rằng bạn muốn gọi 'depth' vì nó là một hàm :) – Wolph

+1

Nghiền nó thành một dòng là một chút không đọc được, nhưng đây là câu trả lời đúng. – Hamish

+0

Chẳng phải 'Node' sẽ cần phương thức' __bool__' hoặc '__nonzero__' cho các phép thử' if self.left' để thực sự hoạt động? – Marius

2

Để rõ ràng, tôi khuyên bạn nên viết phương pháp depth như sau:

def depth(self): 
    current_depth = 0 

    if self.left: 
     current_depth = max(current_depth, self.left.depth()) 

    if self.right: 
     current_depth = max(current_depth, self.right.depth()) 

    return current_depth + 1 
+3

Để rõ ràng, tôi khuyên bạn không nên sử dụng cùng tên cho phương thức và biến cục bộ trong đó. – millimoose

+0

Vì vậy, tất cả các nút có cùng độ sâu 1? Tại sao lại thê nay? – Hyperboreus

+0

@ Hyperboreus: đây thực chất là những gì mã của anh ấy đang làm, tôi đã không kiểm tra tính chính xác. Đơn giản chỉ cần đưa ra một mô hình dễ đọc hơn :) – Wolph

1

Lỗi xuất phát từ dòng này:

return max(depth(self.left), depth(self.right)) + 1 

Bạn đang sử dụng chiều sâu như một chức năng và cố gắng để áp dụng nó vào các nút trái và phải. Bởi vì các nút trái và phải cũng là các nút, chúng có phương thức chiều sâu.

Bạn nên gọi phương thức sâu như thế này:

return max(self.left.depth(), self.right.depth()) + 1 

Tham số tự được ngầm truyền cho phương thức chiều sâu, nhưng sử dụng nó với các nhà điều hành chấm kể Python rằng phương pháp này thuộc về một trường hợp Node, và nó không phải là một số chức năng khác không bị ràng buộc với một đối tượng.

0

Bạn đã có bốn trường hợp để xem xét:

  1. Cả hai subtrees đang trống.
  2. Chỉ còn lại một cây con trái.
  3. Chỉ cần một cây con bên phải trống.
  4. Không có cây con nào trống.

Bạn đã bảo hiểm các trường hợp 1 và 4 nhưng đã bỏ lỡ 2 và 3. Bản sửa lỗi:

# Return height of tree rooted at this node. 
def depth(self): 
    if self.left == None and self.right == None: 
     return 1 
    elif self.left == None: 
     return self.right.depth() + 1 
    elif self.right == None: 
     return self.left.depth() + 1 
    else: 
     return max(self.left.depth(), self.right.depth()) + 1 
Các vấn đề liên quan