如何查找和替换与模式匹配的文件内容?

如何查找和替换与模式匹配的文件内容?

假设我们有一个名为项目。我想&$ 在函数调用时找到文件夹中包含模式的每个文件。

例如应该替换:

AnyFunction(&$arg);

AnyFunction($arg);

AnyFunction与模式匹配的未知函数在哪里。

我需要这个来尝试解决这个问题php问题

如果可能的话我也想,如果一个函数与模式匹配,它的声明也会改变:

function AnyFunction(&$arg)

我该如何执行此操作?

答案1

如果您的源代码格式合理,则可以采用简单的文本方法,除非前面有单词,否则将起作用:AnyFunction(arg1, &$arg2)与函数调用在同一行上没有函数声明,函数名称之间没有注释或换行符,没有包含不平衡的注释函数调用内的括号等。这将捕获注释和字符串文字,并且可能会错过一些复杂的函数调用(例如,它不会捕获in )。AnyFunction(arg1, $arg2)functionfunction&$arg2f(g(), &$arg2)

在您的文件上运行此脚本,它们将被就地修改。警告:未经测试,请先备份!

#!/usr/bin/perl -pi
BEGIN { use warnings; use strict; undef $/; }
sub straighten_ampersands {
    my ($args, $want_ampersands) = @_;
    $want_ampersands = ($want_ampersands ? "&" : "");
    $args =~ s{ ([(,]\s*) &? (\$\w) }
              { $1 $want_ampersands $2 }x;
}
s{
  (\bfunction\s+|)(\w+\s+)      # optional 'function' keyword, then function name
  (\((?:(?>[^()]+)|(?4))*)\)))  # balanced parentheses (from perlre)
 }{
  "$1$2" . straighten_ampersands($3, $1 ne "")
 }ex

答案2

这是相当直接的搜索并用 sed 替换。

  1. 最简单的情况,如果您可以相当确定没有任何其他实例&$您不想更改:

    find Project -name '*.php' -print0 | xargs -0r sed -i -e 's/&\$/$/g'

  2. 如上所述,但将搜索和替换限制为函数调用或定义的第一个参数(如上面的示例所示):

    find Project -name '*.php' -print0 | xargs -0r sed -i -e 's/(&\$/($/g'

  3. 与上面的 1. 相同,但将替换限制为括号内出现 &$ 的行:

    find Project -name '*.php' -print0 | xargs -0r sed -i -e '/([^)]*&\$[^)]*)/ s/&\$/$/g'

    注意1:这仍然会改变&$同一行上括号外的任何其他内容,但仅限于已经在括号内找到的行(...&$...)

    注意2:这不会&$在多行函数调用或定义的第二行和后续行上改变......它们与搜索条件不匹配。

在所有情况下,请制作项目目录的工作副本并使用它。当它更改为您想要的内容并且您已经测试它是否有效(至少不会引入比它解决的问题更多的问题)时,将真实的项目目录移到一边(例如mv Project Project.old),然后将修改后的项目移动到位(例如 mv Project.workingcopy Project

相关内容