In this answer the author proposed the following snippet:
dir -Path C:\FolderName -Filter *.fileExtension -Recurse | %{$_.FullName}
I can understand the majority of it, but I'm unable to search documentation for the last part. The output of the search is piped |
and used in %{}
and as $_
.
I have experimented around it, %{}
is a for-each statement I believe, bing search was not effective. $_
is also somewhat magic: it is a variable, with no name and thus immediately consumed? I don't care much for the .FullName
, that part I sorted out. Again, bing search was not effective, nor searching for those char sequences in PowerShell docs.
Can anybody explain it to me?
%{}
is not "a thing" - it's two things: %
and {}
%
is an alias for the ForEach-Object
cmdlet:
PS ~> Get-Alias '%'
CommandType Name Version Source
----------- ---- ------- ------
Alias % -> ForEach-Object
... so it resolves to:
... |ForEach-Object { $_.FullName }
ForEach-Object
is basically PowerShell's map
function - it takes input via the pipeline and applies the operation described in the {}
block to each one of them.
$_
is an automatic reference to the current pipeline input item being processed
You can think of it a bit like a foreach($thing in $collection){}
loop:
1..10 |ForEach-Object { $_ * 10 }
# produces the same output as
foreach($n in 1..10){
$n * 10
}
Except we can now stick our loop in the middle of a pipeline and have it produce output for immediate consumption:
1..10 |ForEach-Object { $_ * 10 } |Do-SomethingElse
ForEach-Object
is not the only thing that makes use of the $_
automatic variable in PowerShell - it's also used for pipeline-binding expressions:
mkdir NewDirectory |cd -Path { $_.FullName }
... as well as property expressions, a type of dynamic property definition supported by a number of cmdlets like Sort-Object
:
1..10 |Sort-Object { -$_ } # sort in descending order without specifying -Descending
... Group-Object
:
1..10 |Group-Object { $_ % 3 } # group terms by modulo congruence
... and Select-Object
:
1..10 |Select-Object @{Name='TimesTen';Expression={$_ * 10}} # Create synthetic properties based on dynamic value calculation over input