Cách tham gia hai bộ trong một dòng mà không cần sử dụng


171

Giả sử rằng STđược chỉ định bộ. Không sử dụng toán tử nối |, làm thế nào tôi có thể tìm thấy sự kết hợp của hai bộ? Điều này, ví dụ, tìm giao điểm:

S = {1, 2, 3, 4}
T = {3, 4, 5, 6}
S_intersect_T = { i for i in S if i in T }

Vậy làm thế nào tôi có thể tìm thấy sự kết hợp của hai bộ trong một dòng mà không cần sử dụng |?


1
bạn có cần liên minh không? Nếu có thì bạn có thể làm s.union (t)
Ansuman Bebarta

59
Tại sao bạn không thể sử dụng |?
Scott Bartell

1
Bất kỳ lý do chung chung không sử dụng |?
matanster

5
Một lý do có thể là thông qua một hoạt động thiết lập như là một đối số chức năng. Hãy tưởng tượng một chức năng, một cái gì đó như : def apply_set_operation(a, b, set_operation). Khi gọi chức năng này, tôi muốn apply_set_operation(a, b, set.union)đếnapply_set_operation(a, b, set.__or__)
BSA

Câu trả lời:


309

Bạn có thể sử dụng phương thức union cho các bộ: set.union(other_set)

Lưu ý rằng nó trả về một bộ mới tức là nó không tự sửa đổi.


54
Tuy nhiên, |có thể sửa đổi biến nội tuyến:set_a |= set_b
jorgenkg 17/2/2016

12
@jorgenkg giống như : set_a = set_a.union(set_b). Nếu bạn có nghĩa là "tại chỗ", cả hai sẽ không làm điều đó, cả hai sẽ tạo ra một thứ mớiset

3
@jorgenkg nó vẫn tạo một bộ mới và thay thế tham chiếu.
Alvaro

3
@Alvaro @nitely theo một thử nghiệm đơn giản : a = set((1, 2, 3,)); b = set((1, 3, 4,)); id_a = id(a); a |= b; assert id_a == id(a), @jorgenkg là đúng - biến ađược sửa đổi nội tuyến. Tui bỏ lỡ điều gì vậy?
johndodo

3
Không, không giống như nó : a = set((1, 2, 3,)); b = set((1, 3, 4,)); c = a; a |= b; assert id(c) == id(a). Ngay cả khi ađã bị phá hủy, csẽ không được. Ngoài ra, cbây giờ set([1, 2, 3, 4]), vì vậy nhận xét của @ jorgenkg là chính xác.
johndodo

45

Bạn có thể sử dụng or_bí danh:

>>> from operator import or_
>>> from functools import reduce # python3 required
>>> reduce(or_, [{1, 2, 3, 4}, {3, 4, 5, 6}])
set([1, 2, 3, 4, 5, 6])

9
thích cách tiếp cận này, nhiều chức năng hơn và có thể được áp dụng cho 2 hoặc nhiều bộ.
Colin Su

41

Nếu bạn ổn với việc sửa đổi bộ gốc (mà bạn có thể muốn làm trong một số trường hợp), bạn có thể sử dụng set.update():

S.update(T)

Giá trị trả về là None, nhưng Ssẽ được cập nhật thành liên kết của bản gốc ST.


23

Giả sử bạn cũng không thể sử dụng s.union(t), tương đương với s | t, bạn có thể thử

>>> from itertools import chain
>>> set(chain(s,t))
set([1, 2, 3, 4, 5, 6])

Hoặc, nếu bạn muốn hiểu

>>> {i for j in (s,t) for i in j}
set([1, 2, 3, 4, 5, 6])

14

Nếu tham gia bạn có nghĩa là liên minh, hãy thử điều này:

set(list(s) + list(t))

Đó là một chút hack, nhưng tôi không thể nghĩ ra một lớp lót tốt hơn để làm điều đó.


set (list (s) + list (t)) sẽ cho bạn kết quả tương tự nếu bạn sẽ thực hiện một liên minh.
Ansuman Bebarta

Tôi biết, nhưng có vẻ như anh ta đang cố tránh sử dụng các hàm python tích hợp, nếu không anh ta sẽ chỉ sử dụng | nhà điều hành.
BenjaminCohen

listsetđược xây dựng trong các chức năng python
whackamadoodle3000

10

Giả sử bạn có 2 danh sách

 A = [1,2,3,4]
 B = [3,4,5,6]

để bạn có thể tìm thấy AUnion Bnhư sau

 union = set(A).union(set(B))

Ngoài ra nếu bạn muốn tìm giao lộ và không giao nhau, bạn làm như vậy

 intersection = set(A).intersection(set(B))
 non_intersection = union - intersection

7

Bạn chỉ có thể giải nén cả hai bộ thành một như thế này:

>>> set_1 = {1, 2, 3, 4}
>>> set_2 = {3, 4, 5, 6}
>>> union = {*set_1, *set_2}
>>> union
{1, 2, 3, 4, 5, 6}

Việc *giải nén bộ. Giải nén là nơi một iterable (ví dụ: một tập hợp hoặc danh sách) được biểu diễn như mọi mục mà nó mang lại. Điều này có nghĩa là ví dụ trên đơn giản hóa để {1, 2, 3, 4, 3, 4, 5, 6}sau đó đơn giản hóa {1, 2, 3, 4, 5, 6}vì tập hợp chỉ có thể chứa các mục duy nhất.


Làm gì *trong dòng 3?
altabq

5

Bạn có thể làm unionhoặc hiểu danh sách đơn giản

[A.add(_) for _ in B]

A sẽ có tất cả các yếu tố của B


sử dụng sự hiểu biết danh sách cho các tác dụng phụ và với param ẩn danh là thực hành siêu xấu.
Jean-François Fabre
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.