处理繁琐的string.Split重载?

时间:2015-06-18 22:57:59

标签: c#

.NET中的string.Split()使用起来很麻烦。对于许多重载,即使传递单个分隔符,也必须指定一个数组(实际上只有一个重载用params标记)。

有没有这样的选择?有没有一种方法可以在不创建数组的情况下完成任务。

2 个答案:

答案 0 :(得分:3)

问题在于开发此类API时存在两种相互矛盾的最佳实践(它们都是良好实践,除非在此特定情况下通常不会发生冲突):

  • 只有params参数可以/ 必须显示为最后一个参数。
  • 函数的重载应保持相同的参数排序。

所以你有第一次重载:

Split(params char[] separator)

利用params关键字,因此您无需显式创建数组,因为这是隐式完成的。

其他重载遵循第二条准则,将separator参数保留为第一个参数,但因此无法指定params关键字,因为它只能出现在最后一个参数上。

因此,这是两种最佳实践之间的平衡设计选择。在这种情况下,它们遵循维护参数顺序指南,并且没有在其他重载上使用params关键字,因为当其他参数后面跟着它时不允许这样做。

解决方案

您可以实现自己的静态方法或扩展,其中separator参数始终是最后一个参数,因此始终可以使用它指定params。基本上你可以决定支持第一条准则并忽略第二条准则:

public string[] Split(int count, StringSplitOptions options, params char[] separator)

在版本化类库和不断发展的API时必须要小心。在某些情况下,引入新的params重载将允许它模糊地匹配旧的重载并破坏使用它的项目的代码。

替代

如果你想避免编写过载扩展,那么Craig W.指出"x".ToCharArray()可能是一种更直观的方式来生成单项数组(甚至"xyz".ToCharArray()用于多个单字符分隔符)。请注意,这意味着您要添加一些额外的运行时处理,但它可能很小,可以忽略不计。

答案 1 :(得分:2)

您可以创建一个具有可选参数的(扩展名)方法。

public static string[] SplitDelimiter(this string str, char delimiter, int count = 0, StringSplitOptions options = StringSplitOptions.None)
{
    int toCount = count == 0 ? count = str.Length : toCount = count;
    return str.Split(new[] { delimiter }, toCount, options);
}

然后您可以在不明确创建数组的情况下使用它。

string myString = "1,2,3";
Console.WriteLine(myString.SplitDelimiter(',').Count()); //returns 3