使用PowerShell将行与CSV中的下一行进行比较

时间:2016-11-11 23:05:58

标签: powershell csv foreach comparison

我有一个包含信息行的csv文件。一行将告诉我它在做什么,下一行将告诉我它做了什么。如果它没有做任何事情,它就不会有下一行。我想过滤掉那些没有做任何事情的行。因此,如果它缺少下一行,请离开那里,如果它有,请将其删除。以下是CSV的示例。

Event
Recipient Disposition: 1
Message Disposition: 1
Recipient Disposition: 2
Recipient Disposition: 3
Message Disposition: 3
Recipient Disposition: 4
Recipient Disposition: 5
Message Disposition: 5
Recipient Disposition: 6
Message Disposition: 6

我希望仅Recipient Disposition: 2Recipient Disposition: 4已过滤,其他已删除。

PowerShell中的任何想法?

2 个答案:

答案 0 :(得分:1)

你的例子是否正确?从解释中不应该留下1,3,5和6?

无论哪种方式,您可以使用的一种方法是使用Select-String和正则表达式从文件中选择所需的行。通过添加Context选项,您还可以选择下一行。将其导入Where-Object对象,并使用一些逻辑来过滤掉您不想要的对象。像这样:

Select-String .\your_file.txt -Pattern '^Recipient' -Context 0, 1 | ? {
    ($_.Context.PostContext -split ':\s*')[1] -eq ($_.Line -split ':\s*')[1]
} | Select line

这将产生以下输出:

Line
----
Recipient Disposition: 1
Recipient Disposition: 3
Recipient Disposition: 5
Recipient Disposition: 6

答案 1 :(得分:0)

重度已修改以更好地解释脚本

这个脚本反过来做了。它存储最后一行并与当前行进行比较。 switch命令充当Ìf this than that调度程序。如果当前行以Recipient If开头,以检查最后一行是否也开始执行,如果为真,则输出最后一行,因为那样没有Messae跟随的那一行。在cas the curr。行开始于消息没有完成。如果是其他任何东西(默认),则输出该行,就像第一行的情况一样。

$lines = Get-Content Test.csv
Foreach ($line in $lines) {
   switch -wildcard ($line) {
     "Recipient*"  {If ($last -match "^Recipient"){$last}}
     "Message*"    {}
     default       {$line}
  }
  $last = $line
}

将显示此输出:

Event
Recipient Disposition: 2
Recipient Disposition: 4
Recipient Disposition: [554 Denied - Denied by (Mode: normal); Mode: ; Queued: no]
Recipient Disposition: [554 Denied - Denied by (Mode: normal); Mode: ; Queued: no]