¿Cómo contar objetos en PowerShell?

140

Como estoy leyendo en la guía del usuario de PowerShell, uno de los conceptos centrales de PowerShell es que los comandos aceptan y devuelven objetos en lugar de texto. Entonces, por ejemplo, ejecutar get-aliasme devuelve varios System.Management.Automation.AliasInfoobjetos:

PS Z: \> get-alias

Nombre del tipo de comando Definición
----------- ---- ----------
Alias% para cada objeto
Alias ​​? Donde-Objeto
Alias ​​ac Add-Content
Alias ​​asnp Add-PSSnapIn
Alias ​​cat Get-Content
Alias ​​cd Set-Location
Alias ​​chdir Set-Location
...

Ahora, ¿cómo obtengo el recuento de estos objetos?

ulidtko
fuente

Respuestas:

201

Esto te hará contar:

get-alias | measure

Puede trabajar con el resultado como con el objeto:

$m = get-alias | measure
$m.Count

Y si desea tener alias en alguna variable también, puede usar Tee-Object:

$m = get-alias | tee -Variable aliases | measure
$m.Count
$aliases

Hay más información sobre el cmdlet Measure-Object en Technet .

No lo confunda con el cmdlet Measure-Command que es para medir el tiempo. (de nuevo en Technet )

jumbo
fuente
3
Usé, $Counter = $(get-alias | measure).Countya que siempre devuelve el valor 1 en caso de que solo haya una ocurrencia, tal como dijiste.
DarkLite1
66
Otra opción:get-alias | measure | % { $_.Count }
Shameer
FYI: measurees la abreviatura de Measure-Object; y devuelve un montón de otras cosas - como Average, Sum, Maximum, etc ...
BrainSlugs83
1
¿Por qué no solo (gal) .count? Requiere PS v3 o superior IIRC. EDITAR: esto ya ha sido respondido.
uranibaba
44
@Shameer Mientras estamos en eso, uno puede usar Get-Alias | Measure-Object | Select-Object -ExpandProperty Countpara deshacerse de %y {}. Lo que es más fácil de escribir y leer es para otra discusión.
LosManos
110

Tan breve como la respuesta de @jumbo es :-) puedes hacerlo aún más tersamente. Esto solo devuelve la Countpropiedad de la matriz devuelta por la subexpresión antecedente:

@(Get-Alias).Count

Un par de puntos a tener en cuenta:

  1. Puede colocar una expresión arbitrariamente compleja en lugar de Get-Alias, por ejemplo:

    @(Get-Process | ? { $_.ProcessName -eq "svchost" }).Count
  2. El signo inicial (@) es necesario para una solución robusta. Mientras la respuesta es dos o mayor obtendrá una respuesta equivalente con o sin la @, pero cuando la respuesta es cero o uno obtendrá ninguna salida a menos que tenga el signo @! (Obliga a la Countpropiedad a existir al forzar que la salida sea una matriz).

2012.01.30 Actualizar

Lo anterior es cierto para PowerShell V2. Una de las nuevas características de PowerShell V3 es que tiene una Countpropiedad incluso para los singletons, por lo que el signo al no tiene importancia para este escenario.

Michael Sorens
fuente
3
Sé que esto es viejo, pero para otros que buscan esto ... v3 + no parece funcionar sin la @ para conteo <2 si Set-StrictMode -Version Latestse usa. Me encontré con esto hoy (en 5.1): algo funcionó de manera interactiva que no funcionó en una función. Lo rastreé hasta la función que tiene Set-StrictMode; cuando configuré el modo estricto de forma interactiva, tampoco funcionó.
vr8ce
Buena captura, @ vr8ce! También soy un gran defensor Set-StrictMode, así que debería haberlo notado.
Michael Sorens
Para ampliar el consejo de @ vr8ce, no pude usar @ ($ myObject) para contar un objeto existente. Entonces uso un if ($myObject.PSobject.Properties.Name -contains "count")(de stackoverflow.com/questions/26997511/… ) antes de intentar probar la propiedad de conteo. Odio que PoSH me obligue a hacer esto, pero el Modo estricto lo vale.
duct_tape_coder
21

Solo usa paréntesis y 'cuenta'. Esto se aplica a Powershell v3

(get-alias).count
prabhakaran
fuente
1
Esto no proporciona una respuesta a la pregunta. Para criticar o solicitar una aclaración de un autor, deje un comentario debajo de su publicación.
Zo tiene
@Damien OK. Hice la edición. En SO, las personas generalmente provienen de la primera respuesta a la última. De repente no saltan a la tercera respuesta y se confunden. De modo que lo hice como una continuación de las dos primeras respuestas. Esa respuesta tiene más sentido que esta editada.
prabhakaran
1
Esto ya está cubierto en esta respuesta . Básicamente, solo estás reiterando lo que ya se dijo dos años después de que se haya dicho.
Liam
1
@Liam Esa respuesta es para powershell v2. Mi respuesta es para powershell v3. Como dijiste, esta respuesta está cubierta / contada literalmente en la actualización (2012.01.30 Actualización) en esa respuesta. Acabo de dar parte de codificación.
prabhakaran
5

@($output).CountNo siempre produce resultados correctos. Usé el ($output | Measure).Countmétodo

Encontré esto con el cmdlet VMware Get-VmQuestion:

$output = Get-VmQuestion -VM vm1
@($output).Count

La respuesta que dio es una, mientras que

$output

no produjo salida (la respuesta correcta fue 0 como se produjo con el Measuremétodo).

Este solo parece ser el caso con 0 y 1. Cualquier cosa por encima de 1 fue correcta con pruebas limitadas.

bchris999
fuente
Chris, creo que para obtener lo que querías, necesitarías hacer esto: @ (Get-VmQuestion -VM vm1) .count No puedes forzar que la salida sea una matriz ... una vez que la salida ya está hecha . Que es lo que estás haciendo.
Daniel Peel