[英]split a comma-separated string and add Quotes in C# - elegant solution
I have a string
looking like this:我有一个看起来像这样的
string
:
var v = "10,14,18,21"
and would like to use it as something looking like this:并希望将其用作如下所示的东西:
'10', '14', '18', '21'
I have a written a function which splits the values by comma and add them back together as a string.我写了一个 function ,它用逗号分割值并将它们作为字符串加在一起。 Additionally I remove the last
,
from the result string.另外,我从结果字符串中删除了最后一个
,
。
I put everything in a function called prep
for testing.我把所有东西都放在一个名为
prep
for testing 的 function 中。
The function does, what I want it to do. function 做了,我想让它做。 However, I was wondering if there is a more elegant way to achieve the same result.
但是,我想知道是否有更优雅的方法来实现相同的结果。 Here's what I came up with:
这是我想出的:
public static string prep(string s) {
string res = "";
List<string> list = s.Split(',').ToList<string>();
foreach(var item in list)
res += "'" + item + "',";
res = res.TrimEnd(',');
return res;
}
Have you considered this?你考虑过这个吗?
var v = "10,14,18,21";
var r = $"'{v.Replace(",", "', '")}'";
That gives: '10', '14', '18', '21'
这给出:
'10', '14', '18', '21'
You can try regular expressions :您可以尝试正则表达式:
using System.Text.RegularExpressions;
...
string result = Regex.Replace(v, "[^,]+", " '$0'");
here we wrap every item between commas into single quotes.在这里,我们将逗号之间的每个项目包装成单引号。
Edit: As juharr pointed out in the comments, we have extra space at the beginning of the result
string.编辑:正如 juharr 在评论中指出的那样,我们在
result
字符串的开头有额外的空间。 We can either我们既可以
remove it:去掉它:
result = Regex.Replace(v, "[^,]+", " '$0'").TrimStart();
Or prevent it:或阻止它:
string result = Regex
.Replace(v, "[^,]+", m => $"{(m.Index > 0 ? " ":"")}'{m.Value}'");
You could use string.Join()
here:你可以在这里使用
string.Join()
:
var result = string.Join(", ", v.Split(",").Select(x => $"'{x}'"));
Console.WriteLine(result);
// '10', '14', '18', '21'
Which basically concatenates the items by ", "
, then projects single quotes around each string with Enumerable.Select()
from LINQ.它基本上通过
", "
连接项目,然后使用 LINQ 中的Enumerable.Select()
在每个字符串周围投射单引号。
You can also add single quotes without $ - string interpolation :您还可以添加不带$ - 字符串插值的单引号:
var result = string.Join(", ", v.Split(",").Select(x => "'" + x + "'"));
As @Racil Hilan helpfully pointed out in the comments, we don't need LINQ here and can just surround the result with "'"
and join on "', '"
:正如@Racil Hilan在评论中有用地指出的那样,我们在这里不需要 LINQ 并且可以用
"'"
包围结果并加入"', '"
:
var result = "'" + string.Join("', '", v.Split(",")) + "'";
One way is to use Select
on the result of Split
, then string.Join
:一种方法是在
Split
的结果上使用Select
,然后string.Join
:
public static string prep(string s) {
var array = s.Split(',');
// Select takes a lambda that tells it what to do with each item in the array
var quotesAdded = array.Select(x => $"'{x}'");
var result = string.Join(", ", quotesAdded);
return result;
}
Or all in an expression-bodied member :或全部在表达式主体成员中:
public static string prep(string s) => string.Join(", ",
s.Split(',').Select(x => $"'{x}'")
);
Just for the heck of it I wrote some code to test out the various methods here to see how they fair against each other with different length strings.只是为了它,我写了一些代码来测试这里的各种方法,看看它们如何用不同长度的字符串相互竞争。 Feel free to add any other variations to this to find out for yourself which one is fastest and to see how it scales with larger strings.
随意添加任何其他变体,以自己找出哪个是最快的,并看看它如何与更大的字符串一起扩展。
Note: I gave up on a string with 10,000 comma separated items because the Aggregate method was taking a very long time to complete.注意:我放弃了包含 10,000 个逗号分隔项的字符串,因为 Aggregate 方法需要很长时间才能完成。
private static readonly Random Rand = new Random();
private static void Main(string[] args)
{
for (int size = 10; size <= 1000; size *= 10)
{
var input = GenerateInput(size);
Console.WriteLine($"Size {size}:");
Console.WriteLine("Average Total Method");
Tester(input, AddSingleQuotesRegExNotCompiled, nameof(AddSingleQuotesRegExNotCompiled));
Tester(input, AddSingleQuotesRegExCompiled, nameof(AddSingleQuotesRegExCompiled));
Tester(input, AddSingleQuotesStringReplace, nameof(AddSingleQuotesStringReplace));
Tester(input, AddSingleQuotesJoinSplitSelectWithInterpolation, nameof(AddSingleQuotesJoinSplitSelectWithInterpolation));
Tester(input, AddSingleQuotesJoinSplitSelectWithoutInterpolation, nameof(AddSingleQuotesJoinSplitSelectWithoutInterpolation));
Tester(input, AddSingleQuotesJoinSplit, nameof(AddSingleQuotesJoinSplit));
Tester(input, AddSingleQuotesSplitSelectAggregate, nameof(AddSingleQuotesSplitSelectAggregate));
Console.WriteLine();
}
Console.ReadLine();
}
public static void Tester(string input, Func<string, string> func, string name)
{
var sw = Stopwatch.StartNew();
for (int i = 0; i < 10000; i++)
{
func(input);
}
sw.Stop();
Console.Write($"{sw.Elapsed/10000} {sw.Elapsed} {name}");
Console.WriteLine();
}
public static string GenerateInput(int count)
{
var builder = new StringBuilder();
while (count-- > 0)
{
builder.Append(Rand.Next(100));
if (count > 0)
builder.Append(',');
}
return builder.ToString();
}
private static Regex addComma = new Regex("[^,]+", RegexOptions.Compiled);
public static string AddSingleQuotesRegExCompiled(string input) =>
addComma.Replace(input, "'$0'");
public static string AddSingleQuotesRegExNotCompiled(string input) =>
Regex.Replace(input, "[^,]+", " '$0'");
public static string AddSingleQuotesStringReplace(string input) =>
$"'{input.Replace(",", ", ")}'";
public static string AddSingleQuotesJoinSplitSelectWithInterpolation(string input) =>
string.Join(", ", input.Split(",").Select(x => $"'{x}'"));
public static string AddSingleQuotesJoinSplitSelectWithoutInterpolation(string input) =>
string.Join(", ", input.Split(",").Select(x => "'" + x + "'"));
public static string AddSingleQuotesJoinSplit(string input) =>
"'" + string.Join("', '", input.Split(",")) + "'";
public static string AddSingleQuotesSplitSelectAggregate(string input) =>
input.Split(',')
.Select(m => "'" + m + "'")
.Aggregate((tot,next) => tot + "," + next);
}
with the following results结果如下
Size 10:
Average Total Method
00:00:00.0000053 00:00:00.0526194 AddSingleQuotesRegExNotCompiled
00:00:00.0000031 00:00:00.0309486 AddSingleQuotesRegExCompiled
00:00:00.0000002 00:00:00.0018592 AddSingleQuotesStringReplace
00:00:00.0000017 00:00:00.0169309 AddSingleQuotesJoinSplitSelectWithInterpolation
00:00:00.0000008 00:00:00.0084822 AddSingleQuotesJoinSplitSelectWithoutInterpolation
00:00:00.0000004 00:00:00.0039672 AddSingleQuotesJoinSplit
00:00:00.0000010 00:00:00.0102010 AddSingleQuotesSplitSelectAggregate
Size 100:
Total Average Method
00:00:00.0000239 00:00:00.2394021 AddSingleQuotesRegExNotCompiled
00:00:00.0000163 00:00:00.1628607 AddSingleQuotesRegExCompiled
00:00:00.0000015 00:00:00.0149009 AddSingleQuotesStringReplace
00:00:00.0000065 00:00:00.0650797 AddSingleQuotesJoinSplitSelectWithInterpolation
00:00:00.0000069 00:00:00.0693588 AddSingleQuotesJoinSplitSelectWithoutInterpolation
00:00:00.0000034 00:00:00.0338554 AddSingleQuotesJoinSplit
00:00:00.0000129 00:00:00.1287369 AddSingleQuotesSplitSelectAggregate
Size 1000:
Total Average Method
00:00:00.0002089 00:00:02.0892826 AddSingleQuotesRegExNotCompiled
00:00:00.0001607 00:00:01.6066026 AddSingleQuotesRegExCompiled
00:00:00.0000144 00:00:00.1444781 AddSingleQuotesStringReplace
00:00:00.0000578 00:00:00.5776627 AddSingleQuotesJoinSplitSelectWithInterpolation
00:00:00.0000580 00:00:00.5801025 AddSingleQuotesJoinSplitSelectWithoutInterpolation
00:00:00.0000296 00:00:00.2957712 AddSingleQuotesJoinSplit
00:00:00.0005631 00:00:05.6307457 AddSingleQuotesSplitSelectAggregate
Just another approach to solve this problem (without using LINQ):解决此问题的另一种方法(不使用 LINQ):
public static string prep(string s) =>
"'" + string.Join("', '", s.Split(",")) + "'";
I prefer to use aggregate我更喜欢使用聚合
string a = "1,2,3,4,5";
string c = a.Split(',').Select(m => "'" + m + "'").Aggregate((tot,next) => tot + "," + next);
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.