首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何从awk中选择两列并在它们不匹配时进行打印

如何从awk中选择两列并在它们不匹配时进行打印
EN

Stack Overflow用户
提问于 2019-03-13 13:21:48
回答 3查看 104关注 0票数 3

我需要从OMO帐户迁移日志中选择两个MSISDN值,并打印出不匹配的值。

代码语言:javascript
复制
[2019-03-11 04:15:08 INFO-SUBAPP ESBRestClient:117] ## IP-103.228.158.85##TOKEN-201903110416276787774(**923419606907**)RESPONSE-BODY: {"callStatus":"false","responseCode":"18","description":"OMO account migration – **923481057772**"}

2019-03-11 04:24:02 INFO-SUBAPP ESBRestClient:117 ## IP-119.153.134.128##TOKEN-1552260212780839(923214748517)RESPONSE-BODY:{"callStatus":"false","responseCode":"18","description":"OMO帐号迁移- 953214748517"}

923481057772是旧的MSISDN。

923419606907是新的MSISDN,我需要将其保存到一个新文件中。我正在使用以下命令仅选择新的MSISDN:

代码语言:javascript
复制
cat migration.txt | egrep "OMO account migration" | egrep "responseCode\":\"1700" | awk -F"(" '{gsub(/\).*/,"",$2);print $2}' >>newmsisdn.txt

我正在使用保存的MSISDN值来获取令牌号。然后我将使用这些令牌来获取多个参数。最终输出如下所示:

日期时间旧MSISDN新MSISDN旧配置文件新配置文件CNIC Acc状态Acc状态迁移通道(之前)(之后) 2019-03-11 | 00:00:14 | 923135260528 | 923029403541 | OMO BVS MA |0| 1620221953175 | ACTIVE | subapp

2019-03-11 | 00:00:14 | 923135260528 | 923003026654 | OMO BVS MA |0| 1620221953175 |活动||子应用

2019-03-11 | 00:00:14 | 923135260528 | 923003026654 | OMO BVS MA |0| 1620221953175 |活动||子应用

2019-03-11 | 00:00:14 | 923135260528 | 923038048244 | OMO BVS MA |0| 1620221953175 |活动||子应用

在第二个日志实例中,这两个值是相同的。我需要过滤掉这些,即我只需要使用不匹配的值。如何比较两个不匹配的值并打印新的MSISDN?

EN

回答 3

Stack Overflow用户

发布于 2019-03-13 14:01:35

问题的第一个版本的答案

尝试:

代码语言:javascript
复制
awk -F'[*][*]' '/OMO account migration/ && /responseCode":"18"/ && $2 != $4 { print $2}' migration.txt

这避免了产生多个进程并将它们与管道连接的需要。这使得这种方法相对有效。

它是如何工作的

  • -F'[*][*]'

这会将字段分隔符设置为两颗星。这样,新的MSISDN是字段2,旧的MSISDN是字段4.

  • /OMO account migration/ && /responseCode":"18"/ && $2 != $4 { print $4}

这将为以下行选择:(1)包含正则表达式OMO account migration/ (2)包含正则表达式responseCode":"18" ,并且 (3)的第二个字段与第四个字段不同。对于任何这样的行,将打印第二个字段。

示例

让我们考虑一下这个三行的测试文件:

代码语言:javascript
复制
$ cat migration.txt 
[2019-03-11 04:15:08 INFO-SUBAPP ESBRestClient:117] ## IP-103.228.158.85##TOKEN-201903110416276787774(**923419606907**)RESPONSE-BODY: {"callStatus":"false","responseCode":"18","description":"OMO account migration – **923481057772**"}
[2019-03-11 04:15:08 INFO-SUBAPP ESBRestClient:117] ## IP-103.228.158.85##TOKEN-201903110416276787774(**923419606888**)RESPONSE-BODY: {"callStatus":"false","responseCode":"19","description":"OMO account migration – **923481057999**"}
[2019-03-11 04:15:08 INFO-SUBAPP ESBRestClient:117] ## IP-103.228.158.85##TOKEN-201903110416276787774(**923419606123**)RESPONSE-BODY: {"callStatus":"false","responseCode":"18","description":"OMO account migration – **923419606123**"}

让我们运行我们的命令:

代码语言:javascript
复制
$ awk -F'[*][*]' '/OMO account migration/ && /responseCode":"18"/ && $2 != $4 {print $2}' migration.txt >>newmsisdn.txt

输出文件现在包含一个我们需要的新MSISDN:

代码语言:javascript
复制
$ cat newmsisdn.txt 
923419606907
票数 5
EN

Stack Overflow用户

发布于 2019-03-13 15:55:35

考虑到您的实际Input_file与显示的示例相同,并且您需要为每一行提供新的值,如果是这样的话,请尝试如下所示。

代码语言:javascript
复制
awk '
/OMO account migration/ && /responseCode":"18"/{
  val_old=val_new=""
  match($0,/\*\*[0-9]+\*\*/)
  val_old=substr($0,RSTART,RLENGTH)
  $0=substr($0,RSTART+RLENGTH)
  match($0,/\*\*[0-9]+\*\*/)
  val_new=substr($0,RSTART,RLENGTH)
}
(val_old!=val_new){
  gsub("*","",val_new)
  print val_new
}
'   Input_file

解释:现在为上面的代码添加了详细的解释。

代码语言:javascript
复制
awk '                                                     ##Starting awk program here.
/OMO account migration/ && /responseCode":"18"/{          ##Checking condition if a line contains strings OMO account migration AND responseCode":"18" in it then do following.
  val_old=val_new=""                                      ##Nullifying variables val_old and val_new here.
  match($0,/\*\*[0-9]+\*\*/)                              ##Using match OOTB function of awk to match from **digits** here. If match found then value of RSTART and RLENGTH(awk variables) will be SET.
  val_old=substr($0,RSTART,RLENGTH)                       ##Creating variable val_old which is substring of starting point as RSTART and ending point of RLENGTH here.
  $0=substr($0,RSTART+RLENGTH)                            ##Re-defining value of current line with substring whose value starts after matched regexs next index, so that we can catch new value in next further statements.
  match($0,/\*\*[0-9]+\*\*/)                              ##Using match OOTB function of awk to match from **digits** here. If match found then value of RSTART and RLENGTH(awk variables) will be SET(2nd time run).
  val_new=substr($0,RSTART,RLENGTH)                       ##Creating variable named val_new whose value is substring of current line startpoint is RSTART and ending point is RLENGTH here.
}                                                         ##Closing BLOCK for string matching condition here.
(val_old!=val_new){                                       ##Checking condition ig val_old variable is NOT equal to val_new then do following.
  gsub("*","",val_new)                                    ##Globaly subsituting * in val_new to get exact value as per OP need.
  print val_new                                           ##Printing val_new value here.
}
'  Input_file                                             ##Mentioning Input_file name here.
票数 0
EN

Stack Overflow用户

发布于 2019-03-13 16:33:03

我将采用以下方法:我看到每个MSISDN号码都包含12个数字(0-9),位于两个双星号之间。

你可以使用下面的正则表达式来找到它们:

代码语言:javascript
复制
grep -o "\*\*[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]\*\*"

如果您的系统支持此功能,您可以将其简化为:

代码语言:javascript
复制
grep -o "\*\*[0-9]{12}\*\*"

一旦你有了这些,你就可以使用awk来显示那些不同的东西,比如:

代码语言:javascript
复制
'{IF ($1 != $2) PRINT $1 $2}' (not tested).
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/55134913

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档