$locations = Get-ChildItem $readLoc -recurse | ? {!$_.psiscontainer} | select-object name | %{$e = $_.name; get-content $e}
$array = @()
for($i = 0; $i -lt $locations.length; $i++){
#if($locations.name[$i].length -eq "9"){
$paths = Resolve-Path $locations.fullname[$i]
$paths.path
get-content $locations.name[$i]
#$array += $paths.path
#}
}
我需要遍历文件系统中的每个文件并打开每个文件。我正在检查文件中的字符串是否与正则表达式匹配,然后将该文件的完整路径输出到数组中。
但是,$locations
并不接受get-content。
get-content:找不到路径
'C:\Users\xxxxxx\Documents\files\powershell\OWASP_ApplicationThreatModeling.docx'
because it does not exist.
At line:1 char:89
+ ... .psiscontainer} | select-object name |%{$e = $_.name; get-content $e}
+ ~~~~~~~~~~~~~~
+ CategoryInfo : ObjectNotFound: (C:\Users\p61782...atModeling.docx:String) [Get-Content], ItemNotFoundEx
ception
+ FullyQualifiedErrorId : PathNotFound,Microsoft.PowerShell.Commands.GetContentCommand.
答案 0 :(得分:1)
正如TheMadTechnician所示,使用Select-String
执行正则表达式匹配更有效:
$locations = Get-ChildItem $readLoc -File -Recurse |
Select-String -List -Pattern '^\d{3}-?\d{2}-?\d{4}$' |
Select-Object -ExpandProperty Path
注意:
- 传递给-Pattern
的正则表达式是linked to in a comment的简化版本
请注意正则表达式如何包含在'...'
而不是"..."
中,以防止PowerShell对字符串进行无意的预先解释。
Get-ChildItem $readLoc -File -recurse
以递归方式枚举目标目录子树中的所有文件。在PSv3 +中可以使用切换-File
(及其对应的-Directory
),并且无需使用? {!$_.psiscontainer}
过滤器。
Select-String
可以对通过Get-ChildItem
传输的文件的内容进行操作,并默认执行正则表达式匹配:
-List
告诉Select-String
仅返回每个输入文件中的第一个匹配项(如果有)。 Select-String
返回匹配信息对象,其.Path
属性包含输入文件的完整路径,因此Select-Object -ExpandProperty Path
仅用于输出包含至少1个匹配项的任何文件的路径。
总的来说,变量$locations
因此接收那些文件的完整路径的数组,其中至少有1行匹配感兴趣的正则表达式。
请注意,如果输出包含多于1个元素,PowerShell会自动从数组中的命令收集输出。
至于你的尝试:
您当前的问题是您将.Name
- 即仅仅是文件名称 - 传递给Get-Content
而不是.FullName
。
此外,您的明显意图是收集数组$locations
中的文件信息对象,而您的管道实际上生成了所有文件的内容 (作为一系列行)。
答案 1 :(得分:0)
您需要使用FullName
属性。现在,您正在使用Select-Object
命令剥离它。
$locations = Get-ChildItem $readLoc -recurse | ? {!$_.psiscontainer}
for($i = 0; $i -lt $locations.length; $i++){
$locations[$i].fullname
get-content $locations[$i].fullname
}