2015-01-14 9 views
26

का कार्यान्वयन मुझे विश्वविद्यालय के लिए हास्केल सीखना है और इसके लिए मैं शुरुआत के लिए learnyouahaskell.com का उपयोग कर रहा हूं।
मैंने हमेशा अनिवार्य भाषाओं का उपयोग किया, इसलिए मैंने अन्य भाषाओं के लिए बहुत अधिक कोडिंग करके हास्केल का अभ्यास करने का फैसला किया।
मैं सूचियों के साथ काम करने के लिए इस तरह के head, tail, init के रूप में, ...
कुछ बिंदु मैं इन कार्यों के कार्यान्वयन ऊपर देखा मेरा तुलना करने के लिए पर कई कार्यों को लागू करने शुरू कर दिया और मैं अशक्त समारोह List.lhs में परिभाषित पर ठोकर खाई ।शून्य कार्य

अशक्त के कार्यान्वयन:

-- | Test whether a list is empty. 
null     :: [a] -> Bool 
null []     = True 
null (_:_)    = False 

मेरी कार्यान्वयन:

mNull :: [a] -> Bool 
mNull []  = True 
mNull _   = False 

मुझे पता भी आसान सवालों :)
के लिए कोई बेवकूफ सवाल वहाँ तो मेरे सवाल क्यों मूल कार्यान्वयन का उपयोग करता है है सिर्फ _ के बजाय?
(_:_) का उपयोग करने में कोई फायदा है या क्या कोई बढ़िया मामला है जिसे मैं नहीं जानता?
मैं वास्तव में किसी भी लाभ की कल्पना नहीं कर सकता क्योंकि _ सब कुछ पकड़ता है।

+4

वे वास्तव में बराबर हैं, मुझे यह मूर्खतापूर्ण भी लगता है। मेरा अनुमान है कि लेखक स्पष्ट होना चाहता था। – MasterMastic

उत्तर

39

तुम बस खंड के चारों ओर अपने समाधान के साथ चालू नहीं कर सकता आप एक खाली सूची पास करते हैं। चूंकि रनटाइम कभी भी [] खंड पर विचार नहीं करता है, यह तुरंत _ किसी भी चीज़ से मेल खाता है। , (GHC इस तरह के एक अतिव्यापी पैटर्न के बारे में चेतावनी देगा।)

दूसरी ओर,

null' :: [a] -> Bool 
null' (_:_) = False 
null' [] = True 

अभी भी सही ढंग से काम करता है क्योंकि (_:_) एक खाली सूची के विशेष मामले मिलान करने के लिए विफल रहता है।

यह वास्तव में दो स्पष्ट खंडों को एक लाभ नहीं देता है। हालांकि, अधिक जटिल कोड में, सभी पारस्परिक रूप से बहिष्कृत विकल्पों को लिखना एक लाभ है: यदि आप एक विकल्प भूल गए हैं, तो संकलक आपको इसके बारे में भी चेतावनी दे सकता है! जबकि _ किसी भी मामले को पिछले क्लॉज द्वारा निपटाया नहीं जा सकता है, भले ही वह वास्तव में सही न हो।

+0

क्या किसी को पता है कि यह पोस्ट इतनी बेतुका लोकप्रिय क्यों है? – leftaroundabout

6

क्योंकि _ का शाब्दिक अर्थ स्पष्ट रूप से निर्दिष्ट पैटर्न से अलग है। जब आप (_:_) निर्दिष्ट करते हैं तो इसका अर्थ यह है कि किसी भी सूची में कम से कम 1 तत्व वाली सूची के रूप में प्रतिनिधित्व किया जा सकता है, इस बात से परेशान किए बिना कि वास्तव में सूची में कितने तत्व हैं या नहीं। चूंकि खाली सूची के लिए एक स्पष्ट पैटर्न के मामले में पहले से मौजूद है, (_:_) को _ द्वारा प्रतिस्थापित किया जा सकता है।

हालांकि, इसे (_:_) के रूप में प्रतिनिधित्व करने से आपको खाली सूची पैटर्न को स्पष्ट रूप से पास करने की सुविधा भी मिलती है। वास्तव में, यह काम करेगा:

mNull' :: [a] -> Bool 
mNull' _ = False 
mNull' [] = True 

इस हमेशा उपज False, भले ही:

-- | Test whether a list is empty. 
null     :: [a] -> Bool  
null (_:_)    = False 
null _     = True 

Demo

4

मैं जो बाएंअराउंडबाउट कहता हूं उस पर जोड़ दूंगा। यह सूची प्रकार के लिए वास्तव में एक संभावित चिंता नहीं है, लेकिन सामान्य रूप से, डेटा प्रकार कभी-कभी संशोधित होते हैं। यदि आपके पास एक बीमार कल्पना

data FavoriteFood = Pizza 
        | SesameSpinachPancake 
        | ChanaMasala 

और बाद में आप DrunkenNoodles पसंद है और सूची में जोड़ने के लिए, अपने सभी कार्यों को उस प्रकार पर पैटर्न मैच का विस्तार करने की आवश्यकता होगी के लिए सीखने। यदि आपने _ पैटर्न का उपयोग किया है, तो आपको उन्हें मैन्युअल रूप से ढूंढना होगा; कंपाइलर आपकी मदद नहीं कर सकता है। यदि आपने प्रत्येक चीज़ को स्पष्ट रूप से मेल किया है, तो आप -fwarn-incomplete-patterns चालू कर सकते हैं और जीएचसी आपको हर जगह के बारे में बताएगा।

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