Вам нужно будет сделать это в цикле:
s/\(^.*title="[^" ]*\) \([^"]*".*$\)/\1_\2/
или (быстрее)
s/\(title="[^" ]*\) \([^"]*"\)/\1_\2/
или (возможно, снова быстрее, потому что зачем добавлять другое совпадение, чтобы заменить его само?!)
s/\(title="[^" ]*\) /\1_/
и использовать тест sed -and-branch, повторяя попытку замены до тех пор, пока не перестанут вноситься изменения. Смысл шаблонов в этой команде состоит в том, чтобы разделить строку на первом (оставшемся) пробеле и заменить это пробел знаком подчеркивания.
Вот сценарий:
#!/bin/sh
sed -e ':loop' \
-e 's/\(title="[^" ]*\) \([^"]*"\)/\1_\2/' \
-e 't loop' foo.out
diff -u foo.in foo.out
В первоначальном ответе использовался более широкий шаблон, но @ g-man прокомментировал, что в этом нет необходимости. Это было медленнее, о чем свидетельствует синхронизация sed для файла размером 10 МБ (проверено с GNU sed на Debian 7):
$ ./foo1
27.03user 0.01system 0:27.18elapsed 99%CPU (0avgtext+0avgdata 1104maxresident)k
0inputs+0outputs (0major+333minor)pagefaults 0swaps
9.54user 0.00system 0:09.60elapsed 99%CPU (0avgtext+0avgdata 972maxresident)k
0inputs+0outputs (0major+301minor)pagefaults 0swaps
В OSX разница не такая большая:
$ ./foo1
real 0m11.943s
user 0m11.897s
sys 0m0.024s
real 0m5.858s
user 0m5.839s
sys 0m0.014s
Интересно, что более широкий шаблон не работает с Solaris. sed (но более короткий делает). Он не соответствует ни одному концу строки в группе \ (
и \)
, в то время как BSD и GNU делают это. Аналогичным образом, он работает с HPUX 11.31 и AIX 7.1
POSIX sed использует BRE, а функция группировки покрывается 9.3.6 BRE, сопоставление нескольких символов :
Подвыражение может быть определено в BRE заключив его между парами символов
"\ ("
и"\)"
. Такое подвыражение должно соответствовать тому, что было бы сопоставлено без «(» и «)», за исключением того, что привязка внутри подвыражений является необязательным поведением; см. Привязка выражений BRE . Подвыражения могут быть вложены произвольно.
9.3.8 Привязка выражения BRE объясняет этот термин:
BRE может быть ограничен соответствием строк, которые начинают или заканчивают строку; это называется «привязкой».
Итак, в контексте стандарта, как он реализован, это известное ограничение Solaris sed
, которое стандарт допускает как «необязательное» поведение.
Дополнительная литература:
Вот предложение по установке OpenSUSE Tumbleweed (по состоянию на апрель 2019 г. )на новый ПК (Asus G20 )с графическими контроллерами Intel и nVidia (GTX970 ):
в настройках BIOS параметры BOOT можно продолжать использовать режим UEFI, но сменить ОС с "Windows" на "Другая ОС"
Если ваша установка OpenSUSE дает сбой, зависает или завершается с непредвиденной ошибкой, попробуйте добавить эти параметры к строке загрузки ядра (нажмите «e» на экране загрузки Grub ):textmode=1 nomodeset acpi=off splash=verbose
вам может потребоваться делать это каждый раз, когда вы запускаете опцию «Установка» или «Обновление»
после установки на Asus G20 постоянно рекомендуются следующие параметры ядра, которые можно установить в параметрах Yast, Boot, Kernel :pci=acpi pci=noaer splash=silent
также предлагается сначала установить минимальную систему в графическом режиме без -, просто чтобы запустить систему, а затем загрузите драйверы nVidia для X с помощью Yast из репозитория Nvidia OpenSUSE, который описан здесь:https://en.opensuse.org/SDB:NVIDIA_drivers
Установите соответствующий вашей видеокарте. Я использовал для GTX970:
Эта проблема была передана в OpenSUSE.
Возможные причины :-PCI Advanced Error Reporting (AER )заполняет системный журнал -возможные конфликты между контроллерами Intel и nVidia до установки драйверов nVidia вызывают сбой
[конец]