如何在LINQ中实现这一目标?

时间:2009-06-02 21:54:59

标签: c# linq

我想重写一下,也许使用谓词或Lambda,我该怎么做?

        serviceResponse = client.Authorize(....);


        string authorizeResponse = string.Empty;

        foreach (CdcEntry element in serviceResponse.Cdc)
        {
            authorizeResponse += element.Name + Environment.NewLine;
            foreach (CdcEntryItem item in element.Items)
            {
                authorizeResponse += " (" + item.Key + ", " + item.Value + ") " 
                + Environment.NewLine;
            }
        } 

由于

6 个答案:

答案 0 :(得分:5)

我认为在这里使用LINQ没有任何意义,因为您正在尝试构建响应字符串,因此执行最适合命令式而非函数式编程的任务。 (你当然可以在字符串上使用Aggregate方法,但这实际上并没有任何帮助。)

此外,StringBuilder类型更适合此类工作。 (在我看来,效率更高,也更清晰。当然,根据具体情况,前者可能并不重要。)

在我看来,这是执行此操作的最佳方式:

serviceResponse = client.Authorize(....);

var sb = new StringBuilder();

foreach (CdcEntry element in serviceResponse.Cdc)
{
    sb.AppendLine(element.Name);
    foreach (CdcEntryItem item in element.Items)
    {
        sb.AppendFormat(" ({0}, {1}) ", item.Key, item.Value);
        sb.AppendLine();
    }
}

var authorizeResponse = sb.ToString();

答案 1 :(得分:0)

你当然可以,但你所能得到的只是一些ForEach方法调用和多语句lambda,其中(在我看来)的可读性会大大降低。

在不知道标识符的数据类型(特别是serviceResponse.Cdcelement.Items)的情况下,您甚至可能必须推出自己的ForEach扩展方法,以使其发挥作用。

我认为你拥有的东西比LINQ等同,但如果你真的想要LINQify,请发布更多关于你发布的代码的信息,我们可以提供更多帮助。

答案 2 :(得分:0)

这应该粗略地做到:

x = x.Aggregate("",
    (cdc, s) => s + string.Format("{0}{1}",
                    cdc.Name, Environment.NewLine) +

        cdc.Aggregate("",
           (item, s) => s + string.Format(" ({0}, {1}) {2}",
                            item.Key, item.Value, Environment.NewLine)));
坦率地说,我是一个很有实力的人,但是多个嵌套的折叠让我觉得这样的简单问题太难了,尤其是C#的冗长语法。我甚至不会用这个。我会使用您的foreach版本。

答案 3 :(得分:0)

使用字符串生成器而不是字符串连接可以获得很多收益。不要在LINQification中看到任何性能优势。

 StringBuilder sb = new StringBuilder()

 foreach (CdcEntry element in serviceResponse.Cdc)
 {
     sb.AppendLine(element.Name);
     foreach (CdcEntryItem item in element.Items)
     {
        sb.AppendLine(" ({0},{1}) ", item.Key, item.Value);
      }
 }

答案 4 :(得分:0)

您当然可以使用LINQ折叠列表。但是你应该记住,像LINQ这样的语言功能可以使事情更简单,更清晰。我不确定下面的逻辑是:

StringBuilder sb = new StringBuilder();
string authorizeResponse = serviceResponse.Aggregate( sb, 
                              (q,x) => q.Append( string.Format( "{0}{1}{2}", x.Name, Environment.NewLine,
                              x.Aggregate( q, (y,z) => y.Append( string.Format("({0}){1}", z.Key, Environment.NewLine) ) ) );

string authorizeResponse = sb.ToString();

答案 5 :(得分:0)

        var result =
                elements.Select(
                        element =>
                        new[] {element.Name}.Concat(
                                element.Items.Select(item => "({0},{1})".With(item.Key, item.Value)))).SelectMany(
                        item => item).Join(Environment.NewLine);