розділити довгу лінію на роздільнику


21

Яку команду я можу використовувати для поділу вводу таким чином:

foo:bar:baz:quux

в це?

foo
bar
baz
quux

Я намагаюся розібратися з cutкомандою, але, здається, вона працює лише з фіксованою кількістю введення, як-от "перші 1000 символів" або "перші 7 полів". Мені потрібно працювати з довільно довгим введенням.


5
Ви маєте на увазі, як tr : '\n' < input?
jw013

Яку оболонку ви використовуєте? баш?
Гленн Джекман

Відповіді:


34

Є кілька варіантів:

  • tr : \\n
  • sed 's/:/\n/g'
  • awk '{ gsub(":", "\n") } 1'

Ви також можете це зробити чисто bash:

while IFS=: read -ra line; do
    printf '%s\n' "${line[@]}"
done

3
Зауважте, що використання \nв такому рядку заміни буде працювати в GNU sed, але не вдасться в більшості інших реалізацій sed.
wjv

@chrisdown Чи є спосіб отримати перші два для роботи в AIX?
кокедуд


4

Якщо ваш греп підтримує, -oви можете зробити це так:

grep -o '[^:]\+'

Або з awk, встановивши роздільник записів на ::

awk -v RS=: 1

Або з вирізанням GNU:

cut -d: --output-delimiter=$'\n' -f1-

Редагувати

Як зазначає Кріс нижче, це залишить зворотний новий рядок, цього можна уникнути, якщо ваш awk підтримує вказівку RSяк регулярний вираз (протестований GNU awk):

awk -v RS='[:\n]' 1

Ваш awkприклад залишить (мабуть, небажаний) прорив нового рядка.
Кріс Даун

@ChrisDown: ви праві, цього можна уникнути, якщо RS може бути регулярним виразом.
Тор

-1

У деяких рядках у мене були проблеми з рішеннями вище. Але це працювало для мене:

echo $string | sed 's/\\n/ /g' | tr " " \\n

Як написано, це не перетворює вхід для прикладу OP.
kbulgrien
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.