![使用 sed 替换冒号左侧出现的所有破折号](https://linux22.com/image/127407/%E4%BD%BF%E7%94%A8%20sed%20%E6%9B%BF%E6%8D%A2%E5%86%92%E5%8F%B7%E5%B7%A6%E4%BE%A7%E5%87%BA%E7%8E%B0%E7%9A%84%E6%89%80%E6%9C%89%E7%A0%B4%E6%8A%98%E5%8F%B7.png)
我在文件中有以下值config.yml
:
scratch-org-def: config/project-scratch-def.json
assign-permset: false
permset-name:
run-apex-tests: true
apex-test-format: tap
delete-scratch-org: false
show-scratch-org-url: true
我需要将冒号 (:) 左侧出现的所有破折号 (-) 替换为下划线 (_)。
我已经尝试过,sed '/.*: /s/-/_/g' config.yml
但它替换了所有破折号(包括config/project-scratch-def.json
)。
我试过了sed '/^[^:]*:/s/-/_/g' config.yml
,希望能停在冒号处,但效果是一样的。
答案1
$ awk '{ gsub("-", "_", $1) } 1' FS=':' OFS=':' config.yml
scratch_org_def: config/project-scratch-def.json
assign_permset: false
permset_name:
run_apex_tests: true
apex_test_format: tap
delete_scratch_org: false
show_scratch_org_url: true
该awk
脚本将文件读取为一:
组用 - 分隔的字段。它适用gsub()
于每行的第一个字段,将每个破折号更改为下划线。单独的1
缩写{ print }
将打印每个(现已修改的)输入行。
FS=':' OFS=':'
将输入和输出字段分隔符设置为:
。
也可以sed
通过一些非常复杂的正则表达式或利用其保留空间(或两者)来做到这一点,但这不是一个“脱口而出”的解决方案。
(经过一番思考)使用sed
:
$ sed 'h;s/^[^:]*//;x;s/:.*$//;y/-/_/;G;s/\n//' config.yml
scratch_org_def: config/project-scratch-def.json
assign_permset: false
permset_name:
run_apex_tests: true
apex_test_format: tap
delete_scratch_org: false
show_scratch_org_url: true
每一步说明:
h
:将模式空间(当前输入行)复制到保持空间(“通用”缓冲区)。s/^[^:]*//
:
:删除模式空间中第一个之前的所有内容。x
:交换保持空间和模式空间。s/:.*$//
:删除:
模式空间中的 及其后面的所有内容。模式空间现在包含 未修改的左侧
:
,而保持空间包含未修改的右侧,包括:
.y/-/_/
:将模式空间中的所有破折号更改为下划线。G
:将保留空间附加到模式空间的末尾,并在两者之间使用换行符。s/\n//
:删除上一步中的换行符。- (隐式
p
):将模式空间打印到标准输出。
步骤 4 和步骤 5 可以互换,结果不会有任何变化。
简而言之:sed
不是(可能不是)适合这项工作的工具。
答案2
我思考sed
您可以通过替换循环中的破折号来完成此操作,一旦第一个冒号之前的所有内容都不包含破折号,就中断:
sed ':a; /^[^-:]*:/b; s/-/_/;ta'
前任。
$ sed ':a; /^[^-:]*:/b; s/-/_/;ta' config.xml
scratch_org_def: config/project-scratch-def.json
assign_permset: false
permset_name:
run_apex_tests: true
apex_test_format: tap
delete_scratch_org: false
show_scratch_org_url: true
答案3
我通过3步取得了结果
首先,我在保存在 Second_part.txt 文件中的冒号之后分隔了第二部分
第二步我将第一部分分开直到冒号并将“-”替换为“_”并保存在文件first_part_after_relacement中
使用粘贴命令的最后一步我加入了两个文件,从而达到了所需的结果
命令
sed -ne "s/\(.*:\)\(.*\)/\2/p" l.txt > Second_part.txt
sed -ne "s/\(.*:\)\(.*\)/\1/p" l.txt | sed "s/-/_/g" > first_part_after_relacement
paste first_part_after_relacement Second_part.txt | sed -r "s/\s+//g"
输出
scratch_org_def:config/project-scratch-def.json
assign_permset:false
permset_name:
run_apex_tests:true
apex_test_format:tap
delete_scratch_org:false
show_scratch_org_url:true
注意:与之前提供的解决方案相比,多了 2 个步骤