我得到一个包含很多行的文件,如下所示:
Vinh Tranh:438-910-7449:8235 Maple Street, Wilmington, VM 29085:9/23/63:68900
我需要将顺序从名字姓氏更改为姓氏,名字。我已经走到这一步了,但仍然是错误的:
sed -e "s/\([^ ]*\) *\(^ ]*\)/\2 \1 /g" datebook
但它输出为
Tranh:438-910-7449:8235 Vinh Maple Street...
代替
Tranh, Vinh:438-910...
答案1
编辑:我误解了原来的问题,没有看到它使用了几乎正确的 BRE 语法。那是说...
您的正则表达式有一些问题:
- 您的第二个捕获组缺少 a
[
(尽管这可能只是一个转录问题,因为您发布了一些没有 this 就无法获得的输出[
)。 - 要仅将第二个单词与第二个捕获组匹配,您可能希望匹配第一个冒号之前的最后一个字符 - 即您想
:
从第二个捕获组中排除。 - 您不需要最终
g
标志,因为您只对第一场比赛感兴趣。如果包含它,sed
也会尝试将您的表达式与该行的其余部分相匹配,可能会打乱它。
附带说明:由于您sed
只给出了两个非选项参数,因此该-e
选项不是必需的;第一个非选项参数将被视为要解释的脚本。
命令的修改版本:
sed -e "s/\([^ ]*\) *\([^ :]*\)/\2, \1/"
(我删除了反向引用后面的空格\1
,并在后面添加了一个逗号,\2
以使其与您提供的示例输出匹配)。
应用于原始文本时给出的结果:
$ echo "Vinh Tranh:438-910-7449:8235 Maple Street, Wilmington, VM 29085:9/23/63:68900" |
sed -e "s/\([^ ]*\) *\([^ :]*\)/\2, \1/"
Tranh, Vinh:438-910-7449:8235 Maple Street, Wilmington, VM 29085:9/23/63:68900
答案2
我相信这会起作用,
sed 's?^\([[:alpha:]]\{1,\}\)[[:blank:]]\([[:alpha:]]\{1,\}\)?\2, \1?g'
在哪里,
- SED 分隔符 ->
?
(您可以替换为/
,:
等) - POSIX 类 ->
[:alpha:]
=[A-Za-z]
(按字母顺序) - POSIX 类 ->
[:blank:]
=[\s\t]
(空格和制表符) - 至少一个或多个->
{1,}
- 第一组 ->
\([[:alpha:]]\{1,\}\)
- 第二组 ->
\([[:alpha:]]\{1,\}\)
[arif@arif test]$ echo "Vinh Tranh:438-910-7449:8235 Maple Street, Wilmington, VM 29085:9/23/63:68900" | sed 's?^\([[:alpha:]]\{1,\}\)[[:blank:]]\([[:alpha:]]\{1,\}\)?\2, \1?'
Tranh, Vinh:438-910-7449:8235 Maple Street, Wilmington, VM 29085:9/23/63:68900
答案3
$ echo "Vinh Tranh:438-910-7449:8235 Maple Street, Wilmington, VM 29085:9/23/63:68900"| sed 's/:/ /1'| awk '{$30=$1;$1=$2;$2=$30;print $0}'| sed "s/ /,/1"| sed "s/ /:/1"
Tranh,Vinh:438-910-7449:8235 Maple Street, Wilmington, VM 29085:9/23/63:68900 Vinh