Вопрос явно гласит, что заголовки будут содержать пробелы.
В целях безопасности я предполагаю, что заголовки могут содержать точки (точки); например, «История 3.14159» или «Доктор Открытие Дулиттла ».
Мои ответы предполагают, что есть какой-то символ, который никогда не появится в оглавлении; в частности, они предполагают, что это @ .
Если в вашей таблице есть @ , замените его каким-нибудь символом, который никогда не появляется (например, # , ^ , _ , | и т.д.).
Если вы действительно используете каждый символ ASCII, вам может потребоваться использовать последовательность символов, например <@> .
Три способа сделать это с помощью sed:
Loop:
sed 's/\(.*\)\( \)/\1@\2/; :loop; s/ @/ @./; t loop; s/@//'
s/\(.*\)\( \)/\1@\2/ находит последний пробел в строке и вставляет перед ним символ @ .
:loop - это метка, похожая на маркер мили.
s/ @/ @./ (то есть s/␣␣@/␣@./ , для неоднозначности) говорит, что если перед @ есть два пробела, замените их на ␣. (пробел и точка) и переместите @ между ними.
t loop говорится, что если вышеуказанная замена прошла успешно, вернитесь к маркеру :loop и повторите.
В противном случае продолжайте
s/@// , который удаляет @ .
Таким образом, foo bar в вашей таблице будет обрабатываться следующим образом:
Initial value: foo bar url3
s/\(.*\)\( \)/\1@\2/ foo bar @ url3
s/ @/ @./ foo bar @. url3
s/ @/ @./ foo bar @.. url3
s/ @/ @./ foo bar @.. url3 (Substitution fails, so don’t loop)
s/@// foo bar .. url3
Final output: foo bar .. url3
Подавляющие цифры:
sed 's/\(.*\)\( \)/\1@@@@@@@@@@@@@@@@@@@@\2/; s/ [ @]\{20\}/ /; s/@/./g'
s/\(.*\)\( \)/\1@@@@@@@@@@@@@@@@@@@@\2/ очень похож на первую подкоманду s в первом решении; он находит последнее место на линии и вставляет строку 20 @ символов перед ним.
На самом деле это должно быть число, по крайней мере равное максимальному количеству точек, которое вам когда-либо понадобится вставить в одну строку; например, 80.
Управление строки 80 @ символы будут неудобно; вы можете заменить это
s/\(.*\)\( \)/\1<@><@><@><@><@>\2/; s/<@>/@@@@@@@@/g , который вставляет строку из пяти <@> последовательностей, а затем заменяет каждый из них со строкой 16 @ символов, что приводит к 5 × 16 = 80 @ персонажи.
s/ [ @]\{20\}/ / находит строку из 20 последовательных символов, которые являются либо пробелом, либо символом @ , которому предшествует пробел, и заменяет его только предыдущим пробелом.
Замените 20 на число из предыдущего шага.
s/@/./g заменяет каждый оставшийся @ точкой.
Таким образом, строка foo в вашей таблице будет обработана следующим образом:
Initial value: foo url1
s/\(.*\)\( \)/\1@@@@...@@@@\2/ foo @@@@@@@@@@@@@@@@@@@@ url1
s/ [ @]\{20\}/ / _[↑↑↑↑↑↑remove↑↑↑↑↑↑]
foo @@@@@@ url1
s/@/./g foo ...... url1
Используйте «место для удержания»:
sed 's/.*[^ ] /&@/; h; s/ /./g; s/\(\.*\)\./\1 /; x; G; s/@.*@//'
s/.*[^ ] /&@/ аналогичен предыдущим командам; он находит конец заголовка - если быть точным, последнее место, где за непустым символом следует пробел - и вставляет после него символ @ .
h копирует строку в область удержания.
s/ /./g заменяет все пробелы в строке точками.
s/\(\.*\)\./\1 / заменяет последнюю точку пробелом.
(Это нужно будет изменить, если URL может содержать точки, что, я думаю, вероятно.)
x меняет пространство образца и пространство удержания.
G добавляет пространство удержания к пространству шаблона.
Теперь у нас есть, по сути, две копии строки.
s/@.*@// сохраняет первую часть первой копии и вторую часть второй копии, избавляясь от содержимого посередине.
Initial value: foo bar url3
Pattern space Hold space
s/.*[^ ] /&@/ foo bar @ url3
h foo bar @ url3 foo bar @ url3
s/ /./g foo.bar.@...url3 foo bar @ url3
s/\(\.*\)\./\1 / foo.bar.@.. url3 foo bar @ url3
x foo bar @ url3 foo.bar.@.. url3
G foo bar @ url3 foo.bar.@.. url3 foo.bar.@.. url3
s/@.*@// foo bar .. url3 foo.bar.@.. url3
Final output: foo bar .. url3