'How can I print a newline as \n in Bash?
Basically, I want to achieve something like the inverse of echo -e
.
I have a variable which stores a command output, but I want to print newlines as \n.
Solution 1:[1]
Here's my solution:
sed 's/$/\\n/' | tr -d '\n'
Solution 2:[2]
If your input is already in a (Bash) shell variable, say $varWithNewlines
:
echo "${varWithNewlines//$'\n'/\\n}"
It simply uses Bash parameter expansion to replace all newline ($'\n'
) instances with literal '\n'
each.
If your input comes from a file, use AWK:
awk -v ORS='\\n' 1
In action, with sample input:
# Sample input with actual newlines created with ANSI C quoting ($'...'),
# which turns `\n` literals into actual newlines.
varWithNewlines=$'line 1\nline 2\nline 3'
# Translate newlines to '\n' literals.
# Note the use of `printf %s` to avoid adding an additional newline.
# By contrast, a here-string - <<<"$varWithNewlines" _always appends a newline_.
printf %s "$varWithNewlines" | awk -v ORS='\\n' 1
awk
reads input line by line- by setting
ORS
- the output record separator to literal'\n'
(escaped with an additional\
so thatawk
doesn't interpret it as an escape sequence), the input lines are output with that separator 1
is just shorthand for{print}
, i.e., all input lines are printed, terminated byORS
.
Note: The output will always end in literal '\n'
, even if your input does not end in a newline.
This is because AWK terminates every output line with ORS
, whether the input line ended with a newline (separator specified in FS
) or not.
Here's how to unconditionally strip the terminating literal '\n'
from your output.
# Translate newlines to '\n' literals and capture in variable.
varEncoded=$(printf %s "$varWithNewlines" | awk -v ORS='\\n' 1)
# Strip terminating '\n' literal from the variable value
# using Bash parameter expansion.
echo "${varEncoded%\\n}"
By contrast, more work is needed if you want to make the presence of a terminating literal '\n'
dependent on whether the input ends with a newline or not.
# Translate newlines to '\n' literals and capture in variable.
varEncoded=$(printf %s "$varWithNewlines" | awk -v ORS='\\n' 1)
# If the input does not end with a newline, strip the terminating '\n' literal.
if [[ $varWithNewlines != *$'\n' ]]; then
# Strip terminating '\n' literal from the variable value
# using Bash parameter expansion.
echo "${varEncoded%\\n}"
else
echo "$varEncoded"
fi
Solution 3:[3]
You can use printf "%q"
:
eol=$'\n'
printf "%q\n" "$eol"
$'\n'
Solution 4:[4]
A Bash solution
x=$'abcd\ne fg\nghi'
printf "%s\n" "$x"
abcd
e fg
ghi
y=$(IFS=$'\n'; set -f; printf '%s\\n' $x)
y=${y%??}
printf "%s\n" "$y"
abcd\ne fg\nghi
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
Solution | Source |
---|---|
Solution 1 | mklement0 |
Solution 2 | Peter Mortensen |
Solution 3 | anubhava |
Solution 4 |