O cmdlet Select-Object é uma ferramenta essencial no PowerShell para filtrar e transformar objetos. Ele permite selecionar propriedades específicas de objetos passados pelo pipeline, criar novas propriedades calculadas e limitar o número de objetos processados. Nesta aula, exploraremos suas principais funcionalidades.

Com Select-Object, você pode extrair apenas as informações relevantes de um conjunto de dados, facilitando a leitura e o processamento posterior. Além disso, é possível modificar a estrutura dos objetos adicionando propriedades calculadas, o que é útil para relatórios e análises.

Selecionando propriedades

A forma mais básica de uso do Select-Object é especificar quais propriedades de um objeto você deseja manter. Por exemplo, ao listar processos, você pode selecionar apenas Name, Id e CPU.

Get-Process | Select-Object Name, Id, CPU

Isso cria novos objetos contendo apenas essas três propriedades. Você também pode usar curingas, como * para todas as propriedades, ou [a-z]* para propriedades começando com letras minúsculas.

Propriedades calculadas

Propriedades calculadas permitem criar novas propriedades baseadas em expressões. A sintaxe utiliza um hashtable com chaves Name (ou Label) e Expression. Por exemplo, para exibir o nome do processo em maiúsculas:

Get-Process | Select-Object Name, @{Name='NameUpper'; Expression={$_.Name.ToUpper()}}

Você pode usar qualquer scriptblock na expressão, acessando o objeto atual via $_. Isso é útil para formatação, cálculos e transformações.

-First e -Last

Os parâmetros -First e -Last limitam a quantidade de objetos retornados. -First retorna os primeiros N objetos, enquanto -Last retorna os últimos N. São úteis para amostras ou para pegar os top/últimos itens de uma lista ordenada.

Get-Process | Sort-Object CPU -Descending | Select-Object -First 5

O exemplo acima retorna os 5 processos que mais consomem CPU. Combinado com Sort-Object, é uma forma rápida de obter rankings.

-ExpandProperty

O parâmetro -ExpandProperty é usado quando uma propriedade contém uma coleção de objetos. Ele "expande" essa propriedade, retornando cada elemento da coleção como um objeto separado no pipeline. Por exemplo, o cmdlet Get-Service retorna serviços, e a propriedade ServicesDependedOn é uma lista de strings. Para obter cada dependência como um objeto individual:

Get-Service | Select-Object -ExpandProperty ServicesDependedOn

Isso é útil para processar cada item da coleção separadamente. Se a propriedade não for uma coleção, -ExpandProperty retorna o valor da propriedade diretamente, sem encapsulá-lo em um objeto.

Boas práticas

Use Select-Object para reduzir a quantidade de dados transmitidos no pipeline, melhorando a performance. Prefira selecionar propriedades específicas em vez de usar * desnecessariamente. Ao criar propriedades calculadas, mantenha as expressões simples e legíveis.

Referências

Exercícios

  1. Exercício 1: Liste todos os processos em execução, mas selecione apenas as propriedades Name, Id e WorkingSet (memória em bytes).
  2. ✓ Resposta:
    Get-Process | Select-Object Name, Id, WorkingSet
  3. Exercício 2: Crie uma propriedade calculada chamada CPU_Minutes que exiba o tempo de CPU em minutos (dividindo por 60). Use Get-Process como base.
  4. ✓ Resposta:
    Get-Process | Select-Object Name, @{Name='CPU_Minutes'; Expression={$_.CPU / 60}}
  5. Exercício 3: Obtenha os 3 serviços que mais tempo estão em execução (use Get-Service? Na verdade, serviços não têm propriedade de tempo. Use Get-Process e selecione os 3 com maior WorkingSet).
  6. ✓ Resposta:
    Get-Process | Sort-Object WorkingSet -Descending | Select-Object -First 3 Name, WorkingSet
  7. Exercício 4: Use -ExpandProperty para listar todos os módulos carregados por um processo específico (por exemplo, o processo powershell). Dica: use Get-Process -Name powershell | Select-Object -ExpandProperty Modules.
  8. ✓ Resposta:
    Get-Process -Name powershell | Select-Object -ExpandProperty Modules
  9. Exercício 5: Crie um comando que retorne o último evento do log do sistema (Get-WinEvent -LogName System) e exiba apenas a mensagem e o tempo de criação, mas com o tempo formatado como string curta (use Get-Date).
  10. ✓ Resposta:
    Get-WinEvent -LogName System -MaxEvents 1 | Select-Object @{Name='Time'; Expression={Get-Date $_.TimeCreated -Format 'yyyy-MM-dd HH:mm:ss'}}, Message