Я собираюсь отправить форму с помощью cURL, где часть содержимого берется из другого файла, выбранного с помощью sed
Если param1
используется шаблон совпадения строк из другого файла sed
, команда ниже будет работать нормально:
curl -d param1="$(sed -n '/matchpattern/p' file.txt)" -d param2=value2 http://example.com/submit
Теперь перейдем к проблеме. Я хочу показать только текст между 2 соответствующими шаблонами, исключая сам соответствующий шаблон.
Скажем, file.txt
содержит:
Bla bla bla
firstmatch
It is a long established fact that a reader will be distracted by the readable content of a page when looking at its layout.
secondmatch
The point of using Lorem Ipsum is that it has a more-or-less normal distribution of letters, as opposed to using 'Content here, content here', making it look like readable English.
В настоящее время многие команды "Beetween 2 Match Pattern" sed
не удаляются firstmatch
и secondmatch
.
Я хочу, чтобы результат стал:
It is a long established fact that a reader will be distracted by the readable content of a page when looking at its layout.
text-processing
sed
lokomika
источник
источник
Ответы:
Вот один из способов сделать это:
Объяснено: от первой строки до строки, совпадающей с первым соответствием , удалите. От строки, соответствующей второму совпадению до последней строки, удалите.
источник
В awk:
источник
Другое
sed
решение потерпит неудачу, еслиfirstmatch
произойдет в 1-й строке 1 .Проще говоря, используйте один диапазон и пустое регулярное выражение 2 :
либо напечатайте все в этом диапазоне, кроме концов диапазона (автоматическая печать отключена) 3 :
или, короче, удалите все, что не находится в этом диапазоне, а также удалите конец диапазона:
1: Причина в том, что если вторым адресом является регулярное выражение, то проверка на конечное совпадение начнется со строки, следующей за строкой, которая соответствует первому адресу .
Поэтому,
/firstmatch/
никогда не оценивается для 1-й строки ввода,sed
просто удалит его, так как он соответствует номеру строки в,1,/RE/
и перейдет ко 2-й строке, где он проверяет, соответствует ли строка/firstpattern/
2: Когда REGEX пуст (т.е.
//
)sed
ведет себя так, как если бы был указан последний REGEX, использованный в последней примененной команде (либо в качестве адреса, либо в качестве части замещающей команды).3:
;}
синтаксис для современныхsed
реализаций; с более старыми используйте либо символ новой строки вместо точки с запятой, либо отдельные выражения, напримерsed -n -e '/firstmatch/,/secondmatch/{//!p' -e '}' infile
источник
//
делает (внутри{…}
)?//
означает последнее использованное регулярное выражение; из всего, что я прочитал, должно быть/secondmatch/
. В ходе тестирования я проверил, работает ли ваша команда, и поэтому я пришел к выводу, что она работает как/firstmatch|secondmatch/
(что вы подтвердили), но я не могу найти никакой документации (даже документа POSIX, на который вы ссылались, или GNU Руководство пользователя ), которое описывает это поведение. … (Продолжение)sed
: (1) Если я это сделаю/first/,4
, то//
действует как/first/
. (2) Если я это сделаю2,/second/
, то//
получит ошибку «нет предыдущего регулярного выражения». (Я считаю, что это явный отказ следовать указанному поведению.) (3) Добавление--posix
не меняет ничего из вышеперечисленного. (II) В других программах: (4) Invi
, после/first/,/second/
,//
действует как/second/
(и другие формы также являются рациональной реализацией документированного правила). … (Продолжение)awk
похоже, нет понятия «последний использованный RE»;//
относится к не символу до или после любого символа. (Я приглашаю вас попробоватьecho -- | awk '{ gsub(//, "cha"); print }'
.)/first|second/
. Повезло тебе. Я упоминаю другие программы, чтобы продемонстрировать, что это не какое-то общесистемное соглашение о регулярных выражениях. Кто бы ни добавил этоsed
, не удосужился добавить этоvim
, где это имело бы почти такой же смысл. :-)