我有一大堆C ++源文件,我希望在其中插入一个简单的函数定义(大约6行)。该定义应该在另一个函数定义之后立即出现。
使用这个问题的接受答案:sed match multiple lines and then append,我可以插入普通的函数定义,但是我无法将其作为相应类的成员范围。
测试代码:
void object::func1()
{
std::cout << "func1" << std::endl;
}
插入非会员功能:
james@scrapyard:~/Projects$ sed '/func1()$/,/^}/!b;/^}/a \\nint func2()\n{\n\ \ \ \ return 0;\n}' func1.cc
void object::func1()
{
std::cout << "func1" << std::endl;
}
int 1::func2()
{
return 0;
}
尝试对类名称进行分组并使用后面的引用,如下所示1::func2
而不是object::func2
。
sed '/\([[:alnum:]]\+\)::func1()$/,/^}/!b;/^}/a \\nint \1::func2()\n{\n\ \ \ \ return 0;\n}' testcode.cc
如果我使用的是substitute命令而不是append命令,那么它会起作用,但是/,/
会破坏substitute命令,导致:
sed: -e expression #1, char 33: unknown option to
s'`
sed可以吗?
答案 0 :(得分:2)
这可能适合你(GNU sed):
sed '/^.* \([^:]*::\)func1()$/{h;x;s//\nint \1func2()\n{\n return 0;\n}/;x};//,/^}$/{/^}$/G}' file
这将查找函数定义,然后在保留空间(HS)中构建普通函数。在遇到函数结束时,它会附加HS。
答案 1 :(得分:1)
反向引用可能仅指同一表达式中的捕获。 !b
结束第一个表达式后的分号。保持空间可以携带从一个表达式到另一个表达式的字符串。
sed '/\w\+::func1()$/,/^}/!b;/\w\+::func1()$/{h;s/^\w*\s\+\(\w\+\)::func1()$/\1/;x};/^}/ {g;s/.*/}\n\nint &::func2()\n{\n\ \ \ \ return 0;\n}/}' testcode.cc
Sed一次读取一行到模式空间,其中s///
之类的命令运行。
可以在保留空间中放置行,稍后将其恢复到模式空间中。
sed '
/\w\+::func1()$/,/^}/!b # Ignore lines outside the target function.
/\w\+::func1()$/ { # On the line declaring the function,
h # save that line to the hold space;
s/^\w*\s\+\(\w\+\)::func1()$/\1/ # replace the function with its class name;
x # save the class name and restore the function declaration.
}
/^}/ { # at the end of the target function
g # retrieve the class name
# substitue the class name into the new function
s/.*/}\n\nint &::func2()\n{\n\ \ \ \ return 0;\n}/
}
' testcode.cc