我想找到文件中以“_DB”结尾的所有函数声明,并避免perl
和管道。
例如:
prep_DB();
init_DB(DB *database, char *params[])
{
open_DB(database);
}
prep_DB() {
open_DB(database); // open
}
FILE * load_DB(const char * exppath, const char * expfname)
{}
应该只匹配第二行和倒数第二行。该线prep_DB() {
可以存在或不存在。
目前,以下命令可查找所有函数调用:
grep -E '.*_DB(.*)' file
然而,我在否定最后的分号时遇到了麻烦。最接近解释其工作原理的线程是这;然而,分号似乎是一个特殊字符,因为那里的建议不起作用。我怎样才能绕过这个限制?
答案1
假设这是一个名为file.c
.
使用ctags
:
$ ctags file.c
这将创建一个名为的文件tags
:
$ cat tags
init_DB file.c /^init_DB(DB *database, char *params[])$/
load_DB file.c /^FILE * load_DB(const char * exppath, const char * /
prep_DB file.c /^prep_DB() {$/
这可以与函数定义一起使用vi
或vim
自动跳转到函数定义。
您还可以使用cut
and解析此文件grep
:
$ cut -f 1 tags | grep '_DB$'
init_DB
load_DB
prep_DB
在 Ubuntu 系统上,安装ctags
实际上会exuberant-ctags
提供更详细的tags
输出:
$ cat tags
!_TAG_FILE_FORMAT 2 /extended format; --format=1 will not append ;" to lines/
!_TAG_FILE_SORTED 1 /0=unsorted, 1=sorted, 2=foldcase/
!_TAG_PROGRAM_AUTHOR Darren Hiebert /[email protected]/
!_TAG_PROGRAM_NAME Exuberant Ctags //
!_TAG_PROGRAM_URL http://ctags.sourceforge.net /official site/
!_TAG_PROGRAM_VERSION 5.9~svn20110310 //
init_DB file.c /^init_DB(DB *database, char *params[])$/;" f
load_DB file.c /^FILE * load_DB(const char * exppath, const char * expfname)$/;" f
prep_DB file.c /^prep_DB() {$/;" f
在这里我们可以确保只获得函数定义
$ awk '$NF == "f" && $1 ~ /_DB$/ { print $1 }' tags
init_DB
load_DB
prep_DB
这里的要点是,最好使用专用的 C 语言解析器,而不是尝试在解析 C 代码的awk
脚本或正则表达式中考虑所有可能的编程风格。grep
你也可以做
$ ctags -x file.c
init_DB function 3 file.c init_DB(DB *database, char *params[])
load_DB function 12 file.c FILE * load_DB(const char * exppath, const char * expfname)
prep_DB function 8 file.c prep_DB() {
然后以您需要的任何方式解析/过滤它。该数字是定义的行号。这一切都取决于您所说的“想要找到”的含义。
答案2
我决定发布上面 20 多条评论讨论的摘要。
@don_crissti 提供了一种解决方案,他建议使用以下命令:
$ grep -E '.*_DB([^;]*)$' <filename>
产生输出
init_DB(DB *database, char *params[])
prep_DB() {
FILE * load_DB(const char * exppath, const char * expfname)
根据他的建议,如果需要,我想出了以下命令来排除中间结果:
$ grep -E '_DB\(.*\)$' <filename>