sed :заменить шаблон в другом шаблоне

read_and_verify— это функция, в этом контексте $1— первый аргумент (здесь вы вызываете ее с одним из доменов, dbrootp или dbuserp )и $2— второй аргумент (строки, следующие за каждым из этих опций в вызовах ). Если мы расширим его для вызова:

function read_and_verify  {
    read -p "domain:" tmp1
    read -p "Please enter the domain of your web application twice:" tmp2
    if [ "$tmp1" != "$tmp2" ]; then
        echo "Values unmatched. Please try again."; return 2
    else
        read "domain" <<< "$tmp1"
    fi
}

И это то, что $1и $2делают в вашей функции.

0
25.06.2020, 16:10
5 ответов

Я думаю, что решение sed было бы слишком запутанным. Могу ли я предложить awk?

dollars.awk:

{
    for(i=1;i<=NF;i++){
        if($i ~ /\$[[:upper:]_]+\$/){    #If field contains two $
            gsub(/\$/,"@",$i) #Substitute $ with @
            gsub(/_/,".",$i)  #Substitute _ with.
            $i=tolower($i)    #Make field lowercase
        }
    }
}
1
$ awk -f dollars.awk file
Lorem @ipsum@ $dolor_sit_amet _ _ _ consectetur @adipisicing.elit@ sed do $EUISMOD_TEMPOR INCIDIDUNT_UT_LABORE$ @et.dolore.magna.aliqua@
1
28.04.2021, 23:12

Использование Perl:

$ cat file
Lorem $IPSUM$ $dolor_sit_amet _ _ _ consectetur $ADIPISICING_ELIT$ sed do $EUISMOD_TEMPOR INCIDIDUNT_UT_LABORE$ $ET_DOLORE_MAGNA_ALIQUA$
$ perl -pe 's/\$([[:upper:]_]+)\$/"@". lc $1 =~ tr[_][.]r. "@"/eg' file
Lorem @ipsum@ $dolor_sit_amet _ _ _ consectetur @adipisicing.elit@ sed do $EUISMOD_TEMPOR INCIDIDUNT_UT_LABORE$ @et.dolore.magna.aliqua@

Здесь используется Perl-выражение

s/\$([[:upper:]_]+)\$/"@". lc $1 =~ tr[_][.]r. "@"/eg

Это замена, которая применяется к подстрокам, состоящим из начального $, за которым следует один или несколько символов верхнего регистра -или символов подчеркивания, за которыми следует еще один символ $.

Шаблон замены представляет собой выражение Perl, которое заменяет все знаки подчеркивания на точки в подстроке, которая соответствует группе в скобках в шаблоне ($1), используя оператор tr, а затем опускает -результат, используя lc. Затем к результату добавляется символ @.

Именно флаг /eдля выражения s///заставляет Perl рассматривать замещающий текст как выражение Perl, а не просто как текст. Замена повторяется для всех совпадений с использованием флага /g.

2
28.04.2021, 23:12

Если ввод был сохранен в переменной $stringв оболочке zsh, вы могли бы сделать:

set -o extendedglob
string=${string//(#b)\$([A-Z]##(_[A-Z]##)#)\$/@${(L)match[1]//_/.}@}

То же, что perlдля

string=$(
  printf '%s\n' "$string" | perl -pe '
    s{\$[A-Z]+(_[A-Z]+)*\$}{lc$& =~ y/_$/.@/r}ge'
)

или:

string=$(
  printf '%s\n' "$string" | perl -pe '
    s{\$[A-Z]+(_[A-Z]+)*\$}{$& =~ y/A-Z_$/a-z.@/r}ge'
)

За исключением того, что perlработает на уровне байтов (ожидается кодирование ASCII в системах на основе ASCII -), а zshработает на уровне символов (возвращается к байтам, когда байты не могут быть декодированы в символы )в соответствии с кодировкой локали. Поведение также будет отличаться, если $stringзаканчивается символами новой строки, поскольку подстановка команд удаляет их.

1
28.04.2021, 23:12

Другой, немного более короткий GNUsed

sed -E "s/\\\$([A-Z_]+)\\\$/@\L\1@/g; :X s/(@[a-z.]+)_/\1./; tX" file

Предполагается, что @не встречается естественным образом в вашем источнике, а в $было только первоначально[A-Z_]

Lorem $IPSUM$ $dolor_sit_amet _ _ _ consectetur $ADIPISICING_ELIT$ sed do $EUISMOD_TEMPOR INCIDIDUNT_UT_LABORE$ $ET_DOLORE_MAGNA_ALIQUA$
Lorem @ipsum@ $dolor_sit_amet _ _ _ consectetur @adipisicing.elit@ sed do $EUISMOD_TEMPOR INCIDIDUNT_UT_LABORE$ @et.dolore.magna.aliqua@

Это нормально для вашего примера, но не получится, если у вас$BLAH_BLAH$blah_-> @blah.blah@blah.вместо@blah.blah@blah_

Изменить re @Quasimodo комментарий+-> *во второмsed

sed -E "s/\\\$([A-Z_]+)\\\$/@\L\1@/g; :X s/(@[a-z.]*)_/\1./; tX" file

Lorem $_IPSUM$ $dolor_sit_amet _ _ _ consectetur $ADIPISICING_ELIT$ sed do $EUISMOD_TEMPOR INCIDIDUNT_UT_LABORE$ $ET_DOLORE_MAGNA_ALIQUA$
Lorem @.ipsum@ $dolor_sit_amet _ _ _ consectetur @adipisicing.elit@ sed do $EUISMOD_TEMPOR INCIDIDUNT_UT_LABORE$ @et.dolore.magna.aliqua@
1
28.04.2021, 23:12

Perl с его Eval -d rhs команды s/// сделан специально для ths pbm:

echo "$var" |\
perl -lpe 's/(\$[A-Z_]+\$)/$1 =~ tr|$A-Z_|@a-z.|r/ge' 

Также можно использовать GNU sed.

sed -Ee '
  :a; s/\$([A-Z_]+)\$/\n\L\1\n/; ta
  :b; s/(\n[^\n]*)_/\1./; tb
  y/\n/@/
 ' 
1
28.04.2021, 23:12

Теги

Похожие вопросы