字符串替换函数,支持自定义通配符并在C#中转义这些通配符

时间:2012-03-06 12:58:22

标签: c# regex string replace escaping

我需要使用自定义通配符支持编写字符串替换函数。我也应该能够逃脱这些通配符。我目前有一个带有Usage,Value和Escape属性的通配符类。

因此,假设我有一个名为通配符的全局列表。通配符只有一个成员添加到这里:

Wildcards.Add(new Wildcard
{
    Usage = @"\Break",
    Value = Enviorement.NewLine,
    Escape = @"\\Break"
});

所以我需要一个CustomReplace方法来完成这个技巧。我应该将给定字符串中的指定参数替换为另一个,就像string.Replace一样。这里唯一的区别是它必须使用我的自定义通配符。

string test = CustomReplace("Hi there! What's up?", "! ", "!\\Break");
// Value of the test variable should be: "Hi there!\r\nWhat's up?"
// Because \Break is specified in a custom wildcard in Wildcards

// But if I use the value of the wildcard's Escape member,
// it should be replaced with the value of Usage member.
test = CustomReplace("Hi there! What's up?", "! ", "!\\\\Break");
// Value of the test variable should be: "Hi there!\\BreakWhat's up?"

我当前的方法不支持转义字符串。 它在性能方面也不是很好,因为我调用string.Replace两次,每个都搜索整个字符串,我想。

// My current method. Has no support for escape strings.
CustomReplace(string text, string oldValue, string newValue)
{
    string done = text.Replace(oldValue, newValue);
    foreach (Wildcard wildcard in Wildcards)
    {
        // Doing this:
        // done = done.Replace(wildcard.Escape, wildcard.Usage);
        // ...would cause trouble when Escape contains Usage.

        done = done.Replace(wildcard.Usage, wildcard.Value);
    }

    return done;
}

那么,我是否必须编写一个替换方法,用char搜索字符串char,并使用逻辑来查找和分离Usage和Escape值,然后用另一个给定字符串替换Usage,将Escape替换为Usage?

或者你知道一个已写的吗?

我可以在此场景中使用正则表达式吗?

如果我可以,怎么样? (没有经验,模式会很好)

如果我这样做,通过字符搜索会比char更快还是更慢?

对于这篇长篇文章感到抱歉,我试图说清楚并抱歉任何错别字等等;这不是我的主要语言。提前谢谢。

4 个答案:

答案 0 :(得分:1)

因此,如果您乐意使用正则表达式来满足您的需求,那么您应该check out this link。它有一些在.Net中使用的好信息。该网站还有大量关于为许多不同需求构建正则表达式模式的例子。

使用通配符替换字符串的基本示例可能如下所示......

string input = "my first regex replace";

string result = System.Text.RegularExpressions.Regex.Replace(input, "rep...e", "result");

//result is now "my first regex result"

注意Replace函数中的第二个参数如何采用正则表达式模式字符串。在这种情况下,点作为通配符,它​​们基本上意味着“匹配任何单个字符”

希望这可以帮助您获得所需。

答案 1 :(得分:1)

答案 2 :(得分:1)

你可以试试这个:

public string CustomReplace(string text, string oldValue, string newValue)
{
    string done = text.Replace(oldValue, newValue);

    var builder = new StringBuilder();
    foreach (var wildcard in Wildcards)
    {
        builder.AppendFormat("({0}|{1})|", Regex.Escape(wildcard.Usage),
            Regex.Escape(wildcard.Escape));
    }
    builder.Length = builder.Length - 1; // Remove the last '|' character

    return Regex.Replace(done, builder.ToString(), WildcardEvaluator);
}

private string WildcardEvaluator(Match match)
{
    var wildcard = Wildcards.Find(w => w.Usage == match.Value);

    if (wildcard != null)
        return wildcard.Value;
    else
        return match.Value;
}

我认为这是最简单,最快速的解决方案,因为对所有通配符只有一个Replace方法调用。

答案 3 :(得分:0)

如果为通配符和转义方法定义模式,则可以创建一个可以找到文本中所有通配符的正则表达式。然后,您可以使用MatchEvaluator替换它们。

class Program
{
    static Dictionary<string, string> replacements = new Dictionary<string, string>();

    static void Main(string[] args)
    {
        replacements.Add("\\Break", Environment.NewLine);

        string template = @"This is an \\Break escaped newline and this should \Break contain a newline.";

        // (?<=($|[^\\])(\\\\){0,}) will handle double escaped items
        string outcome = Regex.Replace(template, @"(?<=($|[^\\])(\\\\){0,})\\\w+\b", ReplaceMethod);

    }

    public static string ReplaceMethod(Match m)
    {
        string replacement = null;
        if (replacements.TryGetValue(m.Value, out replacement))
        {
            return replacement;
        }
        else
        {
            //return string.Empty?
            //throw new FormatException()?
            return m.Value;
        }
    }
}