Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/281.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/regex/16.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 在正则表达式的输入字符串中使用括号_C#_Regex - Fatal编程技术网

C# 在正则表达式的输入字符串中使用括号

C# 在正则表达式的输入字符串中使用括号,c#,regex,C#,Regex,我正在尝试将项目添加到多行文本框。文本框不应包含重复的行。如果存在副本,则应将其重命名为name(1)。我使用Regex就是为了这个目的 以下是我的职责: private string Rename(string input, string[] lines) { string output = string.Empty; if (lines.Contains(input)) { Regex regEx = new Regex(string.Format(@

我正在尝试将项目添加到多行
文本框
文本框
不应包含重复的行。如果存在副本,则应将其重命名为
name(1)
。我使用Regex就是为了这个目的

以下是我的职责:

private string Rename(string input, string[] lines)
{
    string output = string.Empty;
    if (lines.Contains(input))
    {
        Regex regEx = new Regex(string.Format(@"\b{0}\b", input), RegexOptions.ExplicitCapture);
        string[] str = lines.Select(x => x).Where(y => regEx.IsMatch(y)).ToArray();
        regEx = new Regex(string.Format(@"\b{0}\b \(\d+\)", input));
        string[] matchedStrings = str.Select(x => x).Where(y => regEx.IsMatch(y)).ToArray();
        if (matchedStrings.Length > 0)
        {
            return string.Format("{0} ({1})", input, (matchedStrings.Length + 1));
        }
        else
        {
            return string.Format("{0} (1)", input, matchedStrings.Length);
        }
    }
    else
    {
        return input;
    }
}
这是我在单击按钮时调用函数的方式:

// textBox2 is a multiline text bor. textBox1 is where the input is taken from
textBox2.Text += Rename(textBox1.Text, textBox2.Lines) + Environment.NewLine;
以上代码适用于普通文本。例如:


如果
input
abc
并且再次给出相同的
input
,则返回
abc(1)
。在此之后,如果我以
abc(1)
的形式输入,那么第一个正则表达式模式返回零匹配。因此,我无法正确重命名。

将输入注入正则表达式时,需要将其转义为

//                                                vvvvvvvvvvvvv     v
Regex regEx = new Regex(string.Format(@"\b{0}\b", Regex.Escape(input)), RegexOptions.ExplicitCapture);
input
abc(1)
时,不转义正则表达式将变为
\babc(1)\b
。看见括号是不可替换的,这使得literal
(1)
字符串成为组中捕获的literal
1
模式

请注意
RegexOptions。您使用的ExplicitCapture
不会使括号按字面意思处理。此选项仅告诉正则表达式引擎使用括号进行分组,而不用于捕获

根据经验,一定要对注入正则表达式的字符串进行转义


第二个问题是关闭后
\b
无法匹配
<代码>)
不被视为单词字符,因此
之后的字符串结尾不是单词边界。要解决此问题,您可以为结束
\b
提供一个与
前面的任何内容匹配的替代项。这可能被称为
(?我是否正确地将您的方法称为
重命名(“abc”,new[]{“abc”,“abc”})
?我将
文本框作为第二个参数传递。行
然后请提供一些具有预期输出的示例调用。为什么返回字符串而不是字符串列表/数组?我知道您可能有
新[]{“abc”,“abc(2)”,“def”}
,当您将
abc
作为输入传递时,您希望获得“abc(4)\ndef字符串?因为,输入字符串是根据第二个参数验证的,如果它存在,则会进行修改。为什么我要返回列表?我知道您可能有
new[]{“abc”,“abc(2)”,“def”}
?当您将
abc
作为输入传递时,您希望获得
“abc(4)\ndef”
string?我怀疑这对OP会有帮助,因为代码似乎不符合OP的需要。此外,如果整行必须匹配,
\b
不是OP需要的。还有一点是,
\babc\(1\)\b
将在
abc(1)abc
中匹配,而不是在
abc(1)中匹配
@WiktorStribiżew:我认为未转义括号是主要(或可能是第一个)问题,因为OP声明“如果我以
abc(1)
的形式提供输入,那么第一个正则表达式模式返回零匹配”。我打算过一段时间再进行操作码审查,以应对任何进一步的问题。@Abhishek:这是因为关闭
\b
后关闭
后关闭
失败<代码>)
不被视为单词字符,因此
之后的字符串结尾不是单词边界。我们需要澄清解决问题的要求。
是否应包含
abc(1)def
abc(1)def
(后者在
def
之前有空格,前者没有空格)。如果是,则
重命名(“abc(1)”、新建[]{“abc(1)def”)和
重命名(“abc(1)”、新建[]{“abc(1)def”)的预期结果是什么?(同样,两者在
def
之前相差一个空格)要解决
\b
之后的
\b
问题,请将结束
\b
更改为
(?:\b |)(?)?
//                                           v  vvvvvvvvv
Regex regEx = new Regex(string.Format(@"\b{0}(\b|(?<=\)))", Regex.Escape(input)), RegexOptions.ExplicitCapture);