4

这是代码:

StringBuilder sb = new StringBuilder();
Regex rgx = new Regex("[^a-zA-Z0-9 -]");

var words = Regex.Split(textBox1.Text, @"(?=(?<=[^\s])\s+\w)");
for (int i = 0; i < words.Length; i++)
{
    words[i] = rgx.Replace(words[i], "");
}

当我这样做时,Regex.Split()这些单词还包含带有字符的字符串,例如:

Daniel>

或者

Hello:

或者

\r\nNew

或者

hello---------------------------

我只需要得到没有所有迹象的单词

所以我尝试使用这个循环,但我总结说有很多地方有"" 而且有些地方只有------------------------

我不能在我的代码后面使用它作为字符串。

4

3 回答 3

11

您不需要正则表达式来清除非字母。这将删除所有非 Unicode 字母。

public string RemoveNonUnicodeLetters(string input)
{
    StringBuilder sb = new StringBuilder();
    foreach(char c in input)
    {
        if(Char.IsLetter(c))
           sb.Append(c);
    }

    return sb.ToString();
}

或者,如果你只想允许拉丁字母,你可以使用这个

public string RemoveNonLatinLetters(string input)
{
    StringBuilder sb = new StringBuilder();
    foreach(char c in input)
    {
        if(c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z')
           sb.Append(c);
    }

    return sb.ToString();
}

基准与正则表达式

public static string RemoveNonUnicodeLetters(string input)
{
       StringBuilder sb = new StringBuilder();
       foreach (char c in input)
       {
            if (Char.IsLetter(c))
                sb.Append(c);
       }

            return sb.ToString();
}



static readonly Regex nonUnicodeRx = new Regex("\\P{L}");

public static string RemoveNonUnicodeLetters2(string input)
{
     return nonUnicodeRx.Replace(input, "");
}


static void Main(string[] args)
{

    Stopwatch sw = new Stopwatch();

    StringBuilder sb = new StringBuilder();


    //generate guids as input
    for (int j = 0; j < 1000; j++)
    {
        sb.Append(Guid.NewGuid().ToString());
    }

    string input = sb.ToString();

    sw.Start();

    for (int i = 0; i < 1000; i++)
    {
        RemoveNonUnicodeLetters(input);
    }

    sw.Stop();
    Console.WriteLine("SM: " + sw.ElapsedMilliseconds);

    sw.Restart();
    for (int i = 0; i < 1000; i++)
    {
        RemoveNonUnicodeLetters2(input);
    }

    sw.Stop();
    Console.WriteLine("RX: " + sw.ElapsedMilliseconds);


}

输出(SM = 字符串操作,RX = 正则表达式)

SM: 581
RX: 9882

SM: 545
RX: 9557

SM: 664
RX: 10196
于 2013-07-03T20:42:49.677 回答
2

keyboardP 的解决方案很不错——考虑一下。但正如我在评论中所说,正则表达式实际上是这项工作的正确工具,你只是让它变得不必要的复杂。实际的解决方案是单行:

var result = Regex.Replace(input, "\\P{L}", "");

\P{…}指定我们不想匹配的 Unicode 字符类相反\p{…})。L字母的 Unicode 字符类。

当然,将它封装到一个方法中是有意义的,就像keyboardP 所做的那样。为了避免再次重新编译正则表达式,您还应该考虑将正则表达式的创建从实际代码中提取出来(尽管这可能不会对性能产生很大影响):

static readonly Regex nonUnicodeRx = new Regex("\\P{L}");

public static string RemoveNonUnicodeLetters(string input) {
    return nonUnicodeRx.Replace(input, "");
}
于 2013-07-03T20:57:08.933 回答
2

为了帮助 Konrad 和 keyboardP 解决他们之间的差异,我使用他们的代码进行了基准测试。事实证明,keyboardP 的代码比 Konrad 的代码快 10 倍

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.Text.RegularExpressions;

    namespace ConsoleApplication1
    {
        class Program
        {
            static void Main(string[] args)
            {
                string input = "asdf234!@#*advfk234098awfdasdfq9823fna943";
                DateTime start = DateTime.Now;
                for (int i = 0; i < 100000; i++)
                {
                    RemoveNonUnicodeLetters(input);
                }
                Console.WriteLine(DateTime.Now.Subtract(start).TotalSeconds);
                start = DateTime.Now;
                for (int i = 0; i < 100000; i++)
                {
                    RemoveNonUnicodeLetters2(input);
                }
                Console.WriteLine(DateTime.Now.Subtract(start).TotalSeconds);
            }
            public static string RemoveNonUnicodeLetters(string input)
            {
                StringBuilder sb = new StringBuilder();
                foreach (char c in input)
                {
                    if (Char.IsLetter(c))
                        sb.Append(c);
                }

                return sb.ToString();
            }
            public static string RemoveNonUnicodeLetters2(string input)
            {
                var result = Regex.Replace(input, "\\P{L}", "");
                return result;
            }
        }
    }

我有

0.12
1.2

作为输出

更新:

为了查看是否是正则表达式编译减慢了正则表达式方法,我将正则表达式放在一个只构造一次的静态变量中。

            static Regex rex = new Regex("\\P{L}");
            public static string RemoveNonUnicodeLetters2(string input)
            {
                var result = rex.Replace(input,m => "");
                return result;
            }

但这对运行时没有影响。

于 2013-07-03T21:19:24.550 回答