2012-02-03 40 views
9

में उपज रिटर्न तत्वों के आदेश के साथ रिकर्सन मेरे पास एक रिकर्सिव फ़ंक्शन है जो प्रारंभिक रूट नोड को देखते हुए सभी सबट्री नोड्स देता है।पेड़

private IEnumerable<Node> getAllNodesRecursively(Node subnode) 
{ 
    foreach (Node node in subnode.Nodes) 
     getAllNodesRecursively(node); 

    yield return subnode; 
} 

निम्नलिखित वृक्ष संरचना के लिए:

A 
| 
+--B 
| 
+--C 
| | 
| +--D 
| 
+--E 

जब मैं इस तरह के रूप पुनरावृति करने की कोशिश:

foreach (Node n in getAllNodesRecursively(a)) 
{ 
    Console.WriteLine(n); 
} 

फ़ंक्शन केवल मान।

मैं रिकर्सन के साथ उपज-वापसी का उपयोग करना चाहता हूं और इस उदाहरण में प्रीऑर्डर (ए, बी, सी, डी, ई) में तत्वों को पुनर्प्राप्त करना चाहता हूं।

(यदि मैं foreach से पहले उपज वापसी डालता हूं, तो foreach कभी नहीं होगा)।

क्या यह संभव है?

+0

क्या आपने कोशिश की है कि यदि आप उपज रिटर्न सामने डालते हैं तो foreach नहीं कहा जाता है? मुझे लगता है कि इसे बुलाया जाएगा। – okrumnow

+0

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

उत्तर

16

आप की तरह कुछ कोशिश की है।

+0

यह काम करता है, लेकिन मुझे फिर से फिर से क्यों करना है (आंतरिक foreach)? इटेटरेटर विधि पुनरावृत्ति की अनुमति क्यों नहीं देती है? मैंने डीबगर के साथ प्रयास किया है और यह केवल मेरे पुनरावर्ती कॉल को छोड़ देता है जब तक कि इसे पुनरावृत्ति में उपयोग नहीं किया जाता है (जैसे foreach)। ऐसा क्यों है? –

+0

@ क्रिस्टियन हैटर "क्या वह दो बार शीर्ष नोड को छोड़कर वापस नहीं करेगा?" सं। – Joe

+1

जो का उदाहरण थोड़ा सा सरल हो सकता है: निजी आईनेमेरेबल getAllNodesRecursively (नोड रूट) { उपज वापसी रूट; foreach (रूट में var child.Nodes.SelectMany (getAllNodesRecursively)) { उपज वापसी बच्चे; } } – peter70

3

हां यह संभव है, से पहले yield return डालें। आप सामान्य return कथन के व्यवहार के बारे में सोच रहे हैं।

private IEnumerable<Node> getAllNodesRecursively(Node subnode) 
{ 
    // Return the parent before its children 
    yield return subnode; 

    foreach (Node node in subnode.Nodes) 
    { 
     foreach(Node n in getAllNodesRecursively(node)) 
     { 
      yield return n; 
     } 
    } 
} 

आपका क्रियान्वयन getAllNodesRecursively रिकर्सिवली बुला रहा है, लेकिन इसकी वापसी मान अनदेखी:

+0

मैंने अपनी पोस्ट संशोधित की है, क्योंकि मैं दिखाया गया था कि क्या गलत होगा। केवल पहला तत्व लौटाया जाता है। अगर मैं foreach से पहले उपज वापसी डालता हूं, वही बात होती है। कैसे? –

+0

हम्म। मैं अभी खुद को आजमाने की स्थिति में नहीं हूं। क्या आपने डीबगर के साथ कोड के माध्यम से कदम उठाने की कोशिश की है? –

+0

डीबगर बस रिकर्सिव कॉल छोड़ देता है। यह एक दिलचस्प है। –

1
 public IEnumerable<int> preOrder(Node root) 
     { 
      if (root == null) 
       yield break; 

      yield return root.val; 

      if (root.left != null) 
       foreach (int i in preOrder(root.left)) 
        yield return i; 

      if (root.right != null) 
       foreach (int i in preOrder(root.right)) 
        yield return i; 
     } 
+0

जबकि यह कोड स्निपेट प्रश्न हल कर सकता है, [एक स्पष्टीकरण सहित] (http://meta.stackexchange.com/questions/114762/explaining-entirely-code-based-answers) वास्तव में गुणवत्ता में सुधार करने में मदद करता है आपकी पोस्ट का याद रखें कि आप भविष्य में पाठकों के लिए प्रश्न का उत्तर दे रहे हैं, और वे लोग आपके कोड सुझाव के कारणों को नहीं जानते हैं। – lokusking

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

  • कोई संबंधित समस्या नहीं^_^