2011-12-23 12 views
12

Nếu tôi có một đối tượng so sánh với một phần tử của một bộ Python, nhưng không phải là cùng một đối tượng, có cách nào hợp lý để có được một tham chiếu đến đối tượng trong bộ này không? Trường hợp sử dụng sẽ sử dụng bộ này để xác định và chia sẻ dữ liệu trùng lặp.Làm thế nào để truy cập vào một phần tử của một tập hợp bằng cách sử dụng một đối tượng tương đương?

Ví dụ (Python 2.7):

>>> a = "This is a string" 
>>> b = "This is a string" 
>>> a is b 
False 
>>> a == b 
True 
>>> s = set((a,)) 
>>> b in s 
True 

Làm thế nào để có được một tài liệu tham khảo để a sử dụng bs? Tôi có thể nghĩ ra một cách, nhưng tôi không chắc chắn liệu nó có phụ thuộc vào việc thực hiện hay không bạn có nhận được a hoặc b hay không. EDIT: Điều này không hoạt động khi s có nhiều hơn một phần tử; ngã tư là khá tự nhiên thực hiện một cái gì đó giống như [x for x in smaller_set if x in larger_set]

>>> for x in set((b,)).intersection(s): c = x 
... 
>>> c is a 
True 

Có lẽ một workaround tốt sẽ được sử dụng một dict mà các bản đồ mỗi chìa khóa để bản thân, thay vì các thiết lập.

+2

Nếu bạn cần một trong hai đối tượng bằng nhau, có thể băm, có vẻ như các đối tượng không được bằng nhau và/hoặc có thể băm. Tại sao bạn cần điều này? – delnan

+0

Tôi nghĩ rằng sự nghi ngờ của bạn là hợp lý: pypy 1.7.0 và ironpython 3.0 cả hai (có thể) trả về False cho c cuối cùng của bạn là a. – DSM

+0

Tôi có thể lưu bộ nhớ bằng cách thay đổi tham chiếu đến đối tượng bằng nhau thành tham chiếu đến cùng một đối tượng. –

Trả lời

3

Tôi đã tìm thấy câu hỏi tương tự trên danh sách python: Get item from set. Có một câu trả lời thông minh với tham chiếu đến get_equivalent(container, item) (Python recipe).

Bí quyết là xây dựng đối tượng bao bọc cho đối tượng 'khóa' và kiểm tra xem trình bao bọc có nằm trong tập hợp bằng toán tử in hay không. Nếu băm bọc bằng khóa, phương thức __eq__ của nó có thể có quyền truy cập vào đối tượng trong bộ và lưu tham chiếu đến nó. Một điểm quan trọng từ cuộc thảo luận là phương pháp __eq__ của các phần tử đã đặt phải trả lại NotImplemented cho các loại không được công nhận, nếu không, thì không thể gọi được số __eq__ của trình bao bọc.

1

Trường hợp sử dụng của bạn có vẻ như đây là trường hợp sử dụng cho từ điển. Sử dụng, như các phím, thuộc tính của đối tượng so sánh với đối tượng "nước ngoài", và làm giá trị cho các đối tượng mong muốn.

Nếu nó là một trường hợp sử dụng đơn giản, và bạn có thể có một seartch tuyến tính, tuy nhiên, bạn có thể làm rõ ràng - nó sẽ không được xấu:

def get_equal(in_set, in_element): 
    for element in in_set: 
     if element == in_element: 
      return element 
    return None 

Nếu bạn cần những gì chính xác những gì bạn ar hỏi (Tôi có thể tự hỏi một số trường hợp sử dụng cho điều đó) - wya để đi là tạo một lớp từ điển tùy chỉnh có một bộ là thành viên của nó, thực hiện các proxy mehthods cho tập hợp thành viên, và cả từ điển và phương thức thiết lập, giữ đồng bộ hóa cả từ điển và nội dung cài đặt. Điều này sẽ tốn thời gian để thực hiện đúng, nhưng tương đối đơn giản.

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