为什么一个具有收益率的函数不能递归?

时间:2013-04-28 05:07:34

标签: c# recursion yield-return

我有一段像这样的代码

class Program
{
    static IEnumerable<string> GetSequences(string a)
    {
        yield return a;
        GetSequences(a + ">");
    }

    static void Main(string[] args)
    {
        foreach (var n in GetSequences(">"))
            Console.Write(n + ",");
    }
}

我期待像这样的输出

  

,&GT;&GT;,&GT;&GT;&GT;

但事实并非如此。它只打印“&gt;,”。有谁知道我错过了什么?

2 个答案:

答案 0 :(得分:7)

在功能本身中使用相同的foreach:

static IEnumerable<string> GetSequences(string a)
{
    yield return a;
    foreach (var n in GetSequences(a + ">"))
        yield return n;
}

并且不要忘记退出递归。

答案 1 :(得分:3)

foreach循环仅适用于yield return,并且在GetSequences()方法中没有GetSequences()命令的yield return;无论它返回什么都不会被存储或返回。就像你这样做: 这就像你这样做:

static IEnumerable<string> GetSequences(string a)
{
    GetSequences(a + ">");
}

当然没有return语句(它不会编译,但你知道)。 在玩了一会儿之后,如果你想使用递归,我建议你不要使用枚举,特别是因为循环和递归意味着服务于单独的目的,而使用IEnumerable的foreach最适用于具有枚举的集合已被列举。上面建议的循环,只是启用无限递归,并实现递归的转义,如下所示:

    static IEnumerable<string> GetSequences(string a)
    {
        if(a.Length > 100)
            yield return a;
        else
            foreach (var n in GetSequences(a + ">"))
                yield return n;            
    }

产生此输出: >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>,(也许是为了扩展,我不想算数) 通过像这样实现它,我能够得到你想要的输出:

    static string GetSequences(string a, int len)
    {
        if (a.Length < len)
        {
             return GetSequences(a + ">", len);
        }
        else
            return a;
    }

    static void Main(string[] args)
    {

        for (int i = 1; i < 5; i++)
        {
            Console.Write(GetSequences(">", i) + ",");
        }
        Console.Read();
    }

当然,我的整数是任意的,它可以任意长度。

编辑:我知道有一种方法可以像abatishchev所说的那样去做,但我无法理解。在绞尽脑汁之后,我得到的是:

    static IEnumerable<string> GetSequences(string a)
    {
        if (a.Length < 100)
        {
            yield return a;
            foreach (var n in GetSequences(a + ">"))
                yield return n;
        }else
            yield break;
    }

这有你想要的输出,虽然我仍然认为使用带循环的递归有点搞笑。