PowerShell’s formatting and output cmdlets transform raw data into readable, actionable information. Whether you’re displaying process information, exporting logs, or creating reports, understanding these cmdlets is essential for effective PowerShell scripting and administration.
Understanding PowerShell’s Formatting System
PowerShell uses a sophisticated formatting system that automatically determines how to display objects. When you run a command, PowerShell checks for custom formatting rules and applies them before displaying output. The formatting cmdlets give you explicit control over this process.
The Four Core Formatting Cmdlets
PowerShell provides four primary formatting cmdlets, each serving different visualization needs:
- Format-Table: Displays output in tabular format with columns
- Format-List: Shows each property on a separate line
- Format-Wide: Displays objects in multiple columns with limited properties
- Format-Custom: Uses custom view definitions for specialized formatting
Format-Table: Tabular Data Display
Format-Table (alias: ft) is the most commonly used formatting cmdlet. It organizes data into columns, making it ideal for comparing multiple objects with similar properties.
Basic Format-Table Usage
# Display processes in table format
Get-Process | Format-Table
# Select specific properties
Get-Process | Format-Table Name, CPU, WorkingSet
# Alternative syntax
Get-Process | ft Name, CPU, WorkingSet
Output:
Name CPU WorkingSet
---- --- ----------
chrome 45.23 234567890
powershell 2.15 89012345
explorer 12.89 156789012
AutoSize Parameter
The AutoSize parameter adjusts column widths to fit content, eliminating wasted space:
Get-Service | Format-Table Name, Status, DisplayName -AutoSize
Name Status DisplayName
---- ------ -----------
BITS Running Background Intelligent Transfer Service
Spooler Running Print Spooler
wuauserv Running Windows Update
Property Expressions and Calculated Properties
Create custom columns with calculated values using hashtable syntax:
Get-Process | Format-Table Name,
@{Label="Memory(MB)"; Expression={$_.WorkingSet / 1MB}; FormatString="N2"},
@{Label="CPU(s)"; Expression={$_.CPU}; FormatString="N2"} -AutoSize
Name Memory(MB) CPU(s)
---- ---------- ------
chrome 223.74 45.23
powershell 84.88 2.15
explorer 149.51 12.89
GroupBy Parameter
Group related items together based on a property:
Get-Service | Format-Table Name, DisplayName -GroupBy Status
Status: Running
Name DisplayName
---- -----------
BITS Background Intelligent Transfer Service
Spooler Print Spooler
Status: Stopped
Name DisplayName
---- -----------
AppIDSvc Application Identity
Format-List: Detailed Property View
Format-List (alias: fl) displays each property on its own line, making it perfect for viewing detailed information about individual objects.
Basic Format-List Usage
# Display all properties of a process
Get-Process powershell | Format-List
# Display specific properties
Get-Process powershell | Format-List Name, Id, CPU, StartTime
# Show all properties including hidden ones
Get-Process powershell | Format-List *
Output:
Name : powershell
Id : 12345
CPU : 2.15625
StartTime : 10/22/2025 9:30:45 AM
When to Use Format-List
Format-List excels when you need to:
- Examine detailed properties of a single object
- View properties with long text values
- Troubleshoot by seeing all available properties
- Display nested or complex object structures
# Perfect for viewing service details
Get-Service BITS | Format-List *
# Excellent for examining file properties
Get-Item C:\Windows\notepad.exe | Format-List *
Out-File: Redirecting Output to Files
Out-File sends command output to a text file, essential for logging, reporting, and data export.
Basic Out-File Syntax
# Save process list to file
Get-Process | Out-File C:\Logs\processes.txt
# Append to existing file
Get-Service | Out-File C:\Logs\services.txt -Append
# Specify encoding
Get-Process | Out-File C:\Logs\processes.txt -Encoding UTF8
Out-File Parameters
# Control width to prevent line wrapping
Get-Process | Format-Table | Out-File C:\Logs\processes.txt -Width 200
# Overwrite without confirmation
Get-Service | Out-File C:\Logs\services.txt -Force
# No line wrapping
Get-Process | Out-File C:\Logs\processes.txt -NoNewline
Out-File vs Redirection Operator
PowerShell offers the redirection operator (>) as a shorthand:
# These are equivalent
Get-Process | Out-File C:\Logs\processes.txt
Get-Process > C:\Logs\processes.txt
# Append with >>
Get-Service >> C:\Logs\services.txt
Export-Csv: Structured Data Export
Export-Csv creates comma-separated value files, ideal for data analysis in Excel or other tools.
Basic CSV Export
# Export processes to CSV
Get-Process | Export-Csv C:\Reports\processes.csv
# Without type information header
Get-Process | Export-Csv C:\Reports\processes.csv -NoTypeInformation
# Select specific properties
Get-Process | Select-Object Name, CPU, WorkingSet |
Export-Csv C:\Reports\processes.csv -NoTypeInformation
Custom Delimiters and Encoding
# Use semicolon delimiter
Get-Service | Export-Csv C:\Reports\services.csv -Delimiter ";" -NoTypeInformation
# Specify encoding
Get-Process | Export-Csv C:\Reports\processes.csv -Encoding UTF8 -NoTypeInformation
# Append to existing CSV
Get-Service | Export-Csv C:\Reports\services.csv -Append -NoTypeInformation
Importing CSV Data
# Import and work with CSV data
$processes = Import-Csv C:\Reports\processes.csv
$processes | Where-Object {$_.CPU -gt 10}
# Convert CSV to objects for processing
Import-Csv C:\Reports\services.csv |
Where-Object Status -eq "Running" |
Format-Table Name, DisplayName
Out-GridView: Interactive Data Explorer
Out-GridView (alias: ogv) displays output in a searchable, filterable GUI window, perfect for interactive data exploration.
Basic GridView Usage
# Display processes in grid view
Get-Process | Out-GridView
# Add a custom title
Get-Service | Out-GridView -Title "Windows Services"
# Wait for user selection
$selected = Get-Process | Out-GridView -PassThru
$selected | Stop-Process
Selection Modes
# Single selection
$process = Get-Process | Out-GridView -OutputMode Single
Write-Host "Selected: $($process.Name)"
# Multiple selection
$services = Get-Service | Out-GridView -OutputMode Multiple
$services | Start-Service
# No selection (view only)
Get-EventLog -LogName System -Newest 100 | Out-GridView
ConvertTo-Html: Creating HTML Reports
ConvertTo-Html generates HTML-formatted output for web-based reports and documentation.
Basic HTML Conversion
# Create simple HTML report
Get-Process | ConvertTo-Html | Out-File C:\Reports\processes.html
# Add custom title and styling
Get-Service | ConvertTo-Html -Title "Service Report" -PreContent "Windows Services
" |
Out-File C:\Reports\services.html
Advanced HTML Reports with CSS
$css = @"
"@
Get-Process | Select-Object Name, CPU, WorkingSet -First 10 |
ConvertTo-Html -Head $css -Title "Top 10 Processes" |
Out-File C:\Reports\styled_processes.html
Output Cmdlets Comparison
Choosing the Right Output Cmdlet
# Console viewing: Format-Table
Get-Process | Format-Table Name, CPU
# Detailed inspection: Format-List
Get-Service BITS | Format-List *
# Simple logging: Out-File
Get-EventLog -LogName System -Newest 50 | Out-File C:\Logs\events.txt
# Data export: Export-Csv
Get-ADUser -Filter * | Export-Csv C:\Reports\users.csv -NoTypeInformation
# Interactive filtering: Out-GridView
Get-Process | Out-GridView -PassThru | Stop-Process
# Web reports: ConvertTo-Html
Get-Service | ConvertTo-Html | Out-File C:\Reports\services.html
Format-Wide: Compact Multi-Column Display
Format-Wide (alias: fw) displays objects in multiple columns, showing only one property per object.
Basic Format-Wide Usage
# Display process names in columns
Get-Process | Format-Wide Name
# Specify number of columns
Get-Service | Format-Wide Name -Column 4
# Display with property selection
Get-ChildItem | Format-Wide Name -Column 3
Output:
chrome powershell explorer notepad
winword excel outlook teams
Out-String: Converting to String Format
Out-String converts objects to strings, useful for text manipulation or storing formatted output as variables.
# Convert to string
$output = Get-Process | Format-Table | Out-String
# Store formatted data
$serviceList = Get-Service | Format-List * | Out-String
$serviceList | Out-File C:\Reports\services.txt
# Width control
$wide = Get-Process | Format-Table | Out-String -Width 200
Advanced Formatting Techniques
Custom Format Files
PowerShell allows creating custom .ps1xml format files for consistent object display:
# View current format data
Get-FormatData -TypeName System.Diagnostics.Process
# Load custom format file
Update-FormatData -PrependPath C:\CustomFormats\MyFormat.ps1xml
Combining Format and Output Cmdlets
# Format then export
Get-Process |
Format-Table Name, CPU, WorkingSet |
Out-File C:\Reports\processes.txt -Width 150
# Multiple outputs from same data
$services = Get-Service
$services | Export-Csv C:\Reports\services.csv -NoTypeInformation
$services | ConvertTo-Html | Out-File C:\Reports\services.html
$services | Format-Table | Out-File C:\Reports\services.txt
Pipeline Performance Considerations
# Efficient: Filter before formatting
Get-Process |
Where-Object CPU -gt 10 |
Select-Object Name, CPU, WorkingSet |
Format-Table -AutoSize
# Less efficient: Format before filtering (avoid this)
Get-Process |
Format-Table |
Where-Object CPU -gt 10 # Won't work as expected
Real-World Formatting Examples
System Monitoring Report
# Create comprehensive system report
$date = Get-Date -Format "yyyy-MM-dd"
$reportPath = "C:\Reports\SystemReport_$date.html"
$css = @"
"@
$html = @"
System Report - $(Get-Date -Format 'yyyy-MM-dd HH:mm')
Top 10 CPU Consuming Processes
$(Get-Process | Sort-Object CPU -Descending | Select-Object -First 10 Name, CPU, WorkingSet | ConvertTo-Html -Fragment)
Running Services
$(Get-Service | Where-Object Status -eq "Running" | Select-Object Name, DisplayName, Status | ConvertTo-Html -Fragment)
Disk Space
$(Get-PSDrive -PSProvider FileSystem | Select-Object Name,
@{N="Used(GB)";E={[math]::Round($_.Used/1GB,2)}},
@{N="Free(GB)";E={[math]::Round($_.Free/1GB,2)}} | ConvertTo-Html -Fragment)
"@
ConvertTo-Html -Head $css -Body $html -Title "System Report" | Out-File $reportPath
Service Status Dashboard
# Interactive service management
$services = Get-Service |
Select-Object Name, DisplayName, Status, StartType |
Sort-Object Status, Name
$selected = $services | Out-GridView -Title "Service Manager" -OutputMode Multiple
foreach ($service in $selected) {
$action = Read-Host "Action for $($service.Name) [Start/Stop/Restart]"
switch ($action.ToLower()) {
"start" { Start-Service $service.Name }
"stop" { Stop-Service $service.Name }
"restart" { Restart-Service $service.Name }
}
}
Log Analysis and Export
# Analyze event logs and create multiple outputs
$errors = Get-EventLog -LogName System -EntryType Error -Newest 100
# Console summary
$errors |
Group-Object Source |
Sort-Object Count -Descending |
Format-Table Count, Name -AutoSize
# Detailed CSV export
$errors |
Select-Object TimeGenerated, Source, EventID, Message |
Export-Csv C:\Logs\system_errors.csv -NoTypeInformation
# HTML report
$errors |
Select-Object TimeGenerated, Source, EventID, Message |
ConvertTo-Html -Title "System Errors" |
Out-File C:\Logs\system_errors.html
# Plain text log
$errors |
Format-List TimeGenerated, Source, EventID, Message |
Out-File C:\Logs\system_errors.txt
Best Practices for Formatting and Output
Performance Optimization
- Apply filters with Where-Object before formatting cmdlets
- Use Select-Object to limit properties before exporting
- Avoid using Format-* cmdlets in the middle of pipelines
- Use -AutoSize sparingly for large datasets
# Good: Filter first
Get-Process | Where-Object CPU -gt 5 | Format-Table Name, CPU
# Bad: Format first (loses object properties)
Get-Process | Format-Table Name, CPU | Where-Object CPU -gt 5
Output Encoding
# Ensure proper encoding for international characters
Get-Service | Out-File C:\Reports\services.txt -Encoding UTF8
# Specify encoding for CSV
Get-Process | Export-Csv C:\Reports\processes.csv -Encoding UTF8 -NoTypeInformation
Error Handling
# Safe file operations with error handling
try {
Get-Process | Export-Csv C:\Reports\processes.csv -NoTypeInformation -ErrorAction Stop
Write-Host "Export successful" -ForegroundColor Green
}
catch {
Write-Host "Export failed: $_" -ForegroundColor Red
}
# Test path before writing
$outputPath = "C:\Reports\output.txt"
if (Test-Path (Split-Path $outputPath)) {
Get-Service | Out-File $outputPath
} else {
Write-Host "Directory does not exist" -ForegroundColor Red
}
Common Formatting Pitfalls and Solutions
Truncated Output
PowerShell truncates columns by default. Solutions:
# Use AutoSize for better column width
Get-Process | Format-Table Name, Path -AutoSize
# Increase width for Out-File
Get-Process | Format-Table | Out-File C:\Logs\processes.txt -Width 300
# Use Format-List for long values
Get-Process | Format-List Name, Path
Lost Object Properties
Format-* cmdlets convert objects to formatted text, losing original properties:
# Wrong: Can't access properties after formatting
Get-Process | Format-Table Name, CPU | Where-Object CPU -gt 5 # Won't work
# Correct: Filter before formatting
Get-Process | Where-Object CPU -gt 5 | Format-Table Name, CPU
Type Information in CSV
# Avoid type information header
Get-Process | Export-Csv C:\Reports\processes.csv -NoTypeInformation
# Or use ConvertTo-Csv for in-memory processing
$csv = Get-Service | ConvertTo-Csv -NoTypeInformation
Conclusion
Mastering PowerShell’s formatting and output cmdlets enables you to present data effectively, create professional reports, and export information in various formats. Format-Table and Format-List provide console visualization, Out-File and Export-Csv handle file operations, while Out-GridView and ConvertTo-Html offer interactive and web-based solutions. By combining these cmdlets appropriately and following best practices, you can build powerful scripts that communicate results clearly and efficiently.
Remember to filter data before formatting, choose the right output format for your needs, and always consider your audience when presenting information. With these tools and techniques, you’re equipped to handle any PowerShell formatting and output challenge.








