【问题标题】:Best way to convert all strings in List<String> to a single comma separated string [duplicate]将 List<String> 中的所有字符串转换为单个逗号分隔字符串的最佳方法 [重复]
【发布时间】:2012-01-24 19:36:27
【问题描述】:

可能重复:
Most efficent way of joining strings

我有一个列表。什么是创建单个字符串的最佳方法,该字符串包含 List 中的所有字符串但用“,”分隔。

提前致谢

【问题讨论】:

    标签: c# .net string visual-studio list


    【解决方案1】:

    大概:

    var str = string.Join(",", yourList);
    

    如果您未使用 .NET Framework 4,则缺少 IEnumerable 的重载,因此您需要先将其转换为数组:

    var str = string.Join(",", yourList.ToArray()); 
    

    你可以阅读更多关于string.Joinat MSDN的信息。

    【讨论】:

    • 非常高兴他们终于在.NET 4中包含了这个重载。在此之前,唯一的选择是传入string[] ...这基本上在这个答案中进行了解释...因此我没有理由发表评论。 :)
    【解决方案2】:

    几个选项之一:

    var concat = String.Join(",", mylist.ToArray());
    

    【讨论】:

      【解决方案3】:
      public string getStringFromList(List<string> inputList){
          string returnString = "";
          if(inputList.length < 1)return returnString;
          foreach(string s in inputList){
            returnString += s + ",";
          }
          returnString = returnString.Substring(returnString.length - 2);//remove extra ","
          return returnString
      }
      

      【讨论】:

      • returnString -= "," 无效。
      • 糟糕!谢谢@vcsjones,我修复了解决方案。
      【解决方案4】:

      迭代器的乐趣!

      定义一个 Delimit 扩展方法(如下所示),你可以这样做:

      result = string.Concat(values.Delimit(","));
      

      (所有扩展方法都包含在底部的代码示例中)

      当 string.Join 在这种情况下可以正常工作时,为什么要使用 Delimit 扩展方法?

      好吧,您可以通过添加一个带有前缀和后缀参数的重载来更进一步。您可以使用它来生成 CSV 字符串,例如,如下所示:

      // replace " with ""
      var escapedValues = values.Select(x => x.Replace("\"", "\"\""));
      result = string.Concat(escapedValues.Delimit(",", "\"", "\""));
      

      更进一步,添加带有“智能”(即委托)分隔符的重载。例如,下面显示了与上面相同的 CSV 方法,但这次只有包含空格或逗号的值才会被引号括起来:

      char[] quotables = new char[] { ' ', '\t', '\r', '\n', ',' };
      var result3 = string.Concat(escapedValues.Delimit(
          (previous, current) => ",", // always separate with a comma
          // but only surround with quotes if the value contains whitespace or an embedded comma
          current => current.IndexOfAny(quotables) < 0 ? null : "\"",
          current => current.IndexOfAny(quotables) < 0 ? null : "\""));
      

      好的,所有这些前面的例子仍然可以通过现有的 Linq 方法和 string.Join 方法的某种组合来完成。以下示例演示了一些我认为无法使用这些内置方法完成的事情。

      您可以使用可变分隔符。以下示例使用“”或“=”分隔整数,具体取决于要分隔的两个值。此示例还使用了一个带有Func&lt;int, string&gt; 转换参数的重载:

      var rng = new Random();
      int[] integers = new int[100];
      for (int i = 0; i < integers.Length; i++)
          integers[i] = rng.Next(0, 100);
      
      result = string.Concat(integers.Delimit(
          (current) => current.ToString(), // convert int to string
          // separate with either "<", ">", or "="
          (previous, current) => (previous < current) ? " < " : (previous > current) ? " > " : " = ",
          // no prefix or suffix
          null,
          null));
      

      输出:9 63 70 ...

      最后,并不是说这是必须要做的事情,而是出于演示的目的,假设您有一个 Web UI 控件列表 (List&lt;System.Web.UI.Control&gt;),并且您想在之前插入一个 HTML &lt;label&gt; 控件每个 TextBox 控件:

      result = controls.Delimit(
          null, // no separator
          (current) => {
              var textbox = current as System.Web.UI.WebControls.TextBox;
              if (textbox == null)
                  return null;
              // prefix all TextBox controls with a <label> element
              var label = new System.Web.UI.HtmlControls.HtmlGenericControl("label");
              label.Attributes["for"] = textbox.ClientID;
              label.InnerText = textbox.Attributes["name"];
              return label; },
          null); // no suffix
      

      以下是上述代码示例使用的扩展方法:

      static class DelimitExtensions
      {
          public static IEnumerable<T> Delimit<T>(this IEnumerable<T> source, T separator)
          {
              using (var enumerator = source.GetEnumerator())
              {
                  if (enumerator.MoveNext())
                  {
                      yield return enumerator.Current;
      
                      while (enumerator.MoveNext())
                      {
                          yield return separator;
      
                          yield return enumerator.Current;
                      }
                  }
              }
          }
      
          public static IEnumerable<T> Delimit<T>(this IEnumerable<T> source, T separator, T prefix, T suffix)
          {
              using (var enumerator = source.GetEnumerator())
              {
                  if (enumerator.MoveNext())
                  {
                      yield return prefix;
                      yield return enumerator.Current;
                      yield return suffix;
      
                      while (enumerator.MoveNext())
                      {
                          yield return separator;
      
                          yield return prefix;
                          yield return enumerator.Current;
                          yield return suffix;
                      }
                  }
              }
          }
      
          public static IEnumerable<T> Delimit<T>(this IEnumerable<T> source, Func<T, T, T> separator, Func<T, T> prefix, Func<T, T> suffix)
          {
              using (var enumerator = source.GetEnumerator())
              {
                  if (enumerator.MoveNext())
                  {
                      if (prefix != null)
                          yield return prefix(enumerator.Current);
      
                      yield return enumerator.Current;
      
                      if (suffix != null)
                          yield return suffix(enumerator.Current);
      
                      T previous = enumerator.Current;
      
                      while (enumerator.MoveNext())
                      {
                          if (separator != null)
                              yield return separator(previous, enumerator.Current);
      
                          if (prefix != null)
                              yield return prefix(enumerator.Current);
      
                          yield return enumerator.Current;
      
                          if (suffix != null)
                              yield return suffix(enumerator.Current);
      
                          previous = enumerator.Current;
                      }
                  }
              }
          }
      
          public static IEnumerable<TOut> Delimit<TIn, TOut>(this IEnumerable<TIn> source, Func<TIn, TOut> convert, Func<TIn, TIn, TOut> separator, Func<TIn, TOut> prefix, Func<TIn, TOut> suffix)
          {
              using (var enumerator = source.GetEnumerator())
              {
                  if (enumerator.MoveNext())
                  {
                      if (prefix != null)
                          yield return prefix(enumerator.Current);
      
                      yield return convert(enumerator.Current);
      
                      if (suffix != null)
                          yield return suffix(enumerator.Current);
      
                      TIn previous = enumerator.Current;
      
                      while (enumerator.MoveNext())
                      {
                          if (separator != null)
                              yield return separator(previous, enumerator.Current);
      
                          if (prefix != null)
                              yield return prefix(enumerator.Current);
      
                          yield return convert(enumerator.Current);
      
                          if (suffix != null)
                              yield return suffix(enumerator.Current);
      
                          previous = enumerator.Current;
                      }
                  }
              }
          }
      }
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2011-09-08
        • 2013-03-26
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2010-09-20
        • 2012-02-03
        • 1970-01-01
        相关资源
        最近更新 更多