簡體   English   中英

正則表達式刪除除括號之外的所有空格

[英]regex to remove all whitespaces except between brackets

我一直在努力解決我希望用正則表達式解決的問題。

假設我有一個字符串,可以包含任何字母數字,並且子字符串可能被方括號包圍。 這些子字符串可以像這樣出現在字符串中的任何位置。 也可以有任意數量的括號子串。

例子:

  • aaa [bb b]
  • aaa [bbb] ccc [d dd]
  • [aaa] bbb [c cc]

您可以看到某些括號中的子串中有空格,這很好。 我現在的主要問題是當我遇到括號外的空格時,如下所示:

  • aa [bb b]

現在我想保留括號內的空格,但在其他地方刪除它們。

對於像以下字符串來說,這會變得有點棘手:

  • aa [bb b] c cc [d dd] e ee [f ff]

在這里,我希望返回:

  • aaa [bb b] ccc [d dd] eee [f ff]

我現在花了一些時間閱讀不同的reg ex頁面關於lookarounds,負面斷言等等,這讓我頭暈目眩。

注意:對於訪問此文件的任何人,我並不是在尋找任何涉及嵌套括號的解決方案。 如果是這種情況,我可能會像下面提到的一些評論一樣務實地做。

這個正則表達式應該做的伎倆:

[ ](?=[^\]]*?(?:\[|$))

只需替換與“”匹配的空格即可。

基本上它所做的只是確保你要移除的空間前面有一個“[”,但如果它前面有一個“]”則沒有。

只要您沒有嵌套的方括號,這應該可以工作,例如:

aa [b [cc] b]

因為在這種情況下,第一個“b”之后的空格將被刪除,它將變為:

AA [B [CC] B]

這聽起來不像你真正想要的正則表達式。 通過閱讀直接解析非常容易。 偽代碼:

inside_brackets = false;
for ( i = 0; i < length(str); i++) {
    if (str[i] == '[' )
        inside_brackets = true;
    else if str[i] == ']'
        inside_brackets = false;
    if ( ! inside_brackets && is_space(str[i]) )
        delete(str[i]);
}

任何涉及正則表達式的東西都會涉及很多外觀的東西,這些東西會一遍又一遍地重復,而且它會慢得多,而且難以理解。

要使其適用於嵌套括號,只需將inside_brackets更改為計數器,從零開始,在開括號上遞增,在小括號上遞減。

這對我有用:

(\[.+?\])|\s

然后,當您調用replace函數時,只需傳入$ 1的替換值。 我們的想法是首先在括號內查找圖案,並確保它們不受影響。 然后括號外的每個空格都被替換為空。

請注意,我使用Regex Hero(.NET正則表達式測試程序)進行了測試,而不是使用PHP進行測試。 所以我不是百分百肯定這會對你有用。

這是一個有趣的。 一開始聽起來很簡單,然后看起來相當困難。 然后我終於到達的解決方案確實很簡單。 我很驚訝解決方案不需要任何形式的外觀。 它應該比使用環視的任何方法更快。

如何做到這一點取決於應該做什么:

a b [ c [ d [ e ] f ] g

這是模棱兩可的; 可能的答案至少是:

  • ab[ c [ d [ e ] f ]g
  • ab[ c [ d [ e ]f]g
  • 錯誤; 括號不匹配!

對於前兩種情況,您可以使用regexp。 對於第三種情況,使用(小)解析器會更好。

對於一個或兩個案例,將字符串拆分為第一個[ [之前顯然在括號之外)從所有內容中刪除空格。 接下來,查找.*\\] (案例1)或.*?\\] (案例2)並將其移至輸出。 重復,直到你沒有輸入。

恢復這個問題,因為它有一個沒有提到的簡單解決方案。

\[[^]]*\](*SKIP)(*F)|\s+

交替的左側匹配完整的括號組,然后故意失敗。 右側匹配並捕獲第1組的空格,我們知道它們是正確的空格,因為如果它們在括號內,則左邊的表達式會失敗。

查看此演示中的匹配項

這意味着你可以做到

$replace = preg_replace("~\[[^]]*\](*SKIP)(*F)|\s+~","",$string);

參考

  1. 如何匹配模式除了情況s1,s2,s3
  2. 除非......如何匹配模式

以下內容將匹配行首或行括結束(必須在您要匹配的任何空格之前),后跟任何不是括號或空格的內容,后跟一些空格。

/((^|\])[^ \[]*) +/

$1替換“all”將從每個非括號序列中刪除第一個空格塊。 您必須重復匹配才能刪除所有空格。

例:

abcd efg [hij klm]nop qrst u
abcdefg [hij klm]nopqrst u
abcdefg[hij klm]nopqrstu
done

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM