问题:需要以 340039 等开头的所有 IMSI 的列表,这些 IMSI 具有 EPS_PROFILE_ID、MMEFEATURELIST 的组合
输入
<BEGINFILE>
<SUBBEGIN
IMSI=340039XXXXXXXXX;
MSISDN=59995171393;
EPS_PROFILE_ID=1;
PLMNTPLID=1;
SUB_DYN_EPS_ID=1;
MMEHOST=XXXXXXXXXXXXXXXXXXXXXXXXXX.VVV.VV;
MMEREALM=dwcxd.dnhjxcdws.cdnjkcd;
EPS_IMEI=155186158551851658;
EPS_IMEISV=01;
MMEFEATURELIST=ALL_APN;
MMETIMESTAMP=15513535;
S4SGSNTIMESTAMP=0;
HLR_INDEX=1;
LTEAUTOPROV=NO;
MPS=NO;
RELAY=NO;
<SUBEND
<SUBBEGIN
IMSI=340038XXXXXXXXX;
MSISDN=59995171393;
PLMNTPLID=1;
CURRENTNAM=BOTH;
CAT=COMMON;
TBS=TS11&TS12&TS21&TS22&TS61&BS26&BS2G;
VLRLIST=2;
SGSNLIST=2;
<SUBEND
<ENDFILE>
所需输出
IMSI=340039XXXXXXXXX;EPS_PROFILE_ID=1;MMEFEATURELIST=ALL_APN;
答案1
我更喜欢用于perl
这种解析
perl -ne '
$/ = "\n<SUBBEGIN\n"; # Read blocks starting with this pattern
($i) = /\b(IMSI=340039[^;]*)/; # Get IMSI and value
($e) = /\b(EPS_PROFILE_ID=[^;]+)/; # Get EPS_PROFILE_ID and value
($m) = /\b(MMEFEATURELIST=[^;]+)/; # Get MMEFEATURELIST and value
print "$i;$e;$m;\n" if $i && $e && $m; # Print result only if all three items are present
' input_file
您的示例的输出
IMSI=340039XXXXXXXXX;EPS_PROFILE_ID=1;MMEFEATURELIST=ALL_APN;
答案2
使用任何 POSIX awk:
$ cat tst.awk
BEGIN { FS="[[:space:]=]*"; OFS=";" }
/=/ { tag2val[$2] = $3 }
/<SUBEND/ {
if ( (tag2val["IMSI"] ~ /^340039/) &&
("EPS_PROFILE_ID" in tag2val) &&
("MMEFEATURELIST" in tag2val) ) {
print p("IMSI"), p("EPS_PROFILE_ID"), p("MMEFEATURELIST")
}
delete tag2val
}
function p(tag) { return tag "=" tag2val[tag] }
$ awk -f tst.awk file
IMSI=340039XXXXXXXXX;;EPS_PROFILE_ID=1;;MMEFEATURELIST=ALL_APN;
答案3
GNU sed
这是使用扩展正则表达式模式(-E)解决问题的一种方法。
## holds the keys to be printed
var='IMSI EPS_PROFILE_ID MMEFEATURELIST'
sed -En '
1{:1;x;s/.*/ '"$var"' /;x;}
/^<SUBBEGIN$/,/^<SUBEND$/G
/^\s+((\S+)=\S+)\n(.*) \2(\s)/!d
s//\3\n\1\4/
/(.*\n){3}/!{h;d;}
/^\nIMSI=340039/s/\n|\s$//gp
s/.*/<SUBEND/;b1
' file
IMSI=340039XXXXXXXXX;EPS_PROFILE_ID=1;MMEFEATURELIST=ALL_APN;
使用前瞻我们在正则表达式中与断言。
perl -lne '
push(@A, $_)
if my $e = /^<SUBBEGIN$/ ... /^<SUBEND$/;
print($1, $2, $3)
if $e =~ /E0/ && join($/, splice(@A)) =~
m/(?:
(?=$p(IMSI=340039$q))
(?=$p(EPS_PROFILE_ID=$q))
(?=$p(MMEFEATURELIST=$q))
)/xms;
BEGIN {
$q = qr/ (?:(?!;)\S)+; /xms;
$p = qr/ \A.*\n\h* /xms;
}' file
## keys provided as env to awk
s="IMSI EPS_PROFILE_ID MMEFEATURELIST" \
awk -F '^[[:blank:]]+|=' '
BEGIN {
n = split(ENVIRON["s"],a," ")
for (var in a) b[a[var]] = var
}
/^<SUBBEGIN$/,/^<SUBEND$/ {
if ( /=/ && $2 in b) {
h[$2] = $0
sub(FS, "", h[$2])
}
if ( /^<SUBEND$/ ) {
t=$0;$0=""
for (i=1; a[i] in h; i++) $i = h[a[i]]
split("", h, "=")
f = (NF == n) && ($1 ~ /=340039/)
}
}
f;{f=0}
' OFS= file
答案4
awk '/IMSI=340039/&&/EPS_PROFILE_ID/&&/MMEFEATURELIST/' filename