2016-06-09 68 views
1

我不得不匹配一個數字,然後本身14次。然後我在regexstor.net/tester來到了以下正則表達式:Java中的正則表達式反向引用

(\d)\1{14} 

編輯

當我把它貼在我的代碼,包括反斜線正確:

"(\\d)\\1{14}" 

我已經用"$1"替換了後面的參考"\1",它用於替換Java中的匹配。

然後我意識到它不起作用。當您需要在REGEX中反向引用匹配項時,使用Java,您必須使用"\N",但是當您要替換它時,運算符爲"$N"

我的問題是:爲什麼?

+1

這不僅僅是Java,在大多數正則表達式中,'\ N'是正則表達式模式中的反向引用。 '$'在正則表達式中有特殊的含義 – anubhava

+0

是的,「$」表示表達式的結尾,但爲什麼它們不用'\ N'來替換呢? – Jaumzera

+0

其中一些像'python','sed'或'perl'允許替換'\ N',但Java設計者決定使用'$'符號 – anubhava

回答

2

$1不是Java正則表達式中的反向引用,也不是我能想到的其他任何風格。

String input="A12.3 bla bla my input"; 
input = StringUtils.replacePattern(
      input, "^([A-Z]\\d{2}\\.\\d).*$", "$1"); 
//           ^^^^ 

有大約一回基準是什麼,包括非常到位我得到的片段從一些誤傳:simple java regex with backreference does not work你只當你是更換東西使用$1


Java之外的現有口味在$已經是一個元字符仿照它的正則表達式的語法。它錨定到字符串的末尾(或多行模式下的行)。

同樣,Java使用\1作爲反向引用。因爲正則表達式是字符串,所以它必須被轉義:\\1

從詞彙/句法的角度來看,確實可以使用$1(作爲一種獎勵,它可以防止在使用反向引用時需要「邪惡逃跑」)。

要匹配行結束之後,是1正則表達式將需要$\n1

this line 
1 

它只是更有意義使用,而不是改變規則的一種熟悉的語法,其中大部分來自Perl。

Perl中的第一個版本在1987出來,這比Java,這是在發佈要早得多[1995]

我挖出man pages for Perl 1,其中說:

的包圍結構(\ ...\)也可以使用,在這種情況下,\<digit>匹配digit'的子字符串。 (圖案之外,總是在數字的前面使用$代替\。的$<digit>(和$\`$&$'範圍)延伸到封閉塊或EVAL字符串的末尾,或者到下一個模式匹配與子表達式。\<digit>表示法有時可以在當前模式之外工作,但不應該依賴)。您可以根據需要使用多個括號。如果您有超過9個子字符串,變量$10,$11,...引用相應的子字符串。在該模式內,如果在反向引用之前至少存在那麼多左側parens,那麼\10,\11等等將返回到子字符串。否則(爲了向後兼容)\10\010相同,是一個退格鍵,\11\011相同,是一個製表符。等等。 (\1\9始終是反向引用。)

+1

+提到反向引用和替換之間的區別。 – dognose

+0

「Java在其它現有的風格中對其regex語法進行了建模,其中$已經是元字符,它錨定到字符串的末尾(或多行模式中的行)」這很有道理。你有什麼來源? – Jaumzera

+1

@Jaumzera我現在做;) – Laurel

2

我認爲主要問題不是反向引用 - 這在java中與\1完全吻合。

您的問題更可能是Java中的「整體」轉義正則表達式模式。

如果你想有圖案

(\d)\1{14} 

傳遞給正則表達式引擎,你首先需要逃避它,因爲它是一個java字符串當你寫它:

(\\d)\\1{14} 

瞧,像魅力一樣工作:goo.gl/BNCx7B(添加http://,SO不允許Url-Shorteners,但tutorialspoint.com沒有其他選項,因爲它看起來)

Offline-Example:

import java.util.regex.Matcher; 
import java.util.regex.Pattern; 

public class HelloWorld{ 

    public static void main(String []args){ 
     String test = "555555555555555"; // 5 followed by 5 for 14 times. 

     String pattern = "(\\d)\\1{14}"; 

     Pattern r = Pattern.compile(pattern); 
     Matcher m = r.matcher(test); 
     if (m.find()) { 
      System.out.println("Matched!"); 
     }else{ 
      System.out.println("not matched :-(");  
     } 
    } 
} 
+0

感謝您關注@dognose。我知道Java中的String/Regex轉義。我意識到我應該把它放在問題上。我正在編輯它。 – Jaumzera

+0

@Jaumzera只要看看我提供的例子 - 如果逃脫模式不起作用 - 那麼你的錯誤是在別的地方,但不在「模式」內。 (你確定你有15次相同的數字?(因爲你說1 + 14的追隨者) - 而不僅僅是14個?) – dognose

+0

嗯,我明白你的意思了。但我的疑問是關於替換運算符本身而不是正則表達式。謝謝你的時間。 +一個。 – Jaumzera