Сценарий, который Вы отправили, преобразовывает 4*n пробелы в n вкладки, только если тем пробелам предшествуют только вкладки.
Если Вы хотите заменить 4 пробелов 2 пробелами, но только в добавлении отступа, в то время как возможно сделать это с sed, я рекомендую Perl вместо этого.
perl -pe 's{^((?: {4})*)}{" " x (2*length($1)/4)}e' file
В sed:
sed -e 's/^/~/' -e ': r' -e 's/^\( *\)~ /\1 ~/' -e 't r' -e 's/~//' file
Можно хотеть использовать indent
вместо этого.
Да существует множество способов сделать это. Можно использовать awk
, perl
, или bash
сделать эти операции также. В целом, хотя sed
вероятно, больше всего кстати инструмент для того, чтобы сделать эти типы задач.
Скажите, что у меня есть эти демонстрационные данные в файле data.txt
:
foo bar 12,300.50
foo bar 2,300.50
abc xyz 1,22,300.50
awk
$ awk '{gsub("foo", "foofoofoo", $0); print}' data.txt
foofoofoo bar 12,300.50
foofoofoo bar 2,300.50
abc xyz 1,22,300.50
Perl
$ perl -pe "s/foo/foofoofoo/g" data.txt
foofoofoo bar 12,300.50
foofoofoo bar 2,300.50
abc xyz 1,22,300.50
Вышеупомянутые примеры могут непосредственно изменить файлы также. Пример Perl тривиален. Просто добавьте -i
переключатель.
$ perl -pie "s/foo/foofoofoo/g" data.txt
Для awk
это является немного менее прямым, но столь же эффективным:
$ { rm data.txt && awk '{gsub("foo", "foofoofoo", $0); print}' > data.txt; } < data.txt
Этот метод создает подоболочку с фигурными скобками '{...}' Где файл перенаправляется в него через это:
$ { ... } < data.txt
После того как файл был перенаправлен в подоболочку, он удален и затем awk
выполняется против содержания файла, который был считан в подоболочки STDIN. Это содержание затем обрабатывается awk
и записанный обратно к тому же имени файла, которое мы просто удалили, эффективно заменив его.
Классическая альтернатива для однобуквенных замен tr
команда, которая должна быть доступной в примерно любой системе:
$ echo "foobar" | tr a b
foobbr
tr
лучше, чем sed
для этого на самом деле начиная с использования sed
(уже не говоря о perl
или awk
) поскольку однобуквенные замены похожи на использование молотка саней для уничтожения мухи.
grep
не разработан для этого, это не изменяет свой вход, это только перерывает его.
С другой стороны, можно использовать возможности замены некоторых оболочек. Сюда использование ksh
, zsh
или bash
синтаксис:
$ foo="foobar"
$ echo "${foo//a/b}"
foobbr
Мы могли дать Вам более определенные ответы, если бы Вы объяснили точно, какую проблему Вы пытаетесь решить.
echo "$foo" | sed 's/a/b/i
или дайте класс символов: echo ${foo//[aA]/b}
.
– terdon♦
23.02.2017, 12:03
Если Вы работаете с файлом, а не потоком, Вы могли бы использовать стандартный текстовый редактор, ed
:
printf '%s\n' ',s/a/b/g' w q | ed file.txt
Это должно быть доступно на любом *, отклоняют. Запятая в ',s/a/b/g'
говорит ed
работать над каждой строкой (можно также использовать %
, который будет более знакомым, если Вы привыкнете к энергии), и остальная часть ее является стандартным поиском и заменой. w
говорит, что это для записи (сохранило) файл, q
говорит этому выходить.
Отметьте это, в отличие от sed's -i
опция (и подобные опции в других инструментах), это на самом деле редактирует файл, оперативный вместо того, чтобы обмануть с временными файлами.
Я не думаю, что возможно получить эту работу с потоками, но затем я действительно не знаю много о ed
и я не был бы удивлен, имеет ли это на самом деле ту возможность (философия Unix, являющаяся, что это).
Используя команду редактора предка (в который -s
средства, тихие (тихий) и запятая перед средствами команд, выполняются на всех строках):
Просто печать на STDOUT:
ed -s file <<!
,s/a/b/g
,p
q
!
оперативная замена:
ed -s file <<!
,s/a/b/g
w
q
!
Вы можете использовать Vim в режиме Ex:
ex -s -c '%s/a/b/g|x' file
%
выбрать все строки
s
заменить
g
глобальную замену
x
сохранить и закрыть
Если вы используете ОС Linux, например, Ubuntu Desktop, как и я, у вас будет установлен python
.
С помощью Python мы можем заменить текст, как показано ниже
result=$(python << EOT
s = '$your_string_in_shell_script'
r = s.replace('text to replace', 'replaced by this text')
print(r)
EOT)
echo $result
sed
не я. Sed является соответствующим инструментом для того, чтобы сделать замены, такие как это, и он, очевидно, просит лучше понимать роли этих инструментов, таким образом показывая кому-то эти вещи, хотя плохо, чрезвычайно образование в показе их почему. Слишком много раз знающие люди просто заявляют, "не делают этого", не объясняя, почему, таким образом, я. Но спасибо за то, что, по крайней мере, оставили комментарий, относительно почему Вы DV. – slm♦ 02.11.2013, 18:37