【问题标题】:regular expression to not match something in quotes正则表达式与引号中的内容不匹配
【发布时间】:2013-07-29 15:46:33
【问题描述】:

我在 php preg_match 中使用了一些正则表达式来去除 ":" 和 "(" 中的尾随空格

([\(:])\s+

我遇到的问题是它最终会删除我需要的引号内的空格。例如这个字符串:

img[style*="float: left"]

有没有办法编写正则表达式,使其匹配任何“:”或“(”,除非它被双引号括起来?

【问题讨论】:

  • 如果你只是在寻找尾随空格,你不能只在你的正则表达式中添加一个行尾 ($) 以便它不匹配字符串中的冒号和括号吗?
  • 我希望从字符串中去掉空格,而不仅仅是行尾的空格。我只想跳过引号中的内容。

标签: regex preg-match regex-negation


【解决方案1】:

说明

此例程将:

  • 跳过引号内的匹配项
  • 替换引号外的匹配项

Live Demo

代码

<?php

$string = 'img[style*="float: left"]
img: [style*="float: left"]
img( [style*="float: left"]
';


    $regex = '/"[^"]*"|([:(])\s+/ims';

    $output = preg_replace_callback(
        $regex,
        function ($matches) {
            if (array_key_exists (1, $matches)) {
                return $matches[1] ;
            }
            return $matches[0];
        },
        $string
    );
    echo "this is the output:"  . $output;

输出

this is the output:img[style*="float: left"]
img:[style*="float: left"]
img([style*="float: left"]

【讨论】:

    【解决方案2】:

    有两种方法可以解决这个问题:

    1. 您可以使用否定环视(信息here)来尝试断言在您不想删除的内容之前或之后没有双引号。我遇到的问题是,没有迹象表明与引号 :( 的距离可能有多远,并且环视不能是未知长度。

    2. 我喜欢做的是“保留”包含在双引号中的任何内容,将正则表达式 \"[^"]+\" 放在一个数组中,并用字符串替换它们(我使用“THIS_IS_A_QUOTE”)。将所有引号存储在数组中后,去除所有空格,最后使用数组中的字符串恢复所有“THIS_IS_A_QUOTE”字符串。

    【讨论】:

    • 这是一个聪明的方法。如果我无法获得其他解决方案之一,我会尝试#2。谢谢!
    【解决方案3】:

    你可以试试这个:

    $text = preg_replace('~(?|(\\\{2}|\\\"|"(?>[^"\\\]+|\\\{2}|\\\")*+")|([:(])\s+)~', '$1', $text);
    

    想法是匹配([:(])\s+之前的双引号部分并自行替换。

    为避免匹配转义的引号,反斜杠在之前匹配。

    图案细节:

    ~                                    # pattern delimiter
    (?|                                  # branch reset : all capture groups inside have the same number
        (                                # open a capturing group
            \\\{2}                       # group of 2 backslashes (can't escape everything)
          |                              # OR
            \\\"                         # an escaped double quote
          |                              # OR
            "(?>[^"\\\]+|\\\{2}|\\\")*+" # content inside double quotes
        )                                # close the capturing group
      |                                  # OR
        ( [:(] )                         # a : or a ( in a capturing group
        \s+                              # spaces
    )                                    # close the branch reset group
    ~                                    # pattern delimiter
    

    兴趣是处理这种情况:

    img: " : \" ( "
    img: \" : ( " ( "
    img: \\" : ( " ( "
    

    结果:

    img:" : \" ( "
    img:\" :(" ( "
    img:\\" : ( " ("
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2017-05-25
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-02-17
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多