首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >这是Recursion + Linq示例效率低下吗?

这是Recursion + Linq示例效率低下吗?
EN

Code Review用户
提问于 2011-02-24 10:04:59
回答 2查看 2.3K关注 0票数 5

我有一个组的层次结构,我想得到所有最低级别组的集合(或者如果我们把它看作树)。

我写了以下代码。是低效的吗?

代码语言:javascript
运行
复制
public static class FeatureWeightGroupExtensions
{
    public static IEnumerable<IFeatureWeightGroup> GetLeafGroups(this IFeatureWeightGroup featureWeightGroup)
    {
        return GetLeafGroupsRecursive(featureWeightGroup).ToList();
    }

    private static IEnumerable<IFeatureWeightGroup> GetLeafGroupsRecursive(IFeatureWeightGroup featureWeightGroup)
    {
        if (!featureWeightGroup.ChildGroups.Any())
            return Enumerable.Repeat(featureWeightGroup, 1);

        return featureWeightGroup.ChildGroups.Aggregate(Enumerable.Empty<IFeatureWeightGroup>(),
                                                        (allGroups, group) =>
                                                        allGroups.Concat(GetLeafGroupsRecursive(group)));
    }
}                      
EN

回答 2

Code Review用户

回答已采纳

发布于 2011-02-24 13:14:40

代码语言:javascript
运行
复制
return featureWeightGroup.ChildGroups.Aggregate(Enumerable.Empty<IFeatureWeightGroup>(),
                                                    (allGroups, group) =>
                                                    allGroups.Concat(GetLeafGroupsRecursive(group)));

它看起来可以用以下方式替换:

代码语言:javascript
运行
复制
return featureWeightGroup.ChildGroups
           .SelectMany(g => GetLeafGroupsRecursive(group));

从性能的角度来看,这可能不会更好,但看起来更干净。

票数 5
EN

Code Review用户

发布于 2011-02-24 15:42:37

正如斯诺贝尔斯和我对他的回答的评论所指出的,使用SelectMany而不是Concat可以提高性能和可读性。

不过,我注意到您在最后使用的是ToList()。这让人怀疑使用LINQ和所有这些SelectMany迭代器的好处。使用LINQ牺牲性能有利于懒惰评估,但您没有使用延迟评估方面。因此,如果性能是您所追求的,那么就不要那么多地使用LINQ:

代码语言:javascript
运行
复制
public static class FeatureWeightGroupExtensions
{
    public static IEnumerable<IFeatureWeightGroup> GetLeafGroups(this IFeatureWeightGroup featureWeightGroup)
    {
        var list = new List<IFeatureWeightGroup>();
        populateList(list, featureWeightGroup);
        return list;
    }

    private static void populateList(List<IFeatureWeightGroup> list, IFeatureWeightGroup featureWeightGroup)
    {
        if (!featureWeightGroup.ChildGroups.Any())
            list.Add(featureWeightGroup);
        else
            foreach (var childGroup in featureWeightGroup.ChildGroups)
                populateList(list, childGroup);
    }
}

这是我所能想到的最优化的性能方法,同时也比原始的或SelectMany的替代方案更容易阅读。

票数 5
EN
页面原文内容由Code Review提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://codereview.stackexchange.com/questions/966

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档