PowerShell Measure-Object: Count, Sum, and Average Data

PowerShell Measure-Object: Count, Sum, and Average Data

PowerShell Tips Editor 3 min read
PowerShell Measure-Object: Count, Sum, and Average Data

How many log files are in that directory? What’s the total size? What’s the average file age? All three questions have a one-liner answer when you combine Get-ChildItem with PowerShell Measure-Object. This cmdlet aggregates any numeric property from pipeline input — sum, average, minimum, maximum, and count — turning what would be a manual calculation loop into a single pipeline expression. Whether you’re sizing a folder, averaging response times, or counting words in a file, Measure-Object delivers the answer instantly.

Count Objects in Pipeline

Without any parameters, Measure-Object counts the objects in the pipeline. The result is a GenericMeasureInfo object — access the .Count property to get the number.

# Count processes
(Get-Process | Measure-Object).Count

# Count files in a directory
(Get-ChildItem -Path "C:\Logs" -File | Measure-Object).Count
247
# Equivalently, use .Count directly (PowerShell unrolls to array)
@(Get-ChildItem -Path "C:\Logs" -File).Count

Sum a Numeric Property

Use -Property to specify which property to aggregate, and -Sum to compute the total. The result object’s .Sum property holds the total.

# Total size of all log files in bytes
$total = Get-ChildItem -Path "C:\Logs" -File -Recurse |
    Measure-Object -Property Length -Sum

Write-Output "Total size: $([math]::Round($total.Sum / 1MB, 1)) MB"
Total size: 234.7 MB
# Total CPU time of running processes
$cpuTotal = Get-Process | Measure-Object -Property CPU -Sum
Write-Output "Total CPU seconds: $([math]::Round($cpuTotal.Sum, 1))"

Average, Min, and Max

Combine multiple aggregation switches in one call. The result object has .Sum, .Average, .Minimum, .Maximum, and .Count properties — all populated in a single pass.

$stats = Get-ChildItem -Path "C:\Logs" -File |
    Measure-Object -Property Length -Sum -Average -Minimum -Maximum

Write-Output "Count:   $($stats.Count)"
Write-Output "Total:   $([math]::Round($stats.Sum / 1MB, 1)) MB"
Write-Output "Average: $([math]::Round($stats.Average / 1KB, 1)) KB"
Write-Output "Smallest: $([math]::Round($stats.Minimum / 1KB, 1)) KB"
Write-Output "Largest:  $([math]::Round($stats.Maximum / 1MB, 1)) MB"
Count:    247
Total:    234.7 MB
Average:  972.2 KB
Smallest: 0.1 KB
Largest:  48.2 MB

Count Words and Lines in File

Measure-Object works on text too — use -Word, -Line, and -Character switches to analyze text content. Pass text via pipeline from Get-Content.

# Count lines, words, and characters in a file
Get-Content -Path "C:\Logs\app.log" | Measure-Object -Line -Word -Character
Lines Words  Characters Property
----- -----  ---------- --------
4821  38752  312445
# Count error lines in a log
(Get-Content "C:\Logs\app.log" |
    Where-Object { $_ -match "ERROR" } |
    Measure-Object -Line).Lines

Measure Multiple Properties

Call Measure-Object once per property by piping through multiple calls, or calculate properties dynamically with Select-Object and calculated properties first.

# Multiple property measurements — run separately and compare
$processes = Get-Process

$cpuStats = $processes | Measure-Object -Property CPU -Sum -Average
$memStats = $processes | Measure-Object -Property WorkingSet -Sum -Average

Write-Output "CPU  — Total: $([math]::Round($cpuStats.Sum,0))s  Avg: $([math]::Round($cpuStats.Average,2))s"
Write-Output "RAM  — Total: $([math]::Round($memStats.Sum/1MB,0))MB  Avg: $([math]::Round($memStats.Average/1MB,1))MB"

Combine with Group-Object

Pair Group-Object with Measure-Object for per-group aggregations — such as file counts per extension or process memory totals per application.

# Total disk usage by file extension
Get-ChildItem -Path "C:\Logs" -File -Recurse |
    Group-Object Extension |
    ForEach-Object {
        $sizeStats = $_.Group | Measure-Object -Property Length -Sum
        [PSCustomObject]@{
            Extension = $_.Name
            Count     = $_.Count
            TotalMB   = [math]::Round($sizeStats.Sum / 1MB, 1)
        }
    } |
    Sort-Object TotalMB -Descending |
    Format-Table -AutoSize

Common Errors and Fixes

  • -Sum requires numeric property: If you pass a string property to -Sum, PowerShell throws “Input to -Sum must be numeric.” Verify the property type before measuring: (Get-Process | Select-Object -First 1).CPU.GetType().Name should return a numeric type. For properties stored as strings that contain numbers, cast them first with a calculated property: Select-Object @{ N="SizeNum"; E={ [long]$_.Size } }.
  • Output is a MeasureInfo object — access .Sum not direct value: Measure-Object -Sum returns a GenericMeasureInfo object, not the numeric value itself. Write-Output (Get-ChildItem | Measure-Object -Property Length -Sum) outputs the whole object. To get just the number: (Get-ChildItem | Measure-Object -Property Length -Sum).Sum. This is the most common usage mistake with this cmdlet.

Related Cmdlets / See Also

Wrapping Up

Measure-Object answers quantitative questions about any collection in a single pipeline expression — no loops, no manual accumulators. As a next step, build a disk space summary script that uses Measure-Object -Sum to calculate total and used space per drive across your server fleet, giving you a consolidated storage inventory in seconds.

Send-Item -To