C# 在括号之间匹配一个整数
我收到了以下格式的字符串:C# 在括号之间匹配一个整数,c#,.net,regex,string,C#,.net,Regex,String,我收到了以下格式的字符串: ASDF [ 6] ZXC[1] OtPasd[ 4 ] asdffa[ 7] 我需要检索有效字符串上括号之间的整数。只要满足以下条件,字符串就有效: 括号之间仅存在空白。即:“ZXCV[a2]”无效 所有支架均正确关闭。即:“qwr[2”无效 所有字符串只有一个打开/关闭括号。即:“zxcf[4]]]”无效 我最好避免使用正则表达式,因为我得到了大量的字符串,所以一些计算上不敏感的东西会更好 验证和检索整数的最干净和最快的方法是什么 编辑
ASDF [ 6]
ZXC[1]
OtPasd[ 4 ]
asdffa[ 7]
我需要检索有效字符串上括号之间的整数。只要满足以下条件,字符串就有效:
编辑:我决定使用正则表达式。试试这个正则表达式:
\[\s*(\d+)\s*\]$
如果要避免使用regex,请使用此regex
(?m)(?!)。使用IndexOf/LastIndexOf然后解析剩余字符串是否适合您的需要?要获取括号之间的int,您也可以尝试以下方法:
string tmpString = "ASDF [ 6]";
int start = tmpString.IndexOf('[') + 1;
int length = tmpString.IndexOf(']') - start;
string subString = tmpString.Substring(start, length);
int tempInt;
if(Int.TryParse(subString, out tempInt))
return tempInt;
在我个人看来,最干净的解决方案是使用正则表达式。但是与其猜测它是否是计算密集型的,我宁愿对它进行基准测试。下面是代码
const int Count = 10000000;
const string testString = "<whatever>";
// Solution No. 1: use Regex.Match()
Stopwatch sw = new Stopwatch();
sw.Start();
for (int i = 0; i < Count; i++)
{
var match = Regex.Match(@"\[\s*(\d+)\s*\]$", testString);
if (!match.Success)
continue;
var number = int.Parse(match.Groups[1].Value);
}
sw.Stop();
Console.WriteLine(sw.ElapsedMilliseconds);
// Solution No. 2: use IndexOf() and Substring() shenanigans
sw.Start();
for (int i = 0; i < Count; i++)
{
var lb = testString.IndexOf('[');
var rb = testString.LastIndexOf(']');
if (lb < 0 || rb != testString.Length - 1)
continue;
var str = testString.Substring(lb + 1, rb - lb - 1);
int number;
if (!int.TryParse(str, out number))
continue;
// use the number
}
sw.Stop();
Console.WriteLine(sw.ElapsedMilliseconds);
正如您所看到的,不仅正则表达式解决方案更短、更简洁,它实际上更快。如果您使用不同的输入字符串,您会注意到输入字符串越长,第一个和第二个解决方案之间的差距就越大。您应该向我们展示您的尝试。我可以理解这很难学习,但是你至少应该尝试一些东西并展示一下。你为什么要放弃正则表达式的想法?到目前为止,我认为这是最简单的方法,可以让你的数字出来,它可能会像任何其他解决方案一样快。过早的优化是万恶之源!使用String.IndexOf
,String.Trim
和Int.TryPa的组合rse似乎很有可能。但是,我认为你应该重新考虑使用正则表达式,它们可能没有你最初认为的那么昂贵。@trailmax阿门!而且,正则表达式可能比手动拆分、修剪等更健壮。使用正则表达式,然后如果发现它是一个瓶颈,可以提高性能。编写干净的工作维护e代码,然后编写快速代码。别忘了,在C#中,正则表达式可以编译,这是一个好主意,但在“aasdf[[[5]]][]”之类的情况下需要更多的工作/验证。但是让我们为l46kok留下一些工作要做-)的确,我们不需要给他我认为的所有代码:)但是当他在这里结合一些问题时,他会用括号回答问题的。我只想要括号内的整数。例如:asdf[3]给你[3]支持,但事实并非如此。MatchCollection a=Regex.Matches(s,@“(?m)(?)也匹配括号。我只希望括号内的整数。例如:asdf[3]提供[3]back@IgorKorkhov,通过存储已编译的正则表达式可以更快。var Regex=new Regex(@“\[\s*(\d+)\s*\]$”,RegexOptions.compiled)
@CaffGeek:不太可能,因为静态的Regex.Match()
自动缓存最后10个左右编译的正则表达式。@igorkov,我注意到了一个不同,但可能是创建新正则表达式对象的成本,而不是节省时间的正则表达式编译。
Solution | testString | Time (ms) | Comment
----------|--------------|--------------|-----------------------
1 | abc [ ] | 4476 | Invalid input string
2 | abc [ ] | 6594 | Invalid input string
1 | abc[1234] | 4446 | Valid input string
2 | abc[1234] | 6290 | Valid input string