StringBuilder真的比Aggregate快吗?

时间:2011-03-29 13:44:24

标签: c# string

        string c = tmpArr[0].Aggregate(string.Empty, (current, m) => current + (m.Name + " "));

        StringBuilder sb = new StringBuilder();

        foreach (Mobile m in tmpArr[0])
            sb.Append(m.Name + " ");

        sb.ToString();

这两个中哪一个更快?聚合肯定是更清洁,但它是快速还是与做

相同
foreach(Mobile m in tmpArr[0])
    c += m.Name + " ";

我真正想要的是像string.Join(",",tmpArr[0])这样的东西,但是我不希望它连接他们的ToString值,只是他们的名字,我怎么能做到最好?

我没有使用string.Join的问题是我实际上必须做这样的事情:

        string separator = "";
        StringBuilder sb = new StringBuilder();

        foreach (Mobile m in tmpArr[0])
        {
            separator = ", ";
            sb.Append(separator + m.Name);
        }

6 个答案:

答案 0 :(得分:12)

如果在循环(c += m.Name + " ";)中追加字符串,则会导致创建大量中间字符串;这会导致“伸缩”内存使用,并给GC带来额外负担。 Aggregate与StringBuilder的fluent-API混合在一起可以提供帮助 - 但是与StringBuilder循环一样。重要的不是聚合: 没有创建大量的中间字符串

例如,我会使用:

foreach (Mobile m in tmpArr[0])
        sb.Append(m.Name).Append(" ");

更少; p

对于在Aggregate中使用StringBuilder的类似示例:

string c = tmpArr[0].Aggregate(new StringBuilder(),
    (current, m) => current.Append(m.Name).Append(" ")).ToString();

答案 1 :(得分:10)

  

我不希望它连接他们的ToString值,只是他们的名字,我怎么能做到最好?

string.Join(",",tmpArr[0].Select(t => t.Name).ToArray())

但大部分时间It. Just. Doesn't. Matter!

答案 2 :(得分:1)

Aggregate本身不是问题。问题是你在循环中连接字符串。当您使用+运算符连接两个字符串时,必须在内存中分配一个新位置,并将两个字符串复制到其中。因此,如果您使用+五次,则实际上会创建五个新字符串。这就是为什么你应该使用StringBuilderJoin来避免这种情况。

如果您想使用Join和linq以获得更好的可读性,您仍然可以,只是不要使用Aggregate,而是使用SelectToArray。< / p>

答案 3 :(得分:1)

由于字符串是不可变的,因此添加操作具有性能成本。这是StringBuilder主要设计的内容,它的作用类似于“Mutable”String。我没有对速度进行过多的基准测试,但对于内存优化,StringBuilder肯定更好。

答案 4 :(得分:1)

Aggregate针对IEnumerable中的每个项目运行匿名方法。此方法传递给系统定义的Func<>委托,该委托返回out参数。

它基本上就像运行一个多次执行追加的函数。

因此,对于方法调用等,堆栈上的分配/解除分配肯定比运行简单的for / foreach循环具有更多的开销

所以,在我看来,第二种方法会更快。

答案 5 :(得分:1)

这样的东西?

string joined = string.Join(",", myItems.Select(x => x.Name).ToArray());