ForEach-Object
Realiza una operación en cada elemento de una colección de objetos de entrada.
Sintaxis
ForEach-Object
[-InputObject <PSObject>]
[-Begin <ScriptBlock>]
[-Process] <ScriptBlock[]>
[-End <ScriptBlock>]
[-RemainingScripts <ScriptBlock[]>]
[-WhatIf]
[-Confirm]
[<CommonParameters>]
ForEach-Object
[-InputObject <PSObject>]
[-MemberName] <String>
[-ArgumentList <Object[]>]
[-WhatIf]
[-Confirm]
[<CommonParameters>]
Description
El ForEach-Object
cmdlet realiza una operación en cada elemento de una colección de objetos de entrada. Los objetos de entrada se pueden canalizar al cmdlet o especificarse mediante el parámetro InputObject .
A partir de Windows PowerShell 3.0, hay dos maneras diferentes de construir un ForEach-Object
comando.
Bloque de script. Puede usar un bloque de scripts para especificar la operación. Dentro del bloque de script, use la
$_
variable para representar el objeto actual. El bloque de script es el valor del parámetro Process . El bloque de script puede contener cualquier script de PowerShell.Por ejemplo, el siguiente comando obtiene el valor de la propiedad ProcessName de cada proceso del equipo.
Get-Process | ForEach-Object {$_.ProcessName}
ForEach-Object
admite losbegin
bloques ,process
yend
como se describe en about_functions.Nota:
Los bloques de script se ejecutan en el ámbito del autor de la llamada. Por lo tanto, los bloques tienen acceso a variables de ese ámbito y pueden crear nuevas variables que persistan en ese ámbito una vez completado el cmdlet.
Instrucción Operation. También puede escribir una instrucción operation, que es mucho más similar al lenguaje natural. Puede usar la instrucción de operación para especificar un valor de propiedad o llamar a un método. Las instrucciones de operación se presentaron en Windows PowerShell 3.0.
Por ejemplo, el siguiente comando también obtiene el valor de la propiedad ProcessName de cada proceso del equipo.
Get-Process | ForEach-Object ProcessName
Ejemplos
Ejemplo 1: Dividir enteros en una matriz
En este ejemplo se toma una matriz de tres enteros y se divide cada uno de ellos en 1024.
30000, 56798, 12432 | ForEach-Object -Process {$_/1024}
29.296875
55.466796875
12.140625
Ejemplo 2: Obtener la longitud de todos los archivos de un directorio
En este ejemplo se procesan los archivos y directorios del directorio $PSHOME
de instalación de PowerShell .
Get-ChildItem $PSHOME |
ForEach-Object -Process {if (!$_.PSIsContainer) {$_.Name; $_.Length / 1024; " " }}
Si el objeto no es un directorio, el bloque de script obtiene el nombre del archivo, divide el valor de su propiedad Length en 1024 y agrega un espacio (" ") para separarlo de la entrada siguiente. El cmdlet usa la propiedad PSISContainer para determinar si un objeto es un directorio.
Ejemplo 3: Operar en los eventos del sistema más recientes
En este ejemplo se escriben los 1000 eventos más recientes del registro de eventos del sistema en un archivo de texto. La hora actual se muestra antes y después de procesar los eventos.
Get-EventLog -LogName System -Newest 1000 |
ForEach-Object -Begin {Get-Date} -Process {
Out-File -FilePath Events.txt -Append -InputObject $_.Message
} -End {Get-Date}
Get-EventLog
obtiene los 1000 eventos más recientes del registro de eventos del sistema y los canaliza al ForEach-Object
cmdlet . El parámetro Begin muestra la fecha y hora actuales. A continuación, el parámetro Process usa el Out-File
cmdlet para crear un archivo de texto denominado events.txt y almacena la propiedad message de cada uno de los eventos de ese archivo. Por último, el parámetro End se usa para mostrar la fecha y hora después de que se haya completado todo el procesamiento.
Ejemplo 4: Cambiar el valor de una clave del Registro
En este ejemplo se cambia el valor de la entrada del Registro RemotePath en todas las subclaves de la HKCU:\Network
clave a texto en mayúsculas.
Get-ItemProperty -Path HKCU:\Network\* |
ForEach-Object {
Set-ItemProperty -Path $_.PSPath -Name RemotePath -Value $_.RemotePath.ToUpper()
}
Puede usar este formato para cambiar la forma o el contenido de un valor de la entrada del Registro.
Cada subclave de la clave de red representa una unidad de red asignada que se vuelve a conectar al iniciar sesión. La entrada RemotePath contiene la ruta de acceso UNC de la unidad conectada. Por ejemplo, si asigna la E:
unidad a \\Server\Share
, se crea una subclave E con el valor del Registro RemotePath establecido \\Server\Share
en HKCU:\Network
.
El comando usa el Get-ItemProperty
cmdlet para obtener todas las subclaves de la clave de red y el Set-ItemProperty
cmdlet para cambiar el valor de la entrada del Registro RemotePath en cada clave. En el Set-ItemProperty
comando , la ruta de acceso es el valor de la propiedad PSPath de la clave del Registro. Se trata de una propiedad del objeto de Microsoft .NET Framework que representa la clave del Registro, no una entrada del Registro. El comando usa el método ToUpper() del valor remotePath , que es una cadena REG_SZ.
Dado que Set-ItemProperty
cambia la propiedad de cada clave, el ForEach-Object
cmdlet es necesario para acceder a la propiedad .
Ejemplo 5: Uso de la variable automática $null
En este ejemplo se muestra el efecto de canalización de la $null
variable automática al ForEach-Object
cmdlet .
1, 2, $null, 4 | ForEach-Object {"Hello"}
Hello
Hello
Hello
Hello
Dado que PowerShell trata $null
como un marcador de posición explícito, el ForEach-Object
cmdlet genera un valor para $null
como lo hace para otros objetos canalizaciones a él.
Ejemplo 6: Obtener valores de propiedad
En este ejemplo se obtiene el valor de la propiedad Path de todos los módulos de PowerShell instalados mediante el parámetro MemberName del ForEach-Object
cmdlet .
Get-Module -ListAvailable | ForEach-Object -MemberName Path
Get-Module -ListAvailable | Foreach Path
El segundo comando es equivalente al primero. Usa el Foreach
alias del ForEach-Object
cmdlet y omite el nombre del parámetro MemberName , que es opcional.
El ForEach-Object
cmdlet es útil para obtener valores de propiedad, ya que obtiene el valor sin cambiar el tipo, a diferencia de los cmdlets Format o el Select-Object
cmdlet , que cambian el tipo de valor de propiedad.
Ejemplo 7: Dividir nombres de módulo en nombres de componente
En este ejemplo se muestran tres maneras de dividir dos nombres de módulo separados por puntos en sus nombres de componente. Los comandos llaman al método Split de cadenas. Los tres comandos usan una sintaxis diferente, pero son equivalentes e intercambiables. La salida es la misma para los tres casos.
"Microsoft.PowerShell.Core", "Microsoft.PowerShell.Host" |
ForEach-Object {$_.Split(".")}
"Microsoft.PowerShell.Core", "Microsoft.PowerShell.Host" |
ForEach-Object -MemberName Split -ArgumentList "."
"Microsoft.PowerShell.Core", "Microsoft.PowerShell.Host" |
Foreach Split "."
Microsoft
PowerShell
Core
Microsoft
PowerShell
Host
El primer comando usa la sintaxis tradicional, que incluye un bloque de script y el operador $_
de objeto actual. Usa la sintaxis de puntos para especificar el método y los paréntesis para delimitar el argumento delimitador.
El segundo comando usa el parámetro MemberName para especificar el método Split y el parámetro ArgumentList para identificar el punto (.
) como delimitador de división.
El tercer comando usa el alias Foreach del ForEach-Object
cmdlet y omite los nombres de los parámetros MemberName y ArgumentList , que son opcionales.
Ejemplo 8: Uso de ForEach-Object con dos bloques de script
En este ejemplo, pasamos dos bloques de script de forma posicional. Todos los bloques de script se enlazan al parámetro Process . Sin embargo, se tratan como si se hubieran pasado a los parámetros Begin y Process .
1..2 | ForEach-Object { 'begin' } { 'process' }
begin
process
process
Ejemplo 9: Uso de ForEach-Object con más de dos bloques de script
En este ejemplo, pasamos cuatro bloques de script posicionalmente. Todos los bloques de script se enlazan al parámetro Process . Sin embargo, se tratan como si se hubieran pasado a los parámetros Begin, Process y End .
1..2 | ForEach-Object { 'begin' } { 'process A' } { 'process B' } { 'end' }
begin
process A
process B
process A
process B
end
Nota:
El primer bloque de script siempre se asigna al begin
bloque, el último bloque se asigna al end
bloque y los dos bloques intermedios se asignan al process
bloque.
Ejemplo 10: Ejecución de varios bloques de script para cada elemento de canalización
Como se muestra en el ejemplo anterior, se asignan varios bloques de script mediante el parámetro Process a los parámetros Begin y End . Para evitar esta asignación, debe proporcionar valores explícitos para los parámetros Begin y End .
1..2 | ForEach-Object -Begin $null -Process { 'one' }, { 'two' }, { 'three' } -End $null
one
two
three
one
two
three
Parámetros
-ArgumentList
Especifica una matriz de argumentos para una llamada de método. Para obtener más información sobre el comportamiento de ArgumentList, vea about_Splatting.
Este parámetro se incorporó en Windows PowerShell 3.0.
Tipo: | Object[] |
Alias: | Args |
Posición: | Named |
Valor predeterminado: | None |
Requerido: | False |
Aceptar entrada de canalización: | False |
Aceptar caracteres comodín: | False |
-Begin
Especifica un bloque de script que se ejecuta antes de que este cmdlet procese los objetos de entrada. Este bloque de script solo se ejecuta una vez para toda la canalización. Para obtener más información sobre el begin
bloque, consulte about_Functions.
Tipo: | ScriptBlock |
Posición: | Named |
Valor predeterminado: | None |
Requerido: | False |
Aceptar entrada de canalización: | False |
Aceptar caracteres comodín: | False |
-Confirm
Le solicita su confirmación antes de ejecutar el cmdlet.
Tipo: | SwitchParameter |
Alias: | cf |
Posición: | Named |
Valor predeterminado: | False |
Requerido: | False |
Aceptar entrada de canalización: | False |
Aceptar caracteres comodín: | False |
-End
Especifica un bloque de script que se ejecuta después de que este cmdlet procese todos los objetos de entrada. Este bloque de script solo se ejecuta una vez para toda la canalización. Para obtener más información sobre el end
bloque, consulte about_Functions.
Tipo: | ScriptBlock |
Posición: | Named |
Valor predeterminado: | None |
Requerido: | False |
Aceptar entrada de canalización: | False |
Aceptar caracteres comodín: | False |
-InputObject
Especifica los objetos de entrada. ForEach-Object
ejecuta la instrucción script block o operation en cada objeto de entrada. Especifique una variable que contenga los objetos o escriba un comando o una expresión que obtenga los objetos.
Cuando se usa el parámetro InputObject con ForEach-Object
, en lugar de canalizar los resultados del comando a ForEach-Object
, el valor InputObject se trata como un único objeto. Esto es true incluso si el valor es una colección que es el resultado de un comando, como -InputObject (Get-Process)
.
Dado que InputObject no puede devolver propiedades individuales de una matriz o colección de objetos, se recomienda que si usa ForEach-Object
para realizar operaciones en una colección de objetos para esos objetos que tienen valores específicos en propiedades definidas, se usa ForEach-Object
en la canalización, como se muestra en los ejemplos de este tema.
Tipo: | PSObject |
Posición: | Named |
Valor predeterminado: | None |
Requerido: | False |
Aceptar entrada de canalización: | True |
Aceptar caracteres comodín: | False |
-MemberName
Especifica el nombre de la propiedad miembro a la que se va a obtener o al método miembro que se va a llamar. Los miembros deben ser miembros de instancia, no miembros estáticos.
Se permiten caracteres comodín, pero solo funcionan si la cadena resultante se resuelve en un valor único.
Por ejemplo, si ejecuta Get-Process | ForEach -MemberName *Name
, el patrón comodín coincide con más de un miembro que provoca un error en el comando.
Este parámetro se incorporó en Windows PowerShell 3.0.
Tipo: | String |
Posición: | 0 |
Valor predeterminado: | None |
Requerido: | True |
Aceptar entrada de canalización: | False |
Aceptar caracteres comodín: | True |
-Process
Especifica la operación que se realiza en cada objeto de entrada. Este bloque de script se ejecuta para cada objeto de la canalización. Para obtener más información sobre el process
bloque, consulte about_Functions.
Cuando se proporcionan varios bloques de script al parámetro Process , el primer bloque de script siempre se asigna al begin
bloque . Si solo hay dos bloques de script, el segundo bloque se asigna al process
bloque . Si hay tres o más bloques de script, el primer bloque de script siempre se asigna al begin
bloque, el último bloque se asigna al end
bloque y los bloques intermedios se asignan al process
bloque.
Tipo: | ScriptBlock[] |
Posición: | 0 |
Valor predeterminado: | None |
Requerido: | True |
Aceptar entrada de canalización: | False |
Aceptar caracteres comodín: | False |
-RemainingScripts
Especifica todos los bloques de script que el parámetro Process no toma.
Este parámetro se incorporó en Windows PowerShell 3.0.
Tipo: | ScriptBlock[] |
Posición: | Named |
Valor predeterminado: | None |
Requerido: | False |
Aceptar entrada de canalización: | False |
Aceptar caracteres comodín: | False |
-WhatIf
Muestra lo que sucedería si se ejecutara el cmdlet. El cmdlet no se ejecuta.
Tipo: | SwitchParameter |
Alias: | wi |
Posición: | Named |
Valor predeterminado: | False |
Requerido: | False |
Aceptar entrada de canalización: | False |
Aceptar caracteres comodín: | False |
Entradas
Puede canalizar cualquier objeto a este cmdlet.
Salidas
Este cmdlet devuelve objetos determinados por la entrada.
Notas
Windows PowerShell incluye los siguientes alias para ForEach-Object
:
%
foreach
El ForEach-Object
cmdlet funciona de forma muy similar a la instrucción Foreach , excepto que no se puede canalizar la entrada a una instrucción Foreach . Para obtener más información sobre la instrucción Foreach , consulte about_Foreach.
A partir de PowerShell 4.0, Where
y ForEach
se agregaron métodos para su uso con colecciones. Puede obtener más información sobre estos nuevos métodos aquí about_arrays