2013-07-08 7 views
8

मैं शोध कर रहा हूं कि जीएचसी में कितना शक्तिशाली कार्य ओवरलोडिंग है। मैं निम्नलिखित कोड लिखा है:हास्केल में इस प्रकार की टिप्पणी क्यों आवश्यक है?

class F_third_arg a where 
    run_f :: (Integer, a) -> Integer 

instance F_third_arg Integer where 
    run_f (_, x) = x 

instance F_third_arg String where 
    run_f (x, _) = x 

my_fun :: (F_third_arg a) => Integer -> (a -> Integer) 
my_fun x = \a -> run_f(x, a) 

main :: IO() 
main = putStrLn $ show(((my_fun::Integer->(Integer->Integer)) 5) $ 6) 

(हाँ, मैं -XTypeSynonymInstances -XFlexibleInstances जरूरत है) और मैं हैरान था कि संकलक my_fun करने के लिए कॉल के पास प्रकार एनोटेशन की जरूरत है। यह दो संख्याओं पर लागू होता है - इस एनोटेशन को घुसपैठ करने में समस्या क्या है? इन दो एक्सटेंशन के साथ ओवरलोडिंग के नियम क्या चालू हैं?

+0

'फ्लेक्सिबल इंस्टेंस' पहले से ही 'TypeSynonymInstances' का तात्पर्य है। 'putStrLn। शो' 'प्रिंट' के बराबर है। और आप बहुत सारे माता-पिता को छोड़ सकते हैं ... – leftaroundabout

+3

प्रकार के लिए ** डिफ़ॉल्ट ** (निश्चित रूप से संकलक प्रकार को _infer_ नहीं कर सकता: संख्यात्मक अक्षर polymorphic हैं!), मैं उस पर एक विशेषज्ञ नहीं हूँ, लेकिन जीएचसी ने डिफॉल्ट नियमों को बढ़ाया है ('{- # LANGUAGE एक्सटेंडेडडिफॉल्ट नियम # -} 'या जीएचसीआई)। एक बेहतर तरीका 'my_fun 5 प्रिंट करें (6 :: इंटीजर) '। – leftaroundabout

+0

धन्यवाद! आपकी टिप्पणियां वास्तव में सहायक हैं। –

उत्तर

7

आपके कोड के साथ समस्या यह है कि संख्या अक्षर स्वयं पहले से ही अधिभारित हैं। तो शाब्दिक 6 टाइप Num a => a है, जबकि my_fun 5 में F_third_arg b => b -> Integer टाइप है। तो प्रकार अनुमान के दौरान, यह इन दो प्रकार चर को एकीकृत करता है। लेकिन वहाँ के रूप में उनके बारे में कोई अन्य आवश्यकताओं हैं, GHC एक ठोस प्रकार यहाँ उपयोग करने के लिए नहीं मिल रहा है, और एक उचित त्रुटि संदेश देता है:

 
test.hs:16:26: 
    No instance for (F_third_arg a0) arising from a use of `my_fun' 
    The type variable `a0' is ambiguous 
    Possible fix: add a type signature that fixes these type variable(s) 
    Note: there are several potential instances: 
     instance F_third_arg String -- Defined at test.hs:9:10 
     instance F_third_arg Integer -- Defined at test.hs:6:10 
    In the expression: (my_fun 5) 
    In the first argument of `show', namely `((my_fun 5) $ 6)' 
    In the second argument of `($)', namely `show ((my_fun 5) $ 6)' 

test.hs:16:38: 
    No instance for (Num a0) arising from the literal `6' 
    The type variable `a0' is ambiguous 
    Possible fix: add a type signature that fixes these type variable(s) 
    Note: there are several potential instances: 
     instance Num Double -- Defined in `GHC.Float' 
     instance Num Float -- Defined in `GHC.Float' 
     instance Integral a => Num (GHC.Real.Ratio a) 
     -- Defined in `GHC.Real' 
     ...plus three others 
    In the second argument of `($)', namely `6' 
    In the first argument of `show', namely `((my_fun 5) $ 6)' 
    In the second argument of `($)', namely `show ((my_fun 5) $ 6)' 

एक उम्मीद कर सकते हैं संकलक देखती है कि कि Integer केवल प्रकार है कि दोनों को पूरा करता है आवश्यकताएं, लेकिन इस तरह के हेरिस्टिक आपके कोड को अपेक्षाकृत कमजोर बना देंगे, यानी यह तोड़ देगा क्योंकि आप एक नया उदाहरण जोड़ते हैं (उदाहरण के लिए F_third_arg Double)। इसलिए संकलक कोड को अस्वीकार करता है और आपको प्रश्न के प्रकार के बारे में स्पष्ट होने के लिए कहता है।

आपको इसे ठीक करने का एक तरीका मिला, लेकिन @का उपयोग करने के बाएंराउंडबाउट्स के सुझाव थोड़ा अच्छा है।

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