Як я можу додати рядок після кожного рядка у файлі Bash?


112

Як додати рядок після кожного рядка у файлі за допомогою bash? Чи можна це зробити за допомогою команди sed, якщо так, як?

Відповіді:


188

Якщо ви sedдозволяєте редагувати місце за допомогою -iпараметра:

sed -e 's/$/string after each line/' -i filename

Якщо ні, потрібно створити тимчасовий файл:

typeset TMP_FILE=$( mktemp )

touch "${TMP_FILE}"
cp -p filename "${TMP_FILE}"
sed -e 's/$/string after each line/' "${TMP_FILE}" > filename

Чому ви touchтимчасовий файл? І я зробив би sedумовою, що команда cpможе бути втрачена, або оригінал може бути втрачений
Призупинено до подальшого повідомлення.

Я торкнувся файлу, щоб швидко резервувати тимчасову назву. Це може не знадобитися. Я думаю, ти маєш рацію в тому, щоб умовити команду sed на успіх cp. Чому б не відредагувати код, щоб виправити це. Я не заперечу проти! З повагою, Том
Том ДеГісі,

Що з додаванням рядка перед рядком?
Oxwivi

10
@Oxwivi: sed -e 's/^/string after each line/' -i filename $ означає кінець рядка. ^ означає початок рядка.
Том ДеГісі

Якщо я перекладаю на sed, sed 's/^/string after each line/'виконує те, що я очікував (попередньо до кожного рядка), але sed 's/^/string after each line/'ні (він замінює весь рядок моїм рядком додавання). Що дає? Будь-які ідеї @TomDeGisi?
Філадами

17

Я вважаю за краще використовувати awk. Якщо є лише один стовпець, використовуйте $0, інакше замініть його останнім стовпцем.

Односторонній,

awk '{print $0, "string to append after each line"}' file > new_file

або це,

awk '$0=$0"string to append after each line"' file > new_file

1
Також для додавання номерів рядків (як це було в моєму випадку) можна використовувати NRзмінну:awk '{print $0, NR}'
andrybak

2
@optimus Я спробував ваш метод, але отримавши додатковий простір, але будь-яка ідея, як їх видалити?
Аділ Саджу

@AdilSaju sed 's/ //g'це працювало на мою вимогу, але це видалить простір у кожному рядку, ось який варіант gдля та скрізь у рядку.
Еклавія

@AdilSaju, будь ласка, додайте деталі. Краще поставити нове запитання.
Optimus Prime

@AdilSaju awk Видалити , подобається {print $0"string to append after each line"}.
Куліп


4
  1. Чиста оболонка POSIX і sponge:

    suffix=foobar
    while read l ; do printf '%s\n' "$l" "${suffix}" ; done < file | 
    sponge file
  2. xargsі printf:

    suffix=foobar
    xargs -L 1 printf "%s${suffix}\n" < file | sponge file
  3. Використання join:

    suffix=foobar
    join file file -e "${suffix}" -o 1.1,2.99999 | sponge file
  4. Інструменти Shell , використовуючи paste, yes, head і wc:

    suffix=foobar
    paste file <(yes "${suffix}" | head -$(wc -l < file) ) | sponge file

    Зверніть увагу , що pasteвставляє Tab символ перед тим $suffix.

Звичайно, spongeможна замінити тимчасовий файл, після чого mvнад початковим іменем файлу, як і деякі інші відповіді ...


1
Жодне з них не є переважним sed, якщо тільки ресурси дуже обмежені.
agc

Мені подобається не-sed рішення. sedне потрібна для такої простої роботи.
Брюс

1

Я віддаю перевагу echo. використовуючи чистий bash:

cat file | while read line; do echo ${line}$string; done

-9

Sed трохи некрасивий, ви можете зробити це так елегантно:

hendry@i7 tmp$ cat foo 
bar
candy
car
hendry@i7 tmp$ for i in `cat foo`; do echo ${i}bar; done
barbar
candybar
carbar

2
Помилка для файлів з більшою кількістю рядків, ніж максимальна межа аргументу оболонки. Спробуйте: cat foo | під час читання a; виконувати бар $ {a}; зроблено чи щось подібне замість цього; у більшості випадків це підходить для заміни.
alex

1
Він також провалюється для ліній з пробілами в них.
Призупинено до подальшого повідомлення.

1
Е, ні, це не підводить Денніс. максимальна межа аргументу оболонки? Крик, якого ти піддаєш.
хендрі

Так, це: $ cat foo foo bar baz alex @ armitage: ~ $ for i in cat foo; do echo $ {i} бар; зробив foobar barbar bazbar, але після деяких тестів я можу помилитися з приводу своїх міркувань, але Денніс має рацію
alex

3
@hendry Так, це не вдається для рядків з пробілами, наприклад, echo "foo bar" | (for i in `cat`; do echo ${i}bar; done)які друкують 2 рядки, навіть якщо вхід становить 1 рядок foo barcatчитання з stdin замість файлу для цього не має ніякої різниці).
Гайд
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.