Đối tượng 'dict' không có thuộc tính 'has_key'


105

Trong khi duyệt qua một biểu đồ bằng Python, tôi nhận được lỗi này:

Đối tượng 'dict' không có thuộc tính 'has_key'

Đây là mã của tôi:

def find_path(graph, start, end, path=[]):
    path = path + [start]
    if start == end:
        return path
    if not graph.has_key(start):
        return None
    for node in graph[start]:
        if node not in path:
            newpath = find_path(graph, node, end, path)
            if newpath: return newpath
    return None

Mã nhằm mục đích tìm đường dẫn từ một nút đến các nút khác. Nguồn mã: http://cs.mwsu.edu/~terry/courses/4883/lectures/graphs.html

Tại sao tôi gặp lỗi này và làm cách nào để khắc phục?


2
if not start in graph:
Peter Wood,

1
Có thể có bản sao của 'has_key ()' hoặc 'in'?
Peter Wood,

Câu trả lời:


180

has_keyđã bị xóa trong Python 3. Từ tài liệu :

  • Đã xóa dict.has_key()- sử dụng intoán tử thay thế.

Đây là một ví dụ:

if start not in graph:
    return None

1
Tôi nghĩ key not in d.keys()có lẽ cũng chậm hơn nhiều , vì key not in dnên tra cứu O (1) và tôi tin rằng keystạo ra một danh sách, là tra cứu O (n) (chưa kể đến việc chiếm thêm dung lượng trong bộ nhớ). Mặc dù vậy, tôi có thể sai về điều đó - nó vẫn có thể được tra cứu băm
Adam Smith

3
@AdamSmith không có trong Python 3, d.keys()là một dạng xem triển khai hầu hết giao diện đã đặt.
Antti Haapala

3
Nó bị loại bỏ ... nhưng tại sao? Vì nó làm cho python 2 cổng thành python 3 nhiều việc phải làm hơn.
Trái cây

1
@ 林果 皞: Toàn bộ điểm của một phiên bản chính mới là các nhà phát triển có thể giới thiệu các cải tiến có thể bao gồm các thay đổi đột phá thay vì phải hỗ trợ các tính năng cũ khi ngôn ngữ trưởng thành. Đây luôn là một rủi ro phải được cân nhắc trước khi nâng cấp lên phiên bản chính mới. Trong trường hợp này, inPythonic ngắn hơn và nhiều hơn, cũng như phù hợp với các bộ sưu tập khác trong ngôn ngữ.
johnnyRose

23

has_key đã không được chấp nhận trong Python 3.0 . Ngoài ra, bạn có thể sử dụng 'in'

graph={'A':['B','C'],
   'B':['C','D']}

print('A' in graph)
>> True

print('E' in graph)
>> False

17

Trong python3, has_key(key)được thay thế bằng__contains__(key)

Đã kiểm tra trong python3.7:

a = {'a':1, 'b':2, 'c':3}
print(a.__contains__('a'))

5

Tôi nghĩ rằng nó được coi là "khó hiểu hơn" nếu chỉ sử dụng inkhi xác định xem khóa đã tồn tại hay chưa, như trong

if start not in graph:
    return None

Tôi không chắc, theo The Zen of Python (PEP 20): "Rõ ràng tốt hơn là ngầm hiểu". Tôi nghĩ rằng nếu bạn sử dụng intừ khóa, ý định của bạn có thể không đủ rõ ràng if start not in graph:nghĩa là gì? có thể graphlà một danh sách và nó sẽ kiểm tra nếu không có chuỗi như vậy trong danh sách? Mặt khác, nếu bạn sử dụng cú pháp như has_key(hiện không được dùng nữa) hoặc ít nhất in graph.keys()thì nó rõ ràng hơn graphlà adict
Amitay Drummer

4

Toàn bộ mã trong tài liệu sẽ là:

graph = {'A': ['B', 'C'],
             'B': ['C', 'D'],
             'C': ['D'],
             'D': ['C'],
             'E': ['F'],
             'F': ['C']}
def find_path(graph, start, end, path=[]):
        path = path + [start]
        if start == end:
            return path
        if start not in graph:
            return None
        for node in graph[start]:
            if node not in path:
                newpath = find_path(graph, node, end, path)
                if newpath: return newpath
        return None

Sau khi viết xong, hãy lưu tài liệu và nhấn F 5

Sau đó, mã bạn sẽ chạy trong trình bao Python IDLE sẽ là:

find_path (đồ thị, 'A', 'D')

Câu trả lời bạn sẽ nhận được trong IDLE là

['A', 'B', 'C', 'D'] 

Bạn có thể vui lòng giải thích nó? Cụ thể là phần đệ quy.
Encipher

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.