我想将以下多个awk命令组合成一个awk程序:
awk -F 'FS' '{ $1 = ($1 == "}" ? "" : $1) } 1' sorce > destfil
awk -F 'FS' '{ $3 = ($3 == "]" ? "" : $3) } 1' sorce > destfil
awk -F 'FS' '{ $5 = ($5 == "}" ? "}," : $5) } 1' sorce > destfil
我尝试使用&&
完成此操作,但结果不是我期望的。
awk -F 'FS' '{ $1 = ($1 == "}" ? "" : $1) && $3 = ($3 == "]" ? "" : $3) && $5 = ($5 == "}" ? "}," : $5) } 1' sorce > destfil
输出中似乎有各种零。
问题:
谢谢!
@ RavinderSingh13,当我尝试您的代码时,请按照以下示例输入文件和输出文件
[user@restt]$ tail source
{
}
]
}
{
" e t
{
}
]
}
[user@test]$ awk -F 'FS' '{$1=($1=="}"?"":$1); $3=($3=="]" ? "" : $3) ; $5=($5=="}" ? "}," :$5);} 1' source > target
[user@test]$ tail target
{
}
]
}
{
" e t
{
}
]
}
我认为问题与字段分隔符-F'FS'有关,或者我不确定。
@kvantour,在下面,我给出了示例输入文件,并命令我正在运行什么,我正在获得什么输出以及我需要什么。
源文件内容:
{
"metadata": [
{
sample content line 1
sample content line n
}
]
}
{
"metadata": [
{
sample content line 1
sample content line n
}
]
}
{
"metadata": [
{
sample content line 1
sample content line n
}
]
}
{
"metadata": [
{
sample content line 1
sample content line n
}
]
}
我正在运行的命令
$ awk '($1=="}"){$1="First Column"}
($3=="]"){$3="third Column"}
($5=="}"){$5="Fifth Column"}
{$1=$1}1' sample.json > out
我得到的输出:
[root@centos-src ~]# cat out
{
"metadata": [
{
sample content line 1
sample content line n
First Column
]
First Column
{
"metadata": [
{
sample content line 1
sample content line n
First Column
]
First Column
{
"metadata": [
{
sample content line 1
sample content line n
First Column
]
First Column
{
"metadata": [
{
sample content line 1
sample content line n
First Column
]
First Column
但是我期望输出是:
{
"metadata": [
{
sample content line 1
sample content line n
Fifth Column
third Column
First Column
{
"metadata": [
{
sample content line 1
sample content line n
Fifth Column
third Column
First Column
{
"metadata": [
{
sample content line 1
sample content line n
Fifth Column
third Column
First Column
{
"metadata": [
{
sample content line 1
sample content line n
Fifth Column
third Column
First Column
答案 0 :(得分:2)
在一个不错的awk结构中,可以这样写:
awk -F 'FS' '($1=="}"){$1=""}
($3=="]"){$3=""}
($5=="}"){$5="},"}
{$1=$1}1' <file>
我将$1=$1
添加到列表中的原因是,在上述条件均不满足的情况下,为了正确的$0
重新处理OFS
。如果不这样做,则将行打印为FS
作为行分隔符,而其他行则打印为OFS
。
那你为什么要得到一堆零?
让我们看看你的单线纸:
$1 = ($1 == "}" ? "" : $1) && $3 = ($3 == "]" ? "" : $3) && $5 = ($5 == "}" ? "}," : $5)
并通过假设括号之间的三元运算符返回变量来简化它。因此我们可以将其重写为:
$1 = var1 && $3 = var3 && $5 = var5
考虑到以下因素:
expr1 && expr2
的优先级高于value = expr
。 lvalue = expr
返回expr的值我们可以看到awk将其解释为
$1 = var1 && ($3 = (var3 && ($5 = var5) ) )
因此结果将是:
$5 = var5
$3 = var3 && $5 equalling var3 && var5
$1 = var1 && $3 equalling var1 && var5
在以下示例中可见:
$ echo "a b c d e f" | awk '{ $1="p" && $3 = "q" && $5 = "r"}1'
1 b 1 d rf
最后,在awk
中,一个空字符串和一个数字零具有逻辑值 false 和其他任何 true 。因此,由于您的两个原始三元运算符 可以返回空字符串,因此它们将确保逻辑AND将返回false,这等于数字0。因此,如果原始$1
等于$3
$3
和]
都将与零匹配。
您试图实现的目标并不那么容易。首先,您似乎假设列号暗含了该行中的字符号。不幸的是事实并非如此。在默认模式下,Awk假定字段$n
是该行中的第n
个单词,其中单词是不包含任何空格的字符序列。因此,在以下文本中,
}
]
}
$1
实际上引用了所有字符。
在假设您的JSON文件完全缩进的情况下,可以使用以下内容:
awk '/^} *$/{$0="First Column"}
/^ ] *$/{$0=" Thrid Column"}
/^ } *$/{$0=" Fifth Column"}
{print $0}' <file>
但是,如果您的JSON文件没有统一缩进,则情况会变得很混乱。最简单的方法是首先将jq
解析为
jq . <json-file> | awk ...
答案 1 :(得分:1)
这是您要尝试做的吗(给定source
输入文件)?
$ awk '
BEGIN{ FS="[ ]"; map[1,"}"]=map[3,"]"]=map[5,"}"]="" }
{ for (i=1;i<=NF;i++) $i=((i,$i) in map ? map[i,$i] : $i); print }
' file
{
{
" e t
{
答案 2 :(得分:0)
由于您没有显示示例Input_file,因此无法对其进行测试,请您尝试以下操作。
awk -F 'FS' '{$1=($1=="}"?"":$1);$3=($3=="]"?"":$3);$5=($5=="}"?"":$5);} 1' sorce > destfil
答案 3 :(得分:0)
使用;
分隔语句:
awk ... '{ $1 = ($1 == "}" ? "" : $1); $3 = ($3 == "]" ? "" : $3); $5 = ($5 == "}" ? "}," : $5); } 1' ...