2009-01-27 110 views
2

使用.NET框架,我试图用单斜杠替换字符串中的双斜线字符,但它似乎是删除一个额外的字符,我不知道为什么。正则表达式替换帮助

我有一个字符串:

http://localhost:4170/RCRSelfRegistration//Default.aspx 

我的正则表达式是:

[^(://|:\\\\)](\\\\|//|\\/|/\\) 

,返回值是:

http://localhost:4170/RCRSelfRegistratio/Default.aspx 

你可以看到,在RCRSelfRegistration n个已除去。我不知道为什么。

/// <summary> 
/// Match on double slashes (//, \\, /\, \/) but do not match :// or :\\ 
/// </summary> 
private const string strMATCH = @"[^(://|:\\\\)](\\\\|//|\\/|/\\)"; 

/// <summary> 
/// Replace double slashes with single slash 
/// </summary> 
/// <param name="strUrl"></param> 
/// <returns></returns> 
public static string GetUrl(string strUrl) 
{ 
    string strNewUrl 
    System.Text.RegularExpressions.Regex rxReplace = 
     new System.Text.RegularExpressions.Regex(strMATCH); 

    strNewUrl = rxReplace.Replace(strUrl, "/"); 

    return strNewUrl; 
} 

回答

4

你的正则表达式的第一部分“[^(:// |:\\)]”匹配任何不是“(:/ | \”的字符(如tomalak指出,negset匹配所有字符它没有进一步的处理逻辑),其中包括紧接在“//default.aspx”之前的“n” - 它不是一个零宽度断言。

你可能想要做的是改变那部分模式到一个零宽度lookbehind,以确保斜杠字符没有冒号前面

+0

我明白你的意思了。我已将字符串简化为“[^:](\\\\ | | // | \\/|/\\)”,但您能告诉我零宽度后视的语法吗? – Jeremy 2009-01-27 17:46:22

+0

现在遍布各地。 =) – Instantsoup 2009-01-27 17:47:53

5

[^(://|:\\\\)]不按照您认为的方式工作。

[]是一个字符范围 - 它匹配范围中包含的单个字符。

[^:]将匹配除冒号以外的任何字符。这可能更接近你想要的。

你可能真正想要的是一个zero-width lookbehind assertion(?<!:)

1

的否定部分[^(:// |:\\)]的您正则表达式的N项匹配,从而删除它。

1

您是否尝试过使用字符串的替换方法。它不像正则表达式替换优雅,但只要你没有这样做在一个循环中数百次巨大的字符串,它应该为你的purpo服务se:

string myString = oldString.Replace(@"\\", @"\").Replace("//", "/"); 

否则,你可以花费与正则表达式的年龄fidlign。

2

你需要的是背后组负这个样子的:

(?<!:)(\\\\|//|\\/|/\\) 
0

我想你只需要一个简单的字符串以循环替换。将所有“//”替换为“/”。您需要一个可以保存搜索位置的功能,并让您浏览字符串。一旦你到达了字符串的末尾,再做一次,直到你没有在通行证上进行任何替换。

例如:

///一个// A/A ////

通1

// A/A/A //

通2

/a/a/a/