我有一个变量包含多行文件的内容。该变量由多个命令(awk
,sed
,...)解析,这些命令充当变量的过滤器和后处理器。
echo "$variable" | awk1 | sed1 | awk2
问题不在于处理本身,而在于我在流程中修改行,丢失了对变量原始值的跟踪。问题是最终的awk
进行了条件检查,根据结果返回原始变量。这就是我的问题所在。
我假设在echo之后用原始行创建这个变量是个好主意,但是我在以下子shell中继承它的任何尝试都让我失望了。解决方案必须是便携式的(符合POSIX标准)
变量格式:
John Smith - - [21/Mar/2017:09:24:33 +0100] Physics
Adam Miller - - [22/Feb/2019:09:24:33 +0100] Chemistry
我想比较此文件中的日期与YYYYMMDDHHMMSS
格式的给定日期(例如20180101151515),如果一行包含日期,我想打印整行。
我的代码到目前为止:
date_after="19960101151515"
process=$(echo "$variable" |awk -F' - - ' '{print $2}' | sed "s/Jan/01/; s/Feb/02/;
s/Mar/03/; s/Apr/04/; s/May/05/; s/Jun/06/; s/Jul/07/;
s/Aug/08/; s/Sep/09/; s/Oct/10/; s/Nov/11/; s/Dec/12/" | awk -F'[/:\\[ ]' -v date="$date_after" '{b=$4$3$2$5$6$7; if (b > date) {print $0}}')
任何sed
,awk
,grep
,cut
,......的组合都可以用一个awk
代替。这也允许您存储原始数据并根据条件返回。您可以很容易地看到以下awk
进行您感兴趣的转换(首先是awk和sed)
awk '{ t=$0
match(t,"\\["); t=substr(t,RSTART+1)
match(t," ") ; t=substr(t,1,RSTART-1); split(t,a,"[/:]")
day=a[1]; year=a[3]; hhmmss=a[4]a[5]a[6];
month=sprintf("%02d",(match("JanFebMarAprMayJunJulAugSepOctNovDec",a[2])+2)/3)
print year month day hhmmss, t}'
所以现在你可以插入你的条件t
并返回原来的$0
,如果需要:
awk -v d="$date_after" '
{ t=$0
match(t,"\\["); t=substr(t,RSTART+1)
match(t," ") ; t=substr(t,1,RSTART-1); split(t,a,"[/:]")
day=a[1]; year=a[3]; hhmmss=a[4]a[5]a[6];
month=sprintf("%02d",(match("JanFebMarAprMayJunJulAugSepOctNovDec",a[2])+2)/3)
}
(t > d) { print $0 }'