Замените \ n новой строкой в ​​sed

23

Я так запутался с множеством опций GNU sed, POSIX sedи BSD sed. Как заменить литерал \nсимволом новой строки, используя эти три sedтипа?

Авинаш Радж
источник
У них много разных вещей, какую часть вы хотите знать?
cuonglm
@ Gnouc, я думаю, теперь все ясно.
Авинаш Радж
1
Вы смотрели на этот вопрос ?
Groxxda
2
Что вы хотите, чтобы произошло на входе, как foo\\nbarили foo\\\nbar?
Жиль "ТАК - перестань быть злым"
просто, foo \\ в следующей строке это будет бар.
Авинаш Радж

Ответы:

30
sed 's/\\n/\
/g'

Обратите внимание на обратную косую черту непосредственно перед нажатием return в строке замены.

unxnut
источник
это работает для всех видов седа?
Авинаш Радж
Я считаю, что это должно; Я тестировал только на Linux, используя версию GNU.
unxnut
11
@AvinashRaj. Это POSIX, и он работал с оригинальной sedкомандой в Unix v7 в 1979 году. Единственное место, где это может не сработать, - это sedупрощенные реализации без POSIX, подобные некоторым упрощенным реализациям на основе busybox. Это не сработает в csh, но это проблема csh.
Стефан Шазелас
Так \\nкак используется в поисковой части, почему бы не использовать \nв замене? первое, кажется, подразумевает, что второе существует. то есть. почему не это$ echo '1\n2'|sed 's/\\n/\n/g'
В данном случае, \nэто литерал, означающий, что он отображается в виде двух символов: за ним следует abackslash n, а не как один символ новой строки. Следовательно, два обратных слеша для того, чтобы сделать обратный слэш буквальным, а затемn
unxnut
9

Поскольку у вас уже есть переносимый sedответ, я просто упомяну, что sedон редко является лучшим инструментом, если вам нужно каким-то образом манипулировать символами новой строки. Perl почти так же переносим, ​​как sedи установлен по умолчанию на большинстве систем * nix и может очень легко справиться с этим:

printf '%s\n' 'aa\nbb' | perl -pe 's/\\n/\n/g'

Другой очень портативный выбор awk:

printf '%s\n' 'aa\nbb' | awk  '{gsub("\\\\n","\n")};1'

В Solaris не забудьте использовать стандартный awk в / usr / xpg4 / bin, тот, что в / bin, является историческим и не должен использоваться для новых сценариев.

Тердон
источник
Я бы сказал , что awkимеет аналогичные проблемы с переносимостью (Это мой awkстарый добрый awk, nawkили gawk?). На самом деле, версия в моих коробках Solaris не хватает gsub(). Мой голос здесь за Perl ( perl -nlawe '...'приближается к автоматическому поведению awk).
arielCo
2
@arielCo: Для awkмобильности, придерживайтесь версии, awkкоторая совместима с POSIX, и используйте только эти функции, и все будет в порядке. На Солярисе вы найдете один как /usr/xpg4/bin/awk.
Тщательный анализ
@terdon как насчет этого echo "aa\nbb" | awk '{gsub(/\\n/,"\n");}1;'?
Авинаш Радж
@arielCo на самом деле, awk более переносим, чем perl. Мой второй подход awk, который не использует, gsub()должен работать почти везде. Даже busybox имеет awk.
тердон
1
gsub () - это POSIX (gsub, был добавлен в SVR3.1, POSIX awk основан на SVR4 с несколькими дополнениями, см. руководство gawk для получения дополнительной информации), gensub () - расширение GNU. Оригинальный awk все еще находился в Solaris как / bin / awk, не поддерживал gsub (), но также не поддерживал многосимвольную FS.
Стефан Шазелас
1

Если Holdspace пусто, вы также можете сделать:

sed '/\\n/G;s/\\n\(.*\)\(.\)/\2\1/;P;D'

... но ответ uxnut уже быстрее и проще, так что вы можете принять его как хотите.

Еще одна посторонняя возможность:

INPUT | sed -n l | while read v ; do printf "${v%?}" ; done

Но будьте осторожны, ^ который переводит все стандартные \обратные \bслэши в стиле C - такие как пробел, \rэтанол, \00восьмерик и прочее.

mikeserv
источник
0

Со gnu sedследующим также работает:

gsed -n -e 'H;${x;s/\\n/\n/g;p;}'
Дирк Хоффманн
источник
-2

Вам нужно решение в sed, и это уже дано ниже. Но я хотел добавить еще одну возможность, что ИМХО проще и быстрее,

tr -d "\n"
jpmuc
источник
1
что это делает? удалить все новые строки из ввода?
mikeserv
Да, это именно то, что он делает
jpmuc
5
но почему? какое это имеет отношение к вопросу вообще?
mikeserv
1
Это просто удаляет "\ n", когда возникает вопрос, как заменить строку "\ n" на настоящие символы новой строки.
spuder