Як я можу видалити все, поки шаблон не буде і все після іншого шаблону з рядка?


17

У наступному файлі:

Lorem ipsum dolor sit amet, consectetuer adipiscing elit. Ut eu metus id lectus vestibulum ultrices. Maecenas rhoncus.

Я хочу видалити все до consectetuerі все після elit.

Мій бажаний вихід:

consectetuer adipiscing elit.

Як я можу це зробити?


2
Команда може бути sed. Це також може бути perlабо навіть чистий баш.
муру

@manuel Якщо одна з цих відповідей вирішила вашу проблему, будь ласка, знайдіть хвилинку та прийміть її , натиснувши на галочку зліва. Це означатиме відповідь на питання і спосіб висловлення подяки на сайтах Stack Exchange.
тердон

Відповіді:


27

Я б використав sed

sed 's/^.*\(consectetuer.*elit\).*$/\1/' file

Розшифровано sed s / find / substitute / syntax:

  • s/^.*- заміна, що починається на початку рядка ( ^), а потім що-небудь ( .*) до ...
  • \( - запустити названий блок
  • consectetuer.*elit\.- співставити перше слово, все ( .*) до останнього слова (у цьому випадку, включаючи крапку (крапку) крапки), з якою ви хочете відповідати
  • \) - закінчення названого блоку
  • підрівняйте все інше ( .*) до кінця рядка ( $)
  • / - закінчити розділ пошуку замінника
  • \1- замінити з ім'ям блоку між \(і \)вище
  • / - закінчити заміну

1
Хороша відповідь, але вам не потрібно ^або $оскільки sed намагатиметься знайти найдовший збіг. Також, можливо, ви пропустили крапку після elit, ви можете вставити її \.за потреби.
asoundmove

2
@asoundmove Хороший улов на крапку на "еліт". - у вас досить гостре око !. Я оновив свою відповідь, щоб включити втечену крапку у візерунок. Ви також правильно підтверджуєте, що це ^і $не потрібно - я залишив їх там, оскільки запитуючий зазначив (спочатку), що він був початківець, і це може бути корисно в інших контекстах.
MikeV

Я завжди копіював вкладені рішення для седів і зламав їх, щоб відповідати моїм потребам, але завдяки цій відповіді я відчуваю, що зараз насправді розумію. Чудова відповідь
Тайлер

7

Якщо кожен рядок містить шаблон початкового та кінцевого, тоді це найпростіший спосіб зробити grep. Замість видалення початку та кінця кожного рядка ви можете просто вивести вміст між обома шаблонами. -oВаріант в GNU grepвиводить тільки матчі:

grep -o 'consectetuer.*elit' file

Примітка: як було сказано, це працює лише в тому випадку, якщо кожен рядок у файлі може бути розроблений таким чином. Знову ж таки, це 80% усіх типових випадків використання.


1

Два для циклів у AWK:

$ awk '{for(i=1;i<=NF;i++) {if ($i == "consectetuer") beginning=i; if($i== "elit.") ending=i }; for (j=beginning;j<=ending;j++) printf $j" ";printf "\n"   }' file.txt 
consectetuer adipiscing elit.

Gsub AWK:

$ awk '{gsub(/^.*consectetuer/,"consectetuer"); gsub(/elit.*$/,"elit.");print}' file.txt
consectetuer adipiscing elit.

1

Перл-шлях. Це по суті те саме , щоsed відповідь MikeV :

perl -pe 's/.*(consectetuer.*elit).*./$1/' file

В -pозначає «друк кожен рядок після застосування сценарію із заданою -e». s/foo/bar/Є оператором підстановки; він замінить fooна bar. Круглі дужки фіксують шаблон і дозволяємо використовувати його для заміни. Перший захоплений візерунок - $1другий $2тощо.

Отже, команда буде відповідати всім до consectetuer( .*consectetuer), потім усе до elit( .*elit), а потім все інше до кінця рядка ( .*) і замінить це захопленим шаблоном.


1

Я не впевнений, чому цей заголовок питання було відредаговано " з файлу " в " з рядка ", в той час як ОП не виключає можливості через кілька рядків, хоча приклад здається лише одним рядком. Як би там не було, тут може бути корисно надати рішення для кількох ліній.

Це працює для перехресних ліній:

from1=consectetuer; to2=elit; a="$(cat file)"; a="$(echo "${a#*"$from1"}")"; echo "$from1${a%%"$to2"*}$to2"

Приклади:

[xiaobai@xiaobai tmp]$ cat file
1
abc consectetuer lsl

home

def elit dd
2 consectetuer ABC elit
[xiaobai@xiaobai tmp]$ from1=consectetuer; to2=elit; a="$(cat file)"; a="$(echo "${a#*"$from1"}")"; echo "$from1${a%%"$to2"*}$to2"
consectetuer lsl

home

def elit
[xiaobai@xiaobai tmp]$ 

довідка: Розширення параметра оболонки


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