替换字符串C#

时间:2018-11-27 19:10:27

标签: c# regex string

我有一系列看起来像“ WORD1:JUNK1 WORD2:JUNK2”的字符串,我想从字符串中删除垃圾,同时保留单词之间的字符数(包括垃圾所占用的字符数)。

  • 我有一个清单,列出了将要使用的单词,但不会使用垃圾
  • 单词,所有内容之间的间隔数以及垃圾都会改变每一行

到目前为止,我一直在使用像(word|word|word)(.\*)(word|word|word)(.*)这样的正则表达式,但我不知道该如何维护格式。

已编辑

对不起,您是对的,WORD1 / WORD2和JUNK1 / JUNK2都是我所看到的实际值的变量。其所有字母数字字符和斜杠。

输入示例:

“类别:(4个空格)SIDES(3个空格)创建日期:(3个空格)03/12/16”

“产品:(6个空格)CARROTS(4个空格)删除日期:(4个空格)05/11/17”

输出示例:

“类别:(12个空格)创建日期:(11个空格)”

“产品:(17个空格)删除日期:(12个空格”

我正在尝试用空格替换单词“ SIDES”以及“ 03/12/16”。相反,我希望CATEGORY和DATE CREATED之间的字符数保持相同,并且都为空格。

3 个答案:

答案 0 :(得分:1)

我敢肯定有人会使用regex给您一个很好的清晰答案,但这是我脑海中的一个快速解决方案:

string msg = "this is a silly test message";
string[] junk = new string[] { "silly", "message" };

foreach(string j in junk)
{
    msg = Regex.Replace(msg, j, string.Empty.PadRight(j.Length));
}

答案 1 :(得分:1)

我建议基于Regex.Split操作的解决方案:

var s = "CATEGORY:    SIDES   DATE CREATED:   03/12/16";
var rx = @"(\b(?:CATEGORY|PRODUCT|DATE (?:CREA|DELE)TED):)";
var chunks = Regex.Split(s, rx);
Console.WriteLine(string.Concat(
    chunks.Select(
        x => Regex.IsMatch(x, $"^{rx}$") ? x : new String(' ', x.Length))
    )
);

请参见C# demo

(\b(?:CATEGORY|PRODUCT|DATE (?:CREA|DELE)TED):)正则表达式是捕获组内的定界符模式,因此Regex.Split可以将匹配项添加到结果数组中。它匹配整个单词CATEGORYPRODUCTDATE CREATEDDATE DELETED,然后匹配:。如果该项目完全与该定界符匹配(请参见^中的$Regex.IsMatch(x, $"^{rx}$")锚点),则它必须保持原样,否则将生成new String(' ', x.Length)一串空格。 / p>

如果您需要纯正则表达式解决方案,则可以使用

var delim = @"\b(?:CATEGORY|PRODUCT|DATE (?:CREA|DELE)TED):";
Console.WriteLine(Regex.Replace(s, $@"(\G(?!^)\s*|{delim}\s*)(?!{delim})\S", "$1 "));

请参见this regex demo

详细信息

  • (\G(?!^)\s*|{delim}\s*)-第1组(替换模式中的$1):上一个匹配项(\G(?!^))的结尾,后跟0+空格(\s*)或( |)带有0+空格的delim模式
  • (?!{delim})\S-不是delim序列的起始字符的任何非空白字符

答案 2 :(得分:0)

我认为这是一个有趣的实验,我想出了一种与其他答案完全不同的方法。

public class WordStripper
{
    public string StripWords(string input)
    {
        var ignoreWords = new List<string>
        {
            "CATEGORY:",
            "DATE CREATED:",
            "PRODUCT:",
            "DATE DELETED:"
        };
        var deliminator = string.Join("|", ignoreWords);
        var splitInput = Regex.Split(input, $"({deliminator})");
        var sb = new StringBuilder();
        foreach (var word in splitInput)
        {
            if (ignoreWords.Contains(word))
            {
                sb.Append(word);
            }
            else
            {
                var wordLength = word.Length;
                sb.Append(new string(' ', wordLength));
            }
        }

        return sb.ToString();
    }
}

并进行单元测试以验证您是否感兴趣(使用NUnit)

[TestFixture]
public class Test
{
    [Test]
    [TestCase("CATEGORY:    SIDES   DATE CREATED:   03/12/16", "CATEGORY:            DATE CREATED:           ")]
    [TestCase("PRODUCT:      CARROTS    DATE DELETED:    05/11/17", "PRODUCT:                 DATE DELETED:            ")]
    public void TestMethod(string input, string expectedResult)
    {
        //arrange
        var uut = new WordStripper();

        //act
        var actualResults = uut.StripWords(input);

        //assert
        Assert.AreEqual(expectedResult, actualResults);
    }
}