我有一个包含文本和数字的文件,如下所示:
state(1, s(1,a), [s(1,b)]).
state(1, s(1,b), [s(1,a)]).
state(1, s(2,a), [s(2,b)]).
state(1, s(2,b), [s(2,a)]).
state(1, s(3,a), [s(3,b)]).
state(1, s(3,b), [s(3,a)]).
state(1, s(4,a), [t(1), t(2)]).
state(1, s(5,a), [t(1), t(3)]).
state(1, s(6,a), [s(6,b)]).
state(1, s(6,b), [s(6,a)]).
...so on
我希望 s(x,y) 中的编号更改如下:
state(1, p(1), 0, [p(2)]).
state(1, p(2), 0, [p(1)]).
state(1, p(3), 0, [p(4)]).
state(1, p(4), 0, [p(3)]).
state(1, p(5), 0, [p(6)]).
state(1, p(6), 0, [p(5)]).
state(1, p(7), -1, [t(1), t(2)]).
state(1, p(8), -1, [t(1), t(3)]).
state(1, p(9), 0, [p(10)]).
state(1, p(10), 0, [p(9)]).
...so on
状态中第三个参数中的 0 和 -1 只是表明存在/存在 ss(或 pp)连接(表示为 0)或不存在(表示为 -1)。
我尝试了“sed”,但我根本没有成功。
我可以获得一些提示或解决方案吗?
答案1
gawk -F'(,[[:blank:]]+\\[?|\\]\\)\\.)' '!twice{ seen[$2]=NR; next } {
print $1, "p(" FNR ")", (($3 in seen)?"0, [p("seen[$3]")":"-1, ["$3", "$4)"]).";
}' OFS=', ' infile twice=1 infile
我们将字段分隔符定义为,<one-or-more-whitespaces><with-optional-]>
or的集合]).
我们正在处理输入文件infile
两次,因此首先我们根据上面设置的 FS 读取第二个字段并将它们添加到关联的seen
命名数组中;该数组的键是第二个字段内容,每个值是 NR(NR
在 awk 中表示氮数量右输入的记录FNR
是相同的,但会为每个下一个输入文件重置);重复此循环,直到所有行读取并完成。变量twice=1
和条件!twice
用于强制 awk 仅运行第一个块一次,并且第一次我们仅处理输入文件。
该行print
用于第二次运行并处理输入文件;我们打印第一个字段,然后p(#)
(其中#
s 由 FNR 再现);然后我们对照数组中的所有键检查第三个字段seen
,如果在数组中找到匹配项,则打印0, [p(#)]).
(其中#
是在数组中看到匹配键值的位置号),否则打印-1, [...]).
答案2
我们将输入文件称为“sample.txt”
我们首先需要将 0 和 -1 位放入文件中:
cat sample.txt | sed 's/, \[s/, 0, \[s/g' | sed 's/, \[t/, -1, \[t/g' > sample1.txt
一旦我们有了新的“sample1.txt”文件,我们就可以运行以下 bash 脚本 (convert.bash)。
#!/bin/bash
k=0
maxstates=$(wc -l "$1" | gawk '{print $1}')
for i in $(seq 1 "$maxstates")
do
count=$(grep -c "s($i,a)" "$1")
if [ "$count" -ne 0 ]
then
k=$((k + 1))
sed -i "s/s($i,a)/p($k)/g" "$1"
fi
count=$(grep -c "s($i,b)" "$1")
if [ "$count" -ne 0 ]
then
k=$((k + 1))
sed -i "s/s($i,b)/p($k)/g" "$1"
fi
done
现在,运行该文件:
bash convert.bash sample1.txt
它就地编辑了sample1.txt,新内容是:
state(1, p(1), 0, [p(2)]).
state(1, p(2), 0, [p(1)]).
state(1, p(3), 0, [p(4)]).
state(1, p(4), 0, [p(3)]).
state(1, p(5), 0, [p(6)]).
state(1, p(6), 0, [p(5)]).
state(1, p(7), -1, [t(1), t(2)]).
state(1, p(8), -1, [t(1), t(3)]).
state(1, p(9), 0, [p(10)]).
state(1, p(10), 0, [p(9)]).