【问题标题】:Remove a string from regex match results (remove link class if link contains a specific attribute)从正则表达式匹配结果中删除字符串(如果链接包含特定属性,则删除链接类)
【发布时间】:2013-11-21 07:28:57
【问题描述】:

我正在尝试让我的 PHP 代码从包含属性 data-class="false" 的链接中删除 class="something" 并保留其他链接。

$mytext = 'text text text <a href="/url" data-class="false" class="something">
link1</a> text text text <a href="/url" class="something">link2</a> text text 
text <a href="/url" class="something" data-class="false">link3</a> text text 
text';

// This function is supposed to remove the class="something" string from matches.
function remove_class($matches) {
  return str_replace(' class="something"','', $matches[1]);
}

// Match any link that contains the data-class="false" string and do callback.
$mytext = preg_replace_callback('/<a.*?data-class="false".*?>/', 
'remove_class', $mytext);

echo $mytext;

期望的结果如下:(注意类在 data-class="false" 存在的地方被删除)

text text text <a href="/url" data-class="false">link1</a> text text text
<a href="/url" class="something">link2</a> text text text
<a href="/url" data-class="false">link3</a> text text text

【问题讨论】:

  • 您遇到错误了吗?
  • 不解析 HTML,使用正则表达式,使用特殊解析器

标签: php regex str-replace preg-replace-callback


【解决方案1】:

这应该可以工作

$mytext = 'text text text <a href="/url" data-class="false" class="something">
link1</a> text text text <a href="/url" class="something">link2</a> text text 
text <a href="/url" class="something" data-class="false">link3</a> text text 
text';     
$mytext2=  str_replace('data-class="false" class="something"','data-class="false"', $mytext );
$mytext3=  str_replace('class="something" data-class="false"','data-class="false"', $mytext2 );
echo htmlentities($mytext3);

【讨论】:

  • 你自己试过了吗?这似乎给出了这些结果: text text text link1 text text text link2 text text text link3 text text text跨度>
  • 不,这行不通...寻找 'class="something" data-class="false"' 不够健壮...链接标签,比如name、id、rel等……我不能保证它们会像这样在一起。
【解决方案2】:

从您显示的代码来看,我没有看到使用 preg_replace_callback 的理由,preg_replace 应该足够了。

$mytext = 'text text text <a href="/url" data-class="false" class="something">
link1</a> text text text <a href="/url" class="something">link2</a> text text 
text <a href="/url" class="something" data-class="false">link3</a> text text 
text';

// Match any link that contains the data-class="false" and class="something" 
// Then removes class="something".
$mytext = preg_replace('/(<a.*?)(class="something")\s(.*?data-class="false".*?>)|(<a.*?)(data-class="false".*?)\s(class="something")(.*?>)/', 
'$1$3$4$5$7', $mytext);

echo $mytext;

将输出:

text text text <a href="/url" data-class="false">
link1</a> text text text <a href="/url" class="something">link2</a> text text 
text <a href="/url" data-class="false">link3</a> text text 
text

发生了什么是 preg_replace 匹配 class="something" data-class="false"data-class="false" class="something"。每个子模式 (...) 都可以通过 $ 和子模式的编号来引用。如果我们找到了前三个子模式,那么我们使用 $1$3 省略 $2,只用我们想要的子模式匹配替换匹配项。由于子模式 $4-$7 我们没有使用它们被忽略,反之亦然,如果我们匹配 $4-$7。通过将\s 排除在子模式之外,我们将摆脱多余的空间。

【讨论】:

  • 您自己尝试过吗?我想删除 class="something" 部分,但前提是链接包含 data-class="false"。
  • 抱歉,我的回复有点快。它已更新。
  • 似乎很接近,但它并没有完全起作用......我刚刚尝试过,这就是它给出的结果: text text text link1 text text text link2 text text text link3 文字文字文字
  • 它似乎只在 class="something" 是第一个时才有效,但在这种情况下,没有一种情况可以确定 class="something" 会出现在 data-class="false" 之前...所以无论顺序如何,它都需要工作。
  • @ChrisPaddison 显然排队退货是行不通的。我添加它以使so 更具可读性。我已经修复了上面的代码。这是工作链接:tehplayground.com/#PHuoNHXj6
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-02-01
  • 2010-10-23
  • 2010-10-31
  • 2018-05-01
相关资源
最近更新 更多