В словах принимаются только буквы, любые другие символы являются разделителями. Я хочу поменять первое слово на третье слово.
sed -E 's/([A-Za-z]+) [^A-Za-z] ([A-Za-z]+) [^A-Za-z] ([A-Za-z]+)/\3 \2 \1/' filename
Я написал это, но работает неправильно
Пример:
I 4want5to%change
Эту строку я хочу изменить на:
to 4want5I%change
Есть идеи?
Использование класса символов [[: alpha:]]
для сопоставления верхнего и нижнего регистра и отрицания [^ [: alpha :]]
для соответствия всем остальным:
sed -r 's/^([^[:alpha:]]*)([[:alpha:]]+)([^[:alpha:]]+[[:alpha:]]+[^[:alpha:]]+)([[:alpha:]]+)([^[:alpha:]]*)/\1\4\3\2\5/' file.txt
Пример:
$ sed -r 's/^([^[:alpha:]]*)([[:alpha:]]+)([^[:alpha:]]+[[:alpha:]]+[^[:alpha:]]+)([[:alpha:]]+)([^[:alpha:]]*)/\1\4\3\2\5/' <<<'I 4want5to%change'
to 4want5I%change
$ sed -r 's/^([^[:alpha:]]*)([[:alpha:]]+)([^[:alpha:]]+[[:alpha:]]+[^[:alpha:]]+)([[:alpha:]]+)([^[:alpha:]]*)/\1\4\3\2\5/' <<<'4I 4want5to%change'
4to 4want5I%change
$ sed -r 's/^([^[:alpha:]]*)([[:alpha:]]+)([^[:alpha:]]+[[:alpha:]]+[^[:alpha:]]+)([[:alpha:]]+)([^[:alpha:]]*)/\1\4\3\2\5/' <<<'Spring&summer^winter'
winter&summer^Spring
Если вы не состоите в браке с sed, это хорошая работа для perl: здесь я также предоставляю возможность указать, какие слова вы хотите поменять местами
, если "файл" содержит
I 4want5to%change
#One two three four
Spring&summer^winter
Затем эта команда
$ perl -lnse '
BEGIN {
$i = ($first - 1) * 2;
$j = ($second - 1) * 2;
}
@tokens = /([[:alpha:]]*)([^[:alpha:]]*)/g;
($tokens[$i], $tokens[$j]) = ($tokens[$j], $tokens[$i]);
print join "", @tokens;
' -- -first=1 -second=3 file
выводит
to 4want5I%change
two#One three four
winter&summer^Spring
Уберите пробелы и исправьте обратные ссылки, чтобы сохранить разделители. Кроме того, поскольку у вас есть разделитель « <пробел> 4
», вам, очевидно, необходимо разрешить несколько символов «разделителей» в строке в качестве разделителей.
Вы должны указать, что это в начале строки.
Поэтому вместо:
sed -E 's/([A-Za-z]+) [^A-Za-z] ([A-Za-z]+) [^A-Za-z] ([A-Za-z]+)/\3 \2 \1/' filename
Используйте:
sed -E 's/^([A-Za-z]+)([^A-Za-z]+[A-Za-z]+[^A-Za-z]+)([A-Za-z]+)/\3\2\1/' filename