जवाबों:
इसे सीधे शब्दों में कहें तो पुनरावृत्तियां राज्य रखती हैं, ट्रैवर्सबेल नहीं।
एक Traversable
सार विधि है foreach
:। जब आप कॉल करते हैं foreach
, तो संग्रह पारित फ़ंक्शन को सभी तत्वों को खिलाएगा, एक के बाद एक।
दूसरी ओर, एक Iterable
सार पद्धति है iterator
, जो एक रिटर्न देता है Iterator
। आप कॉल कर सकते हैं next
एक पर Iterator
अपने चयन के समय में अगले तत्व प्राप्त करने के लिए। जब तक आप ऐसा नहीं करते, तब तक इस बात का ध्यान रखना होगा कि यह संग्रह में कहाँ था, और आगे क्या है।
Iterable
विस्तार करता है Traversable
, इसलिए मुझे लगता है कि आप का मतलब है Traversable
कि Iterable
एस नहीं हैं ।
Traversable
इंटरफ़ेस का अनुपालन करने के लिए राज्य को रखने की आवश्यकता नहीं होती है, जबकि Iterator
इंटरफ़ेस का अनुपालन होता है।
Traversable
s जो Iterable
किसी पुनरावृत्ति स्थिति को नहीं रखते हैं। यह Iterator
बनाया गया है और Iterable
राज्य द्वारा लौटाया गया है ।
इसे उड़ाने और चूसने के बीच के अंतर के रूप में सोचें।
जब आपके पास एक Traversable
एस foreach
, या इसके व्युत्पन्न तरीके होते हैं, तो यह एक बार में आपके मूल्यों को अपने फ़ंक्शन में उड़ा देगा - इसलिए इसका नियंत्रण पर नियंत्रण है।
हालांकि Iterator
एक लौटे के साथ Iterable
, आप इसके मूल्यों को चूसते हैं, नियंत्रित करते हैं कि अगले एक को कब स्थानांतरित किया जाए।
tl; dr Iterables
हैं Traversables
जो स्टेटफुल प्रोड्यूस कर सकते हैंIterators
सबसे पहले, पता है कि Iterable
की उप-सीमा है Traversable
।
दूसरा,
Traversable
foreach
विधि को लागू करने की आवश्यकता होती है , जो हर चीज द्वारा उपयोग की जाती है।
Iterable
iterator
विधि को लागू करने की आवश्यकता होती है , जो हर चीज द्वारा उपयोग की जाती है।
उदाहरण के लिए, एक संतोषजनक तत्व पाए जाने find
के बाद Traversable
उपयोग के लिए का उपयोग foreach
(एक समझ के लिए) और BreakControl
इसके अपवाद को रोक देता है।
trait TravserableLike {
def find(p: A => Boolean): Option[A] = {
var result: Option[A] = None
breakable {
for (x <- this)
if (p(x)) { result = Some(x); break }
}
result
}
}
इसके विपरीत, Iterable
घटाव इस कार्यान्वयन को ओवरराइड करता है और कॉल find
करता है Iterator
, जो कि तत्व मिलने पर बस पुनरावृति को रोकता है:
trait Iterable {
override /*TraversableLike*/ def find(p: A => Boolean): Option[A] =
iterator.find(p)
}
trait Iterator {
def find(p: A => Boolean): Option[A] = {
var res: Option[A] = None
while (res.isEmpty && hasNext) {
val e = next()
if (p(e)) res = Some(e)
}
res
}
}
यह अच्छा होगा Traversable
कि पुनरावृत्ति के लिए अपवाद न फेंके , लेकिन यह केवल आंशिक रूप से पुनरावृति का एकमात्र तरीका है जब बस का उपयोग किया जाए foreach
।
एक दृष्टिकोण से, Iterable
अधिक मांग / शक्तिशाली विशेषता है, जैसा कि आप आसानी से foreach
उपयोग करके लागू कर सकते हैं iterator
, लेकिन आप वास्तव में iterator
उपयोग करके लागू नहीं कर सकते हैं foreach
।
सारांश में, Iterable
एक स्टेटफुल के माध्यम से इसे रोकने, फिर से शुरू करने या पुनरावृत्ति को रोकने का एक तरीका प्रदान करता है Iterator
। इसके साथ Traversable
, यह सब या कुछ भी नहीं है (प्रवाह नियंत्रण के लिए अपवाद हैं)।
अधिकांश समय यह मायने नहीं रखता है, और आप अधिक सामान्य इंटरफ़ेस चाहते हैं। लेकिन अगर आपको कभी भी पुनरावृत्ति पर अधिक अनुकूलित नियंत्रण की आवश्यकता है, तो आपको एक की आवश्यकता होगी Iterator
, जिसे आप एक से पुनः प्राप्त कर सकते हैं Iterable
।
डैनियल का जवाब अच्छा लगता है। मुझे देखने दीजिए कि क्या मैं इसे अपने शब्दों में रख सकता हूं।
तो एक Iterable आपको एक पुनरावृत्ति दे सकता है, जिससे आप तत्वों को एक समय में (अगले () का उपयोग करके) पार कर सकते हैं, और रुकें और अपनी इच्छानुसार जाएँ। ऐसा करने के लिए कि पुनरावृत्त को तत्व की स्थिति में एक आंतरिक "पॉइंटर" रखने की आवश्यकता है। लेकिन एक ट्रैवर्सेबल आपको बिना रोक-टोक के एक बार में सभी तत्वों को ट्रेस करने के लिए विधि, फ़ॉरचेक देता है।
रेंज (1, 10) जैसी कुछ चीज़ों को ट्रैवर्सेबल के रूप में केवल 2 पूर्णांक होने की आवश्यकता है। लेकिन रेंज (1, 10) Iterable के रूप में आपको एक पुनरावृत्ति देता है जिसे राज्य के लिए 3 पूर्णांक का उपयोग करने की आवश्यकता होती है, जिनमें से एक सूचकांक है।
यह मानते हुए कि ट्रैवर्सेबल भी फोल्डेफ्ट, फोल्डराइट प्रदान करता है, इसके फोरचेक को एक ज्ञात और निश्चित क्रम में तत्वों को पीछे हटाना होगा। इसलिए ट्रैवर्सेबल के लिए पुनरावृति लागू करना संभव है। जैसे डिफ इटेरेटर = लिस्ट.इटरेटर
Traversable
में अधिक नहीं है (इसे २.१४ तक अभी भी एक अलग उर्फ के रूप में रखा गया है )Iterable