Command Substitution
Prerequisites: Quoting
Command substitution runs a command and uses its output as a value:
$(command).
printf '%s\n' a b c d > items.txt
count=$(wc -l < items.txt)
echo "There are $count items"
first=$(head -n 1 items.txt)
echo "The first is $first"
echo "Uppercase: $(echo "shout" | tr a-z A-Z)"
There are 4 items
The first is a
Uppercase: SHOUT
- The output replaces the
$(...), with trailing newlines removed. - It works inside double quotes, and can be nested.
wc -l < file(rather thanwc -l file) prints just the number, without the file name.
Everyday uses
# illustrative
today=$(date +%Y-%m-%d)
backup="backup-$today.tar.gz"
branch=$(git rev-parse --abbrev-ref HEAD)
echo "Creating $backup on branch $branch"
Creating backup-2025-04-22.tar.gz on branch main
Backticks
Older scripts use backticks: count=`wc -l < items.txt`. It means the
same thing, but $(...) is easier to read and nests cleanly — prefer it.
Common mistakes
- Forgetting quotes around the result:
ls $(find ...)breaks on names with spaces. Quote it —"$(command)"— when using it as a single value. - Using command substitution to read big outputs into a variable when a pipe would do.