使用awk或sed根据模式匹配添加一条线
A有一个包含SQL迁移命令的文件。比如说使用awk或sed根据模式匹配添加一条线,awk,sed,find-replace,Awk,Sed,Find Replace,A有一个包含SQL迁移命令的文件。比如说 // admin_setting $this->createTable('{{%admin_setting}}', [ 'setting_id' => Schema::TYPE_INTEGER . "(11) NOT NULL AUTO_INCREMENT", 'short_description' => Schema::TYPE_STRING . "(255) NOT NULL", 'value' =>
// admin_setting
$this->createTable('{{%admin_setting}}', [
'setting_id' => Schema::TYPE_INTEGER . "(11) NOT NULL AUTO_INCREMENT",
'short_description' => Schema::TYPE_STRING . "(255) NOT NULL",
'value' => Schema::TYPE_TEXT . " NULL",
'PRIMARY KEY (setting_id)',
], $this->tableOptions);
// authorization
$this->createTable('{{%authorization}}', [
'authorization_id' => Schema::TYPE_INTEGER . "(11) NOT NULL AUTO_INCREMENT",
'short_description' => Schema::TYPE_STRING . "(255) NULL",
'PRIMARY KEY (authorization_id)',
], $this->tableOptions);
我想在包含“createTable()命令”的行之前添加另一个命令,以便我的示例文件如下所示:-
// admin_setting
$this->dropTable('{{%admin_setting}}');
$this->createTable('{{%admin_setting}}', [
'setting_id' => Schema::TYPE_INTEGER . "(11) NOT NULL AUTO_INCREMENT",
'short_description' => Schema::TYPE_STRING . "(255) NOT NULL",
'value' => Schema::TYPE_TEXT . " NULL",
'PRIMARY KEY (setting_id)',
], $this->tableOptions);
// authorization
$this->dropTable('{{%authorization}}');
$this->createTable('{{%authorization}}', [
'authorization_id' => Schema::TYPE_INTEGER . "(11) NOT NULL AUTO_INCREMENT",
'short_description' => Schema::TYPE_STRING . "(255) NULL",
'PRIMARY KEY (authorization_id)',
], $this->tableOptions);
我看到了很多删除与模式匹配的行的示例,但到目前为止,没有一个可以让我得到上述更改
最近的一次是
awk '/createTable/{print "$this->DropTable();"}1' file
但我无法填写括号内的内容。这可能适合您(GNU-sed):
复制包含createTable
的行,然后在第一次出现时附加复制的行和模式匹配并替换。这可能适用于您(GNU-sed):
复制包含
createTable
的行,然后在第一次出现时附加复制的行和模式匹配并替换。您可以在awk
中使用字段分隔符。将其设置为单引号,您可以访问字段2中的所需值:
awk -F"'" '/createTable/{print "$this->dropTable('\''"$2"'\'');"}1'
sed的s
也可用于:
sed 's/\$this->createTable(\('\''[^'\'']*'\''\)/$this->dropTable(\1);\n\0/'
转义单引号有点棘手。或者,您可以用双引号括住命令,但是,在这种情况下,您需要注意防止shell解释$
:
sed "s/\\\$this->createTable(\('[^']*'\)/\$this->dropTable(\1);\n\0/"
您可以在
awk
中使用字段分隔符。将其设置为单引号,可以访问字段2中的所需值:
awk -F"'" '/createTable/{print "$this->dropTable('\''"$2"'\'');"}1'
sed的s
也可用于:
sed 's/\$this->createTable(\('\''[^'\'']*'\''\)/$this->dropTable(\1);\n\0/'
转义单引号有点棘手。或者,您可以用双引号括住命令,但是,在这种情况下,您需要注意防止shell解释$
:
sed "s/\\\$this->createTable(\('[^']*'\)/\$this->dropTable(\1);\n\0/"
GNU awk解决方案:
/createTable/ {
match ($0, /createTable\('(.*)',/, x)
print "$this->dropTable('" x[1] "');"
}
{
print $0
}
编辑:使用建议,注意这是GNU awk,并从第一个块tks中删除了不需要的打印
注意:我认为整个{print$0}可能会被“1”(单个字符“1”)取代,但我认为可读性比这里的简短要好。GNU awk解决方案:
/createTable/ {
match ($0, /createTable\('(.*)',/, x)
print "$this->dropTable('" x[1] "');"
}
{
print $0
}
$ cat tst.awk
{ new = $0 }
sub(/createTable/,"dropTable",new) {
sub(/,.*/,");",new)
print new
}
{ print }
$ awk -f tst.awk file
// admin_setting
$this->dropTable('{{%admin_setting}}');
$this->createTable('{{%admin_setting}}', [
'setting_id' => Schema::TYPE_INTEGER . "(11) NOT NULL AUTO_INCREMENT",
'short_description' => Schema::TYPE_STRING . "(255) NOT NULL",
'value' => Schema::TYPE_TEXT . " NULL",
'PRIMARY KEY (setting_id)',
], $this->tableOptions);
// authorization
$this->dropTable('{{%authorization}}');
$this->createTable('{{%authorization}}', [
'authorization_id' => Schema::TYPE_INTEGER . "(11) NOT NULL AUTO_INCREMENT",
'short_description' => Schema::TYPE_STRING . "(255) NULL",
'PRIMARY KEY (authorization_id)',
], $this->tableOptions);
编辑:使用建议,注意这是GNU awk,并从第一个块tks中删除了不需要的打印
注意:我认为整个{print$0}可能会被“1”(单个字符“1”)所取代,但我认为这里的可读性比简短要好。对我来说效果很好。您介意花点时间解释h;G参数吗。@crafter使用
h
命令将当前行复制到称为保持空间(HS)的寄存器中。使用G
命令将HS的内容附加到模式空间(PS)中,模式空间是保存当前行的寄存器。请参阅。这对我来说非常有用。您是否介意花时间解释h;G参数。@crafter使用h
命令将当前行复制到一个称为保持空间(HS)的寄存器中.G命令将HS的内容附加到模式空间(PS)中,后者是保存当前行的寄存器。请参阅。两者都应该工作。它们只是在使用单引号或双引号方面有所不同。使用单引号版本,而不是跳入和跳出shell(顺便说一句,这就是您要做的,不是跳出单引号)只要在需要单个报价的任何地方使用转义序列\047
,例如打印“$this->dropTable(\047”$2”\047);“
。在这种情况下,您也可以使用print”$this->dropTable(“FS$2fs”);“
。两者都应该有效。它们只是在单引号或双引号的使用上有所不同。使用单引号版本,而不是跳进和跳出shell(顺便说一句,这就是你要做的,不是转义单引号),只要在你想要单引号的任何地方使用转义序列就可以了,例如,打印“$this->dropTable(\047”$2”\047);“
。在这种情况下,您也可以使用print”$this->dropTable(“FS$2fs”);“
。请注意,这需要GNU awk用于三参数匹配()函数干式:从第一个块中删除print$0;next
。注意,这需要GNU awk用于三参数匹配()函数干式:从第一个块中删除print$0;next
$ cat tst.awk
{ new = $0 }
sub(/createTable/,"dropTable",new) {
sub(/,.*/,");",new)
print new
}
{ print }
$ awk -f tst.awk file
// admin_setting
$this->dropTable('{{%admin_setting}}');
$this->createTable('{{%admin_setting}}', [
'setting_id' => Schema::TYPE_INTEGER . "(11) NOT NULL AUTO_INCREMENT",
'short_description' => Schema::TYPE_STRING . "(255) NOT NULL",
'value' => Schema::TYPE_TEXT . " NULL",
'PRIMARY KEY (setting_id)',
], $this->tableOptions);
// authorization
$this->dropTable('{{%authorization}}');
$this->createTable('{{%authorization}}', [
'authorization_id' => Schema::TYPE_INTEGER . "(11) NOT NULL AUTO_INCREMENT",
'short_description' => Schema::TYPE_STRING . "(255) NULL",
'PRIMARY KEY (authorization_id)',
], $this->tableOptions);