2012-02-08 6 views
16

मैं अनुक्रम और LazyList के बीच अंतर के चारों ओर अपने सिर को लपेट नहीं सकता। वे दोनों आलसी और संभावित अनंत हैं। जबकि seq<'T>IEnumerable<'T> है .NET फ्रेमवर्क से, LazyListF# PowerPack में शामिल है। प्रैक्टिस में, मुझे LazyList एस से अधिक बार अनुक्रमों का सामना करना पड़ता है।अनुक्रम बनाम LazyList

प्रदर्शन, उपयोग, पठनीयता आदि के संदर्भ में उनके अंतर क्या हैं? seq की तुलना में LazyList की ऐसी बुरी प्रतिष्ठा के कारण क्या हैं?

उत्तर

31

LazyList प्रत्येक तत्व को केवल एक बार गणना करता है इस पर ध्यान दिए बिना कि सूची कितनी बार चलती है। इस तरह, यह Seq.cache (एक सामान्य अनुक्रम की बजाय) से लौटा अनुक्रम के करीब है। लेकिन, कैशिंग के अलावा, LazyList बिल्कुल एक सूची की तरह व्यवहार करता है: यह हुड के नीचे एक सूची संरचना का उपयोग करता है और पैटर्न मिलान का समर्थन करता है। तो आप कह सकते हैं: seq के बजाय LazyList का उपयोग करें जब आपको सूची अर्थशास्त्र और कैशिंग (आलस्य के अलावा) की आवश्यकता होती है।

दोनों अनंत होने के संबंध में, seq की मेमोरी उपयोग स्थिर है जबकि LazyList रैखिक है।

ये docs पढ़ने योग्य हो सकता है।

+0

+1, अच्छा, मुझे कैशिंग भाग के बारे में पता नहीं था। क्या आप एक उदाहरण दे सकते हैं जिसके लिए आलस्य और सूची अर्थशास्त्र दोनों की आवश्यकता होती है? – pad

+0

एक अनुक्रम को पार करते हुए एक साथ कई तत्वों तक पहुंचने के लिए 'seq' के साथ किया जा सकता है, लेकिन यह' LazyList' + पैटर्न मिलान का उपयोग करके बहुत साफ है। – Daniel

+0

उदा। देखें http://stackoverflow.com/questions/3484315/how-to-merge-sorted-sequences-in-f और http://stackoverflow.com/questions/1306140/f-why-is-using-a-sequence- इतनी धीमी-से-उपयोग-एक-सूची-इन-उदाहरण/1306267 # 1306267 – Brian

19

डैनियल के उत्तर के अलावा, मुझे लगता है कि मुख्य व्यावहारिक अंतर यह है कि आप LazyList या seq संरचनाओं (या गणना) को कैसे संसाधित करते हैं।

  • आप LazyList कार्रवाई करने के लिए चाहते हैं, तो आप आमतौर पर एक पुनरावर्ती समारोह पैटर्न मिलान

  • आप seq कार्रवाई करने के लिए चाहते हैं, तो आप कर सकते हैं या तो उपयोग (काफी सामान्य एफ # सूचियों के प्रसंस्करण के लिए इसी तरह) का उपयोग कर लिखते थे अंतर्निहित फ़ंक्शंस या आपको अनिवार्य कोड लिखना है जो GetEnumerator पर कॉल करता है और उसके बाद एक लूप में लौटाए गए एन्यूमेरेटर का उपयोग करता है (जिसे रिकर्सिव फ़ंक्शन के रूप में लिखा जा सकता है, लेकिन यह गणनाकर्ता को बदल देगा)। तुम्हें पता है, हमेशा की तरह सिर/पूंछ शैली (Seq.tail और Seq.head का प्रयोग करके) का उपयोग नहीं कर सकते क्योंकि कि अत्यंत अक्षम है - क्योंकि seq का मूल्यांकन तत्वों नहीं रखता और Seq.head का परिणाम शुरू से ही करने के लिए फिर से पुनरावृति की जरूरत है।

seq और LazyList की प्रतिष्ठा के बारे में, मुझे लगता है कि एफ # पुस्तकालय डिजाइन एक व्यावहारिक दृष्टिकोण लेता है - के बाद से seq वास्तव में नेट IEnumerable है, यह नेट प्रोग्रामिंग के लिए काफी सुविधाजनक है (और यह भी है क्योंकि आप अच्छा है अन्य संग्रहों को seq के रूप में देख सकते हैं)। आलसी सूचियां अक्सर नहीं होती हैं और सामान्य परिस्थितियों में सामान्य F # सूची और seq पर्याप्त नहीं होती हैं।

संबंधित मुद्दे