Parece que tudo o que você precisa é:
sed -e sub1 -e sub2 file
Onde sub tem o formulário:
s/sat/cat/g
Você também pode colocar todas as suas substituições em um arquivo e executá-lo com:
sed -f scriptfile filetomodify
Existe uma maneira de convencer o m4 a substituir uma macro no meio de uma palavra?
Eu gostaria desse arquivo, day.m4:
define(Sat,Cat)dnl
Saturday
e este comando:
m4 day.m4
para produzir esta saída:
Caturday
Como mostrado, o m4 não fará isso.
Alternativamente, existe uma maneira de obter sed para executar várias substituições simultaneamente? Ou seja, sem passar o arquivo para cada substituição.
Eu posso canalizar vários comandos sed juntos ou usar uma combinação de sed e m4 e isso não é tão ruim, mas se houver uma maneira conveniente de fazer isso com um arquivo de entrada e um comando que seria preferível.
Qualquer outra ferramenta comumente disponível também seria boa.
Meu objetivo é usar isso para criar arquivos a partir de modelos. A maioria dos tokens a serem substituídos são separados por espaços.
Parece que tudo o que você precisa é:
sed -e sub1 -e sub2 file
Onde sub tem o formulário:
s/sat/cat/g
Você também pode colocar todas as suas substituições em um arquivo e executá-lo com:
sed -f scriptfile filetomodify
m4
fornece uma função de pesquisa e substituição, que pode realizar substituições em qualquer lugar, inclusive no meio da palavra, chamado patsubst :
Builtin: patsubst (string, regexp, [replacement])
Searches string for matches of regexp, and substitutes replacement for each match.
Isso não envolve a configuração de uma nova definição, portanto, ela não pode ser aplicada por padrão a todas as entradas futuras. Em vez disso, você terá que "inserir" o texto de entrada completo dentro da chamada de função:
patsubst(dnl
[...]
Saturday
[...]
,'Sat','Cat')dnl
m4 também fornece mudança de palavra :
A file being processed by
m4
is split into quoted strings, words (potential macro names) and simple tokens (any other single character). Initially a word is defined by the following regular expression:[_a-zA-Z][_a-zA-Z0-9]*
Using
changeword
, you can change this regular expression:
Infelizmente, a função changeword
não é padrão. Só está disponível se você solicitou com --enable-changeword
em tempo de compilação.
Com isso ativado, você poderia, por exemplo. forçar m4
a aceitar apenas palavras de três letras.
define('Sat','Cat')dnl
changeword('[A-Za-z][a-z]?[a-z]?')dnl
Saturday
Mas changeword
tem problemas adicionais:
regex must obey the constraint that every prefix of the desired final pattern is also accepted by the regular expression.
[...]
Tightening the lexical rules is less useful, because it will generally make some of the builtins unavailable.
O padrão acima evitaria outras definições (apenas reconhece dnl
porque são exatamente três letras). Então, além de não ser padrão, não é adequado para o que você está tentando fazer.
Tags text-processing sed macro m4