2010-06-15 2 views
7

मैं एक साधारण पुनरावर्ती क्रिया उस सूची पर नज़र लिख सकते हैं और पूर्णांक की एक जोड़ी वापस जाने के लिए कोशिश कर रहा हूँ। यह C/C++/जावा में लिखने के लिए आसान है, लेकिन मैं संघर्ष टाइप करने के लिएocaml पैटर्न मैच सवाल

यह होना चाहिए की तरह हो जाता है कारण समाधान पता लगाने के लिए OCaml ताकि किसी भी तरह कठिन नया हूँ ..

let rec test p l = ... ;; 
val separate : (’a -> bool) -> ’a list -> int * int = <fun> 
test (fun x -> x mod 2 = 0) [-3; 5; 2; -6];; 
- : int * int = (2, 2) 

तो समस्या मैं कैसे रिकर्सिवली टपल पर मूल्य लौट सकते हैं .. है

+2

तुम क्या इस समारोह वापस जाने के लिए माना जाता है के रूप में कुछ और विस्तार प्रदान कर सकता है? पूर्णांक की जोड़ी का प्रतिनिधित्व क्या होता है? – goggin13

+0

तो यह (एक्स, वाई) के रूप में पूर्णांक की एक जोड़ी जो ocaml में टपल है कि केवल समस्या यह है कि मैं सामना करना पड़ा है टपल गणना .. है इसलिए इसकी तरह, अगर सूची का एक तत्व तो कम तो कुछ संख्या है (एक्स लौटना चाहिए +1, वाई) और (एक्स, वाई +1) तो वापसी मान हो जाएगा (एक्स, वाई) जहां एक्स है कि कुछ संख्या और y से अधिक है तत्वों की संख्या है – REALFREE

उत्तर

4

थोड़ा के लिए OCaml से दूर किया गया है, लेकिन मुझे लगता है कि आप नेस्टेड मैच बयानों का इस्तेमाल किया करने के लिए टपल के टुकड़े बाहर निकलने के लिए कर सकते हैं इस टिप्पणी

let rec test l = 
    match l with 
     [] -> (0,0) 
    | x::xs -> 
     if x > 0 then match (test xs) with (x,y) -> (x+1, y) 
     else match (test xs) with (x,y) -> (x, y+1);; 

में REALFREE के विवरण के संबंध में चाल करना होगा संशोधित

संपादित करें: मैं वाक्य रचना पास्कल Cuoq नीचे उसकी टिप्पणी में उल्लेख किया है के बारे में पता नहीं था, यहां ऐसे ही कोड है, यह neater है और एक छोटे से कम:

let rec test l = 
    match l with 
     [] -> (0,0) 
    | x::xs -> 
    if x > 0 then let (x,y) = test xs in (x+1, y) 
    else let (x,y) = test xs in (x, y+1);; 

लेकिन स्वीकार्य उत्तर अभी भी बेहतर है, खासकर पूंछ रिकर्सन के साथ;)।

+2

और यदि आप एक ही पैटर्न के साथ 'मिलान .. के साथ ..' लिख रहे हैं, तो आप इसके बजाय 'let' का उपयोग कर सकते हैं: 'x, y = test xs में ...' –

5

एक समस्या यह है कि यहाँ आप दो अलग अलग प्रकार लौट रहे है: एक खाली सूची के लिए एक पूर्णांक है, या एक टपल अन्यथा। यह एक या दूसरे होना चाहिए।

एक और समस्या यह है कि आप 1 से test जोड़ने की कोशिश कर रहे हैं, लेकिन test एक कार्य है, मूल्य नहीं। किसी मूल्य को वापस करने के लिए आपको किसी अन्य चीज़ पर परीक्षण करने की आवश्यकता है, लेकिन तब भी इसे एक ट्यूपल वापस करना होगा, जिसे आप पूर्णांक में नहीं जोड़ सकते हैं।

मैं यह पता लगाने नहीं कर सकते कि आप क्या करना चाहते हैं कोड, लेकिन अगर आप उस जानकारी के साथ अपने प्रश्न अपडेट मैं और अधिक कर सकते हैं।

let rec test l = 
    match l with [] -> 0 
    | x::xs -> if x > 0 then 1 + (test xs) 
       else test xs;; 

अद्यतन:

एक अनुमान मेरे पास है कि आप सूची में सकारात्मक संख्या, जिस स्थिति में आप इसे इस प्रकार लिख सकते गणना करना चाहते हैं, क्योंकि आप स्पष्ट करने के लिए संपादित किया है समस्या, उपरोक्त कोड को निम्नानुसार संशोधित करें:

let test l = 
    let rec test_helper l pos nonpos = 
    match l with [] -> (pos, nonpos) 
    | x::xs -> if x > 0 then test_helper xs 1+pos, nonpos 
       else test_helper xs pos 1+nonpos 
    in test_helper l 0 0;; 

संचयकों का उपयोग इस मामले में बहुत मदद करता है। यह फ़ंक्शन पूंछ-रिकर्सिव बनाता है जो हमेशा अच्छा अभ्यास होता है।

+0

से कम मैं कैसे पुनरावर्ती अग्रेषित करने के लिए इसे संशोधित कर सकते हैं ? – REALFREE