Bagaimana cara saya memeriksa apakah ada sesuatu (tidak) dalam daftar dengan Python?
Solusi termurah dan paling mudah dibaca adalah menggunakan in
operator (atau dalam kasus khusus Anda, not in
). Seperti disebutkan dalam dokumentasi,
Operator in
dan not in
uji keanggotaan. x in s
mengevaluasi
True
apakah x
adalah anggota s
, dan False
sebaliknya. x not in s
mengembalikan negasi dari x in s
.
Selain itu,
Operator not in
didefinisikan memiliki nilai true kebalikan dari in
.
y not in x
secara logis sama dengan not y in x
.
Berikut ini beberapa contoh:
'a' in [1, 2, 3]
# False
'c' in ['a', 'b', 'c']
# True
'a' not in [1, 2, 3]
# True
'c' not in ['a', 'b', 'c']
# False
Ini juga berfungsi dengan tupel, karena tupel dapat hashable (sebagai konsekuensi dari fakta bahwa tuple juga tidak berubah):
(1, 2) in [(3, 4), (1, 2)]
# True
Jika objek pada RHS mendefinisikan suatu __contains__()
metode, in
secara internal akan memanggilnya, seperti yang disebutkan dalam paragraf terakhir dari bagian Perbandingan dari dokumen.
... in
dan not in
, didukung oleh tipe yang dapat diterapkan atau mengimplementasikan
__contains__()
metode. Misalnya, Anda dapat (tetapi tidak seharusnya) melakukan ini:
[3, 2, 1].__contains__(1)
# True
in
sirkuit pendek, jadi jika elemen Anda berada di awal daftar, in
evaluasi lebih cepat:
lst = list(range(10001))
%timeit 1 in lst
%timeit 10000 in lst # Expected to take longer time.
68.9 ns ± 0.613 ns per loop (mean ± std. dev. of 7 runs, 10000000 loops each)
178 µs ± 5.01 µs per loop (mean ± std. dev. of 7 runs, 10000 loops each)
Jika Anda ingin melakukan lebih dari sekadar memeriksa apakah suatu item ada dalam daftar, ada beberapa opsi:
list.index
dapat digunakan untuk mengambil indeks suatu item. Jika elemen itu tidak ada, a ValueError
dinaikkan.
list.count
dapat digunakan jika Anda ingin menghitung kejadian.
Masalah XY: Sudahkah Anda mempertimbangkan set
s?
Tanyakan pada diri Anda pertanyaan-pertanyaan ini:
- apakah Anda perlu memeriksa apakah suatu item ada dalam daftar lebih dari satu kali?
- Apakah pemeriksaan ini dilakukan di dalam loop, atau fungsi yang dipanggil berulang kali?
- Apakah barang-barang yang Anda simpan di daftar Anda bisa dipecahkan? TKI, bisakah Anda memanggil
hash
mereka?
Jika Anda menjawab "ya" untuk pertanyaan ini, Anda seharusnya menggunakan kata set
ganti. Tes in
keanggotaan pada list
s adalah O (n) kompleksitas waktu. Ini berarti bahwa python harus melakukan pemindaian linear daftar Anda, mengunjungi setiap elemen dan membandingkannya dengan item pencarian. Jika Anda melakukan ini berulang kali, atau jika daftarnya besar, operasi ini akan menimbulkan biaya tambahan.
set
objek, di sisi lain, hash nilainya untuk cek keanggotaan waktu konstan. Pemeriksaan juga dilakukan dengan menggunakan in
:
1 in {1, 2, 3}
# True
'a' not in {'a', 'b', 'c'}
# False
(1, 2) in {('a', 'c'), (1, 2)}
# True
Jika Anda cukup disayangkan bahwa elemen yang Anda cari / tidak cari ada di akhir daftar Anda, python akan memindai daftar hingga akhir. Ini terbukti dari timing di bawah ini:
l = list(range(100001))
s = set(l)
%timeit 100000 in l
%timeit 100000 in s
2.58 ms ± 58.9 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)
101 ns ± 9.53 ns per loop (mean ± std. dev. of 7 runs, 10000000 loops each)
Sebagai pengingat, ini adalah opsi yang cocok selama elemen yang Anda simpan dan cari dapat di-hashable. TKI, mereka harus berupa tipe yang tidak berubah, atau objek yang mengimplementasikan __hash__
.
3 -1 > 0 and (4-1 , 5) not in []
⤇True
karena itu kesalahannya bukan merupakan prioritas operator.