在 VI 中搜索和替换

在 VI 中搜索和替换

我需要将下面字符串中的“12.22.54”转换为“12:22:54”,以便它在 MS SQL 中工作。

cast('14-JAN-14 06.65.22 AM' as datetime),'63.124.79.253');
cast('14-JAN-14 12.22.36 AM' as datetime),'63.124.79.253');
cast('14-JAN-14 22.13.54 AM' as datetime),'63.124.79.253');

我尝试在 vi 中打开文件并替换

:s/(\d\{2\})\.(\d\{2\}z)\.(\d\{2\})/$1:$2:$3/g

但它不起作用。请帮忙。

答案1

为了避免使用 IP 地址,我只是在匹配的字符串周围放置了空格:

:%s/ \(\d\d\)\.\(\d\d\)\.\(\d\d\) / \1:\2:\3 /g

答案2

vi不使用 perl 风格的正则表达式。你写道

:s/(\d\{2\})\.(\d\{2\}z)\.(\d\{2\})/$1:$2:$3/g

vi使用这样的语法(vim 和 vile accept \d,但你说“六”):

:s/\([[:digit:]]\{2\}\)\.\([[:digit:]]\{2\}\)\.\([[:digit:]]\{2\}\)/\1:\2:\3/g

(“z”从哪里来的?)。

重点是,Perl 所称的“弃用”是 POSIX 的反向引用语法。当然,只要 Larry Wall 在,Perl 就永远不会标准化。

根据评论,原作者的意图是更改所有行。在 vi 中,这是使用特殊范围完成的%

:%s/\([[:digit:]]\{2\}\)\.\([[:digit:]]\{2\}\)\.\([[:digit:]]\{2\}\)/\1:\2:\3/g

也可以明确使用范围($POSIX 也是):

:1,$s/\([[:digit:]]\{2\}\)\.\([[:digit:]]\{2\}\)\.\([[:digit:]]\{2\}\)/\1:\2:\3/g

还有其他方法可以构造边界以避免 IP 地址。但对于给出的示例,空白就足够了:

:s/ \([[:digit:]]\{2\}\)\.\([[:digit:]]\{2\}\)\.\([[:digit:]]\{2\}\) / \1:\2:\3 /g

同样地,vim卑鄙接受\s空格,但 POSIX 只接受文字空格(如图所示)或字符类[:space:]。大多数人觉得输入[spacetab]比输入麻烦少[[:space:]]

如上所述,如果您说“vi”,其他人可能会选择根据标准 (POSIX) 行为来回答。一些可以代替“vi”使用的编辑器提供了正则表达式语法的扩展。快速检查显示猫王还支持 Perl 风格,\d同时\s韋萊(四个中最符合标准的)则不然。

相关内容