Iterasi adalah istilah umum untuk mengambil setiap item dari sesuatu, satu demi satu. Setiap kali Anda menggunakan loop, eksplisit atau implisit, untuk membahas sekelompok item, yaitu iterasi.
Dalam Python, iterable dan iterator memiliki arti khusus.
Sebuah iterable adalah obyek yang memiliki __iter__
metode yang mengembalikan sebuah iterator , atau yang mendefinisikan __getitem__
metode yang dapat mengambil indeks berurutan mulai dari nol (dan menimbulkan IndexError
ketika indeks tidak lagi berlaku). Jadi iterable adalah objek yang bisa Anda peroleh dari iterator .
Sebuah iterator adalah obyek dengan next
(Python 2) atau __next__
metode (Python 3).
Setiap kali Anda menggunakan for
loop, atau map
, atau daftar pemahaman, dll. Dengan Python, next
metode ini dipanggil secara otomatis untuk mendapatkan setiap item dari iterator , sehingga melalui proses iterasi .
Tempat yang baik untuk memulai pembelajaran adalah bagian iterators dari tutorial dan bagian iterator dari halaman type standar . Setelah Anda memahami dasar-dasarnya, coba bagian iterators dari HOWTO Pemrograman Fungsional .
collections.abc.AsyncIterator
tes__aiter__
dan__anext__
metode. Ini adalah tambahan baru di 3.6.__len__
harus terikat dengan iterasi? Bagaimana mengetahui panjangnya sesuatu membantu Anda mengulanginya?__getitem__
.{'a': 'hi', 'b': 'bye'}
memiliki panjang 2, tetapi tidak dapat diindeks dengan 0, 1, atau 2.__iter__
metode. Saya pikir jlh mengacu pada objek yang dapat diubah secara khusus karena mereka mendefinisikan: "__getitem__
metode yang dapat mengambil indeks berurutan mulai dari nol".Inilah penjelasan yang saya gunakan dalam mengajar kelas Python:
ITERABLE adalah:
for x in iterable: ...
atauiter()
yang akan mengembalikan ITERATOR:iter(obj)
atau__iter__
yang mengembalikan ITERATOR baru, atau mungkin memiliki__getitem__
metode yang cocok untuk pencarian yang diindeks.ITERATOR adalah objek:
__next__
metode itu:StopIteration
__iter__
metode yang mengembalikanself
).Catatan:
__next__
metode dalam Python 3 diejanext
dengan Python 2, dannext()
memanggil metode pada objek yang diteruskan ke sana.Sebagai contoh:
sumber
for
loop, dan peluru ke-1 adalah tentang "pengalihan". Bisakah Anda mengatasinya?iter()
" sebagai "apa pun yang dapat Anda berikaniter()
"Jawaban di atas bagus, tetapi karena sebagian besar dari apa yang saya lihat, jangan terlalu menekankan perbedaan untuk orang-orang seperti saya.
Juga, orang cenderung menjadi "terlalu Pythonic" dengan meletakkan definisi seperti "X adalah objek yang memiliki
__foo__()
metode" sebelumnya. Definisi seperti itu benar - mereka didasarkan pada filosofi pengetikan bebek, tetapi fokus pada metode cenderung terjadi ketika mencoba memahami konsep dalam kesederhanaannya.Jadi saya menambahkan versi saya.
Dalam bahasa alami,
Dengan Python,
iterable adalah objek yang, yah, iterable, yang sederhananya, berarti dapat digunakan dalam iterasi, misalnya dengan
for
loop. Bagaimana? Dengan menggunakan iterator . Saya akan jelaskan di bawah.... iterator sementara adalah objek yang mendefinisikan bagaimana sebenarnya melakukan iterasi - khususnya apa elemen berikutnya . Itu sebabnya harus ada
next()
metode.Iterator sendiri juga dapat diubah, dengan perbedaan bahwa
__iter__()
metode mereka mengembalikan objek yang sama (self
), terlepas dari apakah itemnya telah dikonsumsi oleh panggilan sebelumnya atau tidaknext()
.Jadi apa yang dipikirkan oleh juru bahasa Python ketika ia melihat
for x in obj:
pernyataan?Karena Mr.
obj
berhasil dalam tes ini (dengan memiliki metode tertentu mengembalikan iterator yang valid), kami menghadiahinya dengan kata sifat: Anda sekarang dapat memanggilnya "Mr. iterableobj
".Namun, dalam kasus sederhana, Anda biasanya tidak mendapat manfaat dari memiliki iterator dan iterable secara terpisah. Jadi Anda mendefinisikan hanya satu objek, yang juga merupakan iteratornya sendiri. (Python tidak benar-benar peduli yang
_i
diberikan olehobj
tidak semua yang mengkilap, tetapi hanyaobj
itu sendiri.)Inilah sebabnya mengapa dalam kebanyakan contoh yang saya lihat (dan apa yang membingungkan saya berulang kali), Anda dapat melihat:
dari pada
Namun, ada beberapa kasus ketika Anda dapat memanfaatkan iterator terpisah dari iterable, seperti ketika Anda ingin memiliki satu baris item, tetapi lebih banyak "kursor". Misalnya ketika Anda ingin bekerja dengan elemen "saat ini" dan "yang akan datang", Anda dapat memiliki iterator yang terpisah untuk keduanya. Atau beberapa utas menarik dari daftar besar: masing-masing dapat memiliki iterator sendiri untuk melintasi semua item. Lihat jawaban @ Raymond dan @ glglgl di atas.
Bayangkan apa yang bisa Anda lakukan:
Catatan:
Saya akan ulangi lagi: iterator tidak bisa diubah . Iterator tidak dapat digunakan sebagai "sumber" di
for
loop. Apa yangfor
dibutuhkan terutama loop__iter__()
(yang mengembalikan sesuatu dengannext()
).Tentu saja,
for
bukan satu-satunya loop iterasi, jadi di atas berlaku untuk beberapa konstruksi lain juga (while
...).Iterator
next()
dapat membuang StopIteration untuk menghentikan iterasi. Tidak harus, meskipun, itu dapat beralih selamanya atau menggunakan cara lain.Dalam "proses berpikir" di atas,
_i
tidak benar-benar ada. Saya telah mengarang nama itu.Ada perubahan kecil dalam Python 3.x:
next()
metode (bukan built-in) sekarang harus dipanggil__next__()
. Ya, seharusnya seperti itu selama ini.Anda juga dapat menganggapnya seperti ini: iterable memiliki data, iterator menarik item berikutnya
Penafian: Saya bukan pengembang interpreter Python, jadi saya tidak benar-benar tahu apa yang "dipikirkan" penerjemah. Renungan di atas semata-mata menunjukkan bagaimana saya memahami topik dari penjelasan lain, percobaan dan pengalaman kehidupan nyata dari seorang pemula Python.
sumber
for
loop membutuhkan iterator ("Lihat, for for loop. Sepertinya pekerjaan untuk iterator ... Mari kita mendapatkannya."). Tetapi kemudian Anda mengatakan dalam catatan di akhir bahwa "Iterator tidak dapat digunakan sebagai sumber dalam satufor
loop" ...?pass
kode untuknext
definisi tersebut? Saya berasumsi Anda hanya bermaksud bahwa seseorang harus menerapkan cara untuk mendapatkan yang berikutnya, karena berikutnya harus mengembalikan sesuatu.pass
bagi , setelah semua.)pass
, saya pikir itu ada karena alasan sintaksis. Saya hanya berlari melintasi jawaban di objek elipsis yang cukup menarik: Anda dapat menggunakan...
untuk menunjukkan blok "todo later".NotImplemented
juga tersedia.for
loop '. Saya mendapatkan inti dari jawaban Anda, dan menyukainya sebaliknya, tetapi saya pikir itu akan bermanfaat dengan memperbaikinya.Iterable adalah objek yang memiliki
__iter__()
metode. Mungkin dapat diulang beberapa kali, sepertilist()
s dantuple()
s.Iterator adalah objek yang diulang. Itu dikembalikan oleh suatu
__iter__()
metode, mengembalikan dirinya sendiri melalui__iter__()
metode sendiri dan memilikinext()
metode (__next__()
dalam 3.x).Iterasi adalah proses memanggil
next()
resp ini .__next__()
sampai meningkatStopIteration
.Contoh:
sumber
Iterable
.Iterator
selaluIterable
dan adalah miliknya sendiriIterator
, dua panggilaniter()
tidak harus memberikan dua yang independenIterator
.Inilah lembar contekan saya:
Kuis: Apakah Anda melihat caranya ...
__iter__()
metode dapat diimplementasikan sebagai generator?__next__
metode belum tentu merupakan iterator?Jawaban:
__iter__
metode. Memiliki__iter__
cukup untuk menjadi sesuatu yang bisa diubah. Karena itu setiap iterator adalah iterable.Ketika
__iter__
dipanggil itu harus mengembalikan iterator (return <iterator>
dalam diagram di atas). Memanggil generator mengembalikan generator iterator yang merupakan jenis iterator.Berikut ini sebuah contoh:
sumber
__iter__
metode. Tolong__iter__()
mengembalikan iterator. Generator adalah iterator, sehingga dapat digunakan untuk tujuan ini. kembali 3 .: Saya hanya bisa menebak di sini, tapi saya pikir jika__iter__()
hilang, atau tidak kembaliself
, itu bukan iterator, karena iterator__iter__()
harus kembaliself
.Saya tidak tahu apakah itu membantu siapa pun tetapi saya selalu suka memvisualisasikan konsep di kepala saya untuk lebih memahami mereka. Jadi ketika saya memiliki seorang putra kecil saya memvisualisasikan konsep iterable / iterator dengan batu bata dan kertas putih.
Misalkan kita berada di ruangan gelap dan di lantai kita punya batu bata untuk anakku. Batu bata dengan ukuran berbeda, warna, tidak masalah sekarang. Misalkan kita punya 5 bata seperti itu. Kelima bata itu dapat digambarkan sebagai objek - misalkan kit bata . Kita dapat melakukan banyak hal dengan kit batu bata ini - dapat mengambil satu dan kemudian mengambil kedua dan ketiga, dapat mengubah tempat batu bata, meletakkan bata pertama di atas yang kedua. Kita dapat melakukan banyak hal dengan itu. Oleh karena itu kit batu bata ini adalah objek atau urutan yang dapat diubah karena kita dapat melewati setiap bata dan melakukan sesuatu dengannya. Kami hanya bisa melakukannya seperti putra kecil saya - kami bisa bermain dengan satu bata pada satu waktu . Jadi sekali lagi saya bayangkan sendiri kit batu bata ini menjadiiterable .
Sekarang ingatlah bahwa kita berada di ruangan gelap. Atau hampir gelap. Masalahnya adalah kita tidak melihat dengan jelas batu bata itu, apa warnanya, bentuk apa, dll. Jadi, bahkan jika kita ingin melakukan sesuatu dengan mereka - alias mengulanginya - kita tidak benar-benar tahu apa dan bagaimana karena itu terlalu gelap.
Apa yang bisa kita lakukan adalah dekat dengan bata pertama - sebagai elemen kit batu bata - kita dapat meletakkan selembar kertas fluoresens putih agar kita dapat melihat di mana elemen bata pertama berada. Dan setiap kali kita mengambil batu bata dari kit, kita mengganti selembar kertas putih ke batu bata berikutnya agar dapat melihatnya di ruangan gelap. Selembar kertas putih ini tidak lebih dari sebuah iterator . Itu juga obyek . Tapi sebuah objek dengan apa yang bisa kita kerjakan dan mainkan dengan elemen dari objek kita yang dapat diubah - kit batu bata.
Omong-omong menjelaskan kesalahan awal saya ketika saya mencoba yang berikut di IDLE dan mendapat TypeError:
Daftar X di sini adalah kit batu bata kami tetapi BUKAN selembar kertas putih. Saya perlu menemukan iterator terlebih dahulu:
Tidak tahu apakah itu membantu, tetapi itu membantu saya. Jika seseorang dapat mengkonfirmasi / memperbaiki visualisasi konsep, saya akan berterima kasih. Itu akan membantu saya untuk belajar lebih banyak.
sumber
Iterable : - sesuatu yang dapat diubah adalah dapat diubah; seperti urutan seperti daftar, string dll. Juga memiliki
__getitem__
metode atau__iter__
metode. Sekarang jika kita menggunakaniter()
fungsi pada objek itu, kita akan mendapatkan iterator.Iterator : - Ketika kita mendapatkan objek iterator dari
iter()
fungsi; kita memanggil__next__()
metode (dalam python3) atau hanyanext()
(dalam python2) untuk mendapatkan elemen satu per satu. Kelas atau turunan dari kelas ini disebut iterator.Dari dokumen: -
Penggunaan iterator meliputi dan menyatukan Python. Di belakang layar, pernyataan for memanggil
iter()
objek kontainer. Fungsi mengembalikan objek iterator yang mendefinisikan metode__next__()
yang mengakses elemen dalam wadah satu per satu. Ketika tidak ada elemen lagi,__next__()
memunculkan eksepsi StopIteration yang memberitahu for loop untuk mengakhiri. Anda dapat menghubungi__next__()
metode menggunakannext()
fungsi bawaan; contoh ini menunjukkan cara kerjanya:Mantan kelas: -
sumber
Saya tidak berpikir Anda bisa membuatnya lebih sederhana daripada dokumentasi , namun saya akan mencoba:
Anda dapat menganggap Iterator sebagai metode pseudo pembantu (atau atribut semu) yang memberikan (atau menahan) item berikutnya (atau pertama) di iterable . (Dalam praktiknya itu hanya objek yang mendefinisikan metode
next()
)Iterasi mungkin paling baik dijelaskan dengan definisi kata Merriam-Webster :
sumber
begitu,
iterable
adalah objek yang dapat dilingkarkan . mis. daftar, string, tuple dll.menggunakan
iter
fungsi padaiterable
objek kita akan mengembalikan objek iterator.sekarang objek iterator ini memiliki metode bernama
__next__
(dalam Python 3, atau hanyanext
dalam Python 2) dimana Anda dapat mengakses setiap elemen iterable.jadi, OUTPUT OF KODE DI ATAS AKAN:
1
2
sumber
Luciano Ramalho, Fluent Python.
sumber
Sebelum berurusan dengan iterables dan iterator, faktor utama yang menentukan iterable dan iterator adalah urutan
Sequence: Sequence adalah kumpulan data
Iterable: Iterable adalah objek tipe urutan yang mendukung
__iter__
metode.Metode Iter: Metode Iter mengambil urutan sebagai input dan membuat objek yang dikenal sebagai iterator
Iterator: Iterator adalah objek yang memanggil metode berikutnya dan melintang melalui urutan. Saat memanggil metode berikutnya, ia mengembalikan objek yang dilaluinya saat ini.
contoh:
x adalah urutan yang terdiri dari kumpulan data
Saat memanggilnya
iter(x)
mengembalikan iterator hanya ketika objek x memiliki metode iter jika tidak maka akan memunculkan eksepsi. Jika ia mengembalikan iterator maka y ditugaskan seperti ini:Karena y adalah iterator maka itu mendukung
next()
metodeSaat memanggil metode berikutnya, ia mengembalikan elemen individual dari daftar satu per satu.
Setelah mengembalikan elemen terakhir dari urutan jika kita kembali memanggil metode berikutnya itu meningkatkan kesalahan StopIteration
contoh:
sumber
Dalam Python semuanya adalah objek. Ketika suatu objek dikatakan iterable, itu berarti bahwa Anda dapat melangkah (yaitu iterate) objek sebagai koleksi.
Array misalnya dapat diubah. Anda dapat melangkah melaluinya dengan for loop, dan beralih dari indeks 0 ke indeks n, n menjadi panjang objek array minus 1.
Kamus (pasangan kunci / nilai, juga disebut array asosiatif) juga dapat diubah. Anda dapat menelusuri kunci-kunci mereka.
Jelas benda-benda yang bukan koleksi tidak bisa diubah. Objek bool misalnya hanya memiliki satu nilai, Benar atau Salah. Itu tidak dapat diubah (tidak masuk akal bahwa itu adalah objek yang dapat diubah).
Baca lebih banyak. http://www.lepus.org.uk/ref/companion/Iterator.xml
sumber
iter()
jenis koleksi standar dapat diubah tetapi tidak, itu sendiri, koleksi.