извлечь часть строки с помощью sed

9
ls lib/oracle-11.2.0.3.0.txt | sed 's/lib.\([oracle.*]\)\.txt/\1/'

Он дает целую строку, а не только часть оракула, до .txt Что я делаю не так?

Я могу сделать это с помощью awk следующим образом, но не уверен, почему sed не дает желаемого результата.

echo "lib/oracle-11.2.0.3.0.txt" | awk -F/ '{print substr($2,1,index($0,".txt")-1);}'
would_like_to_be_anon
источник

Ответы:

12

[oracle.*]означает "один из персонажей o, r, a, c, l, e, ., или *". Следовательно, ваше регулярное выражение будет соответствовать только что-то вроде

lib+c.txt

а не фактическое имя файла вы передаете его. Если вы удалите [и ]из регулярного выражения, он будет работать нормально:

ls lib/oracle-11.2.0.3.0.txt | sed 's/lib.\(oracle.*\)\.txt/\1/'

Тем не менее, гораздо более простой способ сделать это

basename lib/oracle-11.2.0.3.0.txt .txt

или, если вы действительно хотите, чтобы файл пришел stdin:

ls lib/oracle-11.2.0.3.0.txt | xargs -I{} basename {} .txt
RICi
источник
7

Вот еще несколько способов сделать это:

  1. Perl

    echo "lib/oracle-11.2.0.3.0.txt" | perl -pe 's/.+(oracle.+)\.txt/$1/'
    
  2. sed

    echo "lib/oracle-11.2.0.3.0.txt" | sed 's/.*\(oracle.*\)\.txt/\1/'
    
  3. cut

    echo "lib/oracle-11.2.0.3.0.txt" | cut -d'/' -f 2 | cut -d '.' -f 1-5
    
  4. basename а также bash

    echo "lib/oracle-11.2.0.3.0.txt" | while read n; do 
      echo $(basename ${n/.txt//}); 
    done
    
Тердон
источник
1

Как насчет использования cut

echo "lib/oracle-11.2.0.3.0.txt" | cut -c5-19
jrnetclueless
источник