patternbashModerate
IFS manipulation to split strings safely without word splitting side effects
Viewed 0 times
IFSword splittingsplit stringreaddelimiterCSVfield separator
Problem
Developers abuse word splitting by relying on default IFS to split strings, which breaks on filenames with spaces. Changing IFS globally affects all subsequent splitting in the script.
Solution
Change IFS locally (in a subshell or with local scoping) or use 'read' with a custom IFS.
# Split a colon-delimited string safely
IFS=':' read -ra parts <<< "$PATH"
for p in "${parts[@]}"; do echo "$p"; done
# Temporarily change IFS with local scoping
parse_csv() {
local IFS=','
read -ra fields <<< "$1"
printf '%s\n' "${fields[@]}"
}
# Restore IFS explicitly
old_IFS="$IFS"
IFS=','
# ... work ...
IFS="$old_IFS"
# Split a colon-delimited string safely
IFS=':' read -ra parts <<< "$PATH"
for p in "${parts[@]}"; do echo "$p"; done
# Temporarily change IFS with local scoping
parse_csv() {
local IFS=','
read -ra fields <<< "$1"
printf '%s\n' "${fields[@]}"
}
# Restore IFS explicitly
old_IFS="$IFS"
IFS=','
# ... work ...
IFS="$old_IFS"
Why
IFS is a global variable. Changing it affects all unquoted expansions and word splitting until it is restored. Using 'local IFS=...' inside a function scopes the change to that function only.
Gotchas
- IFS= (empty) disables all word splitting — useful with read to preserve whitespace
- read without IFS= strips leading/trailing whitespace from each field
- IFS changes affect read, for-loop expansion, and unquoted $var but not quoted "$var"
- Unsetting IFS restores default behavior (space/tab/newline) same as IFS=$' \t\n'
Code Snippets
IFS manipulation for safe string splitting
# Split PATH into array
IFS=':' read -ra path_parts <<< "$PATH"
for dir in "${path_parts[@]}"; do
echo "$dir"
done
# Read CSV line preserving spaces
line="Alice,30,New York"
IFS=',' read -r name age city <<< "$line"
echo "Name: $name, City: $city"
# Read a file line by line without mangling whitespace
while IFS= read -r line; do
echo "Got: $line"
done < file.txtContext
Parsing delimited strings (CSV, PATH, colon-separated values) in bash
Revisions (0)
No revisions yet.