2011-03-03 17 views
6

के लिए तीर की गणना और फ़िल्टरिंग मैं एक एक्सएमएल पार्स करने की कोशिश कर रहा हूं, लेकिन मैं किसी दिए गए नोड से केवल बच्चों की एक निश्चित संख्या को फ़िल्टर और निकालना चाहता हूं। उदाहरण के लिए:एचएफटी

<root> 
    <node id="a" /> 
    <node id="b" /> 
    <node id="c" /> 
    <node id="d" /> 
</root> 

और फिर अगर मैं तीर getChildren >>> myFilter 2 निष्पादित, मैं वापस आईडी के साथ ही नोड्स "एक" और "बी" मिलेगा।

अंतर्ज्ञान देता है कि मुझे ट्रैक रखने के लिए एक राज्य तीर का उपयोग करना चाहिए, लेकिन मुझे नहीं पता कि यह कैसे करना है।

मैंने इसे स्वयं करने की कोशिश की लेकिन यह वही नहीं है जो मैं चाहता हूं, बहुत सुंदर दिखता नहीं है, और काम नहीं करता है। मैं एक XmlTree वापस जाने के लिए की जरूरत है

takeOnly :: IOSLA Int XmlTree XmlTree 
takeOnly = changeState (\s b -> s-1) 
      >>> accessState (\s b -> if s >= 0 then b else Nothing) 

लेकिन निश्चित रूप से मैं Nothing वापस नहीं लौट सकते,: मैं runSLA और प्रारंभिक अवस्था के रूप में एक पूर्णांक पैरामीटर के साथ तीर की मेरी श्रृंखला चलाने का प्रयास है, और फिर परिभाषित करने। लेकिन मैं कुछ भी वापस नहीं करना चाहता!

शायद वहां एक बेहतर तरीका है। क्या आप मेरी मदद कर सकते हैं?

आपके समय और सहायता के लिए धन्यवाद!

उत्तर

4

यह इस तरह की चीज़ को संभालने के लिए Control.Arrow.ArrowList में संयोजकों का उपयोग करने के लिए शायद अधिक मूर्खतापूर्ण होगा।

पैकेज विशेष रूप से (>>.) :: a b c -> ([c] -> [d]) -> a b d प्रदान करता है, जो "एक सूची तीर के परिणाम को किसी अन्य सूची में परिवर्तित करने के लिए संयोजक" है। यह हमें take फ़ंक्शन का उपयोग करने की अनुमति देता है जो हमारे पास पहले से ही इस संदर्भ में सूचियों के लिए है।

module Main where 

import Text.XML.HXT.Arrow 

takeOnly :: (ArrowXml a) => Int -> a XmlTree XmlTree 
takeOnly n = getChildren >>. take n 

main = do 
    let xml = "<root><node id='a' /><node id='b' />\ 
        \<node id='c' /><node id='d' /></root>" 

    print =<< runX (readString [] xml >>> getChildren >>> takeOnly 2) 

यह मेरा मानना ​​है कि लगभग क्या आप देख रहे हैं करता है:

[email protected]% ./ArrowTake 
[NTree (XTag (LP node) [NTree (XAttr (LP id)) [NTree (XText "a") []]]) [], 
NTree (XTag (LP node) [NTree (XAttr (LP id)) [NTree (XText "b") []]]) []] 

नहीं IOSLA आवश्यक

यहाँ कैसे आप इसका इस्तेमाल हो सकता है की एक त्वरित संस्करण है। ध्यान दें कि मैंने फ़ंक्शन प्रकार को थोड़ा भी बदल दिया है- यह संस्करण मेरे लिए अच्छा लगता है, लेकिन आप आसानी से इसे अपने संस्करण में टाइप की तरह कुछ और रूपांतरित कर सकते हैं।

+0

वाह! यही वही है जो मैं ढूंढ रहा था, धन्यवाद! जैसा कि यह स्पष्ट है कि मैं तीर के लिए बहुत नया हूं ... लेकिन मैं उन्हें प्यार करता हूं, अब और भी ^^ –