Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/powershell/11.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
使用Powershell比较两个文件,然后仅输出不同的字符串名称_Powershell - Fatal编程技术网

使用Powershell比较两个文件,然后仅输出不同的字符串名称

使用Powershell比较两个文件,然后仅输出不同的字符串名称,powershell,Powershell,因此,我是Powershell的完全初学者,但需要编写一个脚本,将一个文件与另一个文件进行比较,并告诉我第一个文件与第二个文件中的字符串有什么不同。我尝试过这一点,但我正在努力处理输出,因为我的脚本目前只会告诉我哪一行的内容不同,但它似乎也会计算空的行 为了给我试图实现的目标提供一些上下文,我希望有一个已知良好Windows进程的静态文件($Authorized),我希望我的脚本提取当前正在运行的进程列表,按进程名称列进行筛选,以便只提取进程名称字符串,然后匹配超过1个字符的任何内容,按唯一值对

因此,我是Powershell的完全初学者,但需要编写一个脚本,将一个文件与另一个文件进行比较,并告诉我第一个文件与第二个文件中的字符串有什么不同。我尝试过这一点,但我正在努力处理输出,因为我的脚本目前只会告诉我哪一行的内容不同,但它似乎也会计算空的行

为了给我试图实现的目标提供一些上下文,我希望有一个已知良好Windows进程的静态文件($Authorized),我希望我的脚本提取当前正在运行的进程列表,按进程名称列进行筛选,以便只提取进程名称字符串,然后匹配超过1个字符的任何内容,按唯一值对文件进行排序,然后将其与$Authorized进行比较,最后输出$processs中的不同进程字符串(到ISE输出窗格),或者仅将不同的进程名称输出到文件

今天,我在Powershell ISE中尝试了以下内容,并在谷歌上搜索,试图找到解决方案。我听说“fc”是一个更好的选择,而不是比较对象,但我无法让它工作。到目前为止,我已经设法让它工作,但在最后一部分,它比较了两个文件,它似乎是逐行比较的,因为它总是给我错误的肯定,因为所提供的文件中进程名称的行位置会发生变化,而且我只想看到更改的进程名称,而不是它报告的行号(“第34行的过程是一个异常值”是当前输出的)

我希望这是有意义的,对此的任何帮助都将不胜感激

Get-Process | Format-Table -Wrap -Autosize -Property ProcessName | Outfile c:\users\me\Desktop\Processes.txt    
$Processes = 'c:\Users\me\Desktop\Processes.txt'
$Output_file = 'c:\Users\me\Desktop\Extracted.txt'
$Sorted = 'c:\Users\me\Desktop\Sorted.txt'
$Authorized = 'c:\Users\me\Desktop\Authorized.txt'
$regex = '.{1,}'
select-string -Path $Processes -Pattern $regex |% { $_.Matches } |% { $_.Value } > $Output_file
Get-Content $Output_file | Sort-Object -Unique > $Sorted
$dif = Compare-Object -ReferenceObject $(Get-Content $Sorted) -DifferenceObject $(get-content $Authorized) -IncludeEqual 
$lineNumber = 1
foreach ($difference in $dif)
{
if ($difference.SideIndicator -ne "==") 
{
Write-Output "The Process at Line $linenumber is an Outlier"
}
$lineNumber ++
}
Remove-Item c:\Users\me\Desktop\Processes.txt
Remove-Item c:\Users\me\Desktop\Extracted.txt
Write-Output "The Results are Stored in $Sorted"

从你剧本的长度和复杂性来看,我觉得我遗漏了什么,但你的描述似乎很清楚

  • 正在运行的进程名称:
    • $ProcessNames=@(获取进程|选择对象-扩展属性名)
    • 。。其中不为空:
      $ProcessNames=$ProcessNames | Where Object{$\ ne'}
  • 文件中的授权名称列表:
    • $AuthorizedNames=Get Content'c:\Users\me\Desktop\Authorized.txt'
  • 比较:
    • $UnAuthorizedNames=$ProcessNames |其中对象{$\不在$AuthorizedNames}
  • 文件的可选输出:
    • $UnAuthorizedNames | Set Content out.txt
  • 或者在外壳中:

    @(gps).Name -ne '' |? { $_ -notin (gc authorized.txt) } | sc out.txt
    
    1  2    3     4     5        6      7                      8
    
    1. @() forces something to be an array, even if it only returns one thing
    2. gps is a default alias of Get-Process
    3. using .Property on an array takes that property value from every item in the array
    4. using an operator on an array filters the array by whether the items pass the test
    5. ? is an alias of Where-Object
    6. -notin tests if one item is not in a collection
    7. gc is an alias of Get-Content
    8. sc is an alias of Set-Content
    

    您应该使用
    Set Content
    而不是
    Out File
    ,因为它可以很好地处理字符编码,而它们不能。而且,因为Get Content/Set Content听起来像是一对令人难忘的配对,而Get Content/Out File则不然。

    首先非常感谢您的详细回复,它帮助我更好地理解Powershell,它看起来很棒,正是我想要的!然而,我有一个快速跟进的问题,因为我还没有在网上找到答案。当我尝试这两种方法时,我似乎得到了一个关于'-notin'运算符的错误,当运行代码时,我收到这样的消息:“您必须在'-notin'运算符的右侧提供一个值表达式”。根据经验,您是否也知道这个错误指的是什么?非常感谢。@Dronzil是的,我喜欢。PowerShell在2012年发布的3.0版中获得了
    -notin
    ,您生活在过去:p您不必测试集合中的
    您必须将其交换到
    集合包含项
    ,例如
    {$AuthorizedNames-notcontains$}
    ,它与PS 2.0Ah兼容,我明白了,这就解释了!经过测试,效果很好。谢谢你的帮助!:)