2013-03-05 46 views
4

的指數,我需要借這個字符串:正則表達式替換字符與匹配

book_id = ? and author_id = ? and publisher_id = ? 

,並把它變成這個字符串:使用此代碼

book_id = @p1 and author_id = @p2 and publisher_id = @p3 

Regex.Replace(input, @"(\?)", "@p **(index of group)**"); 

什麼是替代模式給我的小組的索引?

+0

一行程序很容易 - 只需執行**替換(」 \ n「,」「)** – 2013-03-05 00:43:04

+0

非常可愛的迴應; p – schmij 2013-03-05 00:58:44

+0

我可以使用正則表達式替換第三個參數中的模式嗎? – schmij 2013-03-05 01:26:17

回答

2

你可以使用,需要一個MatchEvaluator,用計數器變量沿Regex.Replace method

string input = "book_id = ? and author_id = ? and publisher_id = ?"; 
string pattern = @"\?"; 
int count = 1; 
string result = Regex.Replace(input, pattern, m => "@p" + count++); 

m =>部分是MatchEvaluator。在這種情況下,不需要使用Match(即m);我們只想返回連接結果並增加計數器。

+0

我們正在回暖,但我需要包含在索引計算放置模式。 – schmij 2013-03-05 01:06:37

+0

@schmij你能解釋一下你的意思嗎?我的方法給出了類似於你的問題的結果。如果你需要在輸入中出現'?'的索引,你可以在lambda中使用'm.Index'而不是'count'變量。或者,如果模式使用一個組,「@」(\?)「',則可以使用'm.Groups [1] .Index'。我認爲這不符合你的要求。也許輸出的另一個例子將有助於澄清你的內容。 – 2013-03-05 01:15:26

+0

我正在尋找一個正則表達式替換模式來生成匹配組的索引。 – schmij 2013-03-05 01:21:22

0

未經測試:

int n, i=1; while((n=input.IndexOf("?")) != -1) { input = input.Substring(0,n-1) + "@p" + (++i) + input.Substring(n+1); } 

稍長線,但不能完全不合理。

+0

是的,它是一行..但我不完全確定是OP的目標是什麼.. – 2013-03-05 01:12:41

0

如果你想要一個一行的解決方案,你可以做類似的事情,但對於大型字符串可能會很慢,因爲它必須找到「?」的計數。對於每場比賽

var result = Regex.Replace(input, @"\?", m => "@p" + input.Take(m.Index).Count(c => c == '?')); 

返回"book_id = @p0 and author_id = @p1 and publisher_id = @p2"

這是我可以看到得到一個indext沒有聲明外部變量的唯一途徑。

+0

我已經用一行解決方案更新了我的答案 – 2013-03-05 02:13:29

0

我寫了一個項目來測試其他答案和我自己的答案。你可以得到它here
結論:
- linq解決方案是最快的。
- 正則表達式的解決方案是最優雅的。
- 我與StringBuilder的解決方案是不壞,但不是最快的也不是最優雅:(

這裏是我的解決方案:

var count = 1; 
var sb = new StringBuilder(input); 
for (int i = 0; i < sb.Length; i++) 
{ 
    if (sb[j] == '?') 
    { 
     sb.Remove(i, 1); 
     sb.Insert(i, "@p" + (count++)); 
     i += 3; 
    } 
} 
result = sb.ToString(); 
相關問題