如何打印其中包含特定字符串的任何函数的完整函数声明?

如何打印其中包含特定字符串的任何函数的完整函数声明?

我的 中有很多函数bashrc,但对于新创建的函数,我经常忘记函数的名称。

例如,当我在我的中定义了这个函数时.bashrc

function gitignore-unstaged
{
    ### Description:
    # creates a gitignore file with every file currently not staged/commited.
    # (except the gitingore file itself)
    ### Args: -

    git ls-files --others | grep --invert-match '.gitignore' > ./.gitignore

}

我想要另一个函数来打印函数的定义,例如:

$ grepfunctions "gitignore"
function gitignore-unstaged
{
    ### Description:
    # creates a gitignore file with every file currently not staged/commited.
    # (except the gitingore file itself)
    ### Args: -

    git ls-files --others | grep --invert-match '.gitignore' > ./.gitignore
}

但我不想匹配“gitignore”每一个funtction和之间的字符串},因此$ grepfunctions "###"$ grepfunctions "creates"应该输出完全相同的内容。这也是原因、为什么声明 -f 等并不能解决问题

我尝试过的

  • 我不能使用grep
  • 我知道,这sed -n -e '/gitignore-unstaged/,/^}/p' ~/.bashrc会打印出我想要的东西 - 但sed -n -e '/creates/,/^}/p' ~/.bashrc不是。相反,我收到:

        # creates a gitignore file with every file currently not staged/commited.
        # (except the gitingore file itself)
        ### Args: -
    
        git ls-files --others | grep --invert-match '.gitignore' > ./.gitignore
    }
    

    函数名和第一个{都被删掉了,这不是我想要的。

如何打印其中包含特定字符串的任何函数的完整函数声明?当然,除了 sed 之外,其他工具也是允许的。

答案1

请注意,使用zsh,您可以执行以下操作:

 printf '%s() {\n%s\n}\n\n' ${(kv)functions[(R)*gitignore*]}

从当前定义的函数中检索信息(显然不包括注释)。

现在,如果您想从源文件中提取信息,那么除非您实现完整的 shell 解析器,否则您无法可靠地做到这一点。

如果您可以对函数的声明方式做出一些假设,例如,如果您始终使用 ksh 样式的函数定义,并function在行}的开头使用 和 ,则可以这样做:

perl -l -0777 -ne 'for (/^function .*?^\}$/gms) {
  print if /gitignore/}' ~/.bashrc

或者只查看函数体:

perl -l -0777 -ne 'for (/^function .*?^\}$/gms) {
  print if /\{.*gitignore/s}' ~/.bashrc

相关内容