Quero encontrar tudo \textbf
no meu .tex
arquivo e excluí-lo, junto com seu argumento chaves {}
. Por exemplo, quero mudar:
\textbf{text}
paratext
\textbf{text \textit{textbis}}
paratext \textit{textbis}
\textbf{\textit{\textls[-5]{textbis}} text}
para\textit{\textls[-5]{textbis}} text
\textbf{\textit{X{textbis}} text}
para\textit{X{textbis}} text
(ondeX
está uma quebra de parágrafo).
Tentei usar \\textbf\{([^}]*)\}
in \1
mas não funcionou porque para no início }
.
Responder1
Como já mencionado por @David Carlisle você não pode igualar umarbitrário{
}
número de pares bem aninhados . Mas, de uma perspectiva prática, você pode conhecer um limite superior para o nível máximo de aninhamento. Se este limite for conhecido, então é possível escrever uma expressão regular reconhecendo expressões bem entre parênteses até o nível máximo de aninhamento.
Para reconhecer \texbf{normal text}
(ninho máximo = 1) você pode fazer
\textbf{([^{}]*)}
proibir {
dentro dos colchetes é uma precaução para nunca combinar coisas com nível de aninhamento maior que o máximo.
Para combinar coisas com max nest = 2 você pode fazer o seguinte:
- primeiro você combina
\\textbf\{
- então você combina qualquer caractere que não seja colchete com
[^{}]*
- agora você pode ter terminado de combinar o conteúdo (o nível de aninhamento real é 1) e combinar o final com sucesso
\}
- ou você pode estar em uma posição com um colchete aberto. Nesse caso, você precisa combinar algo com nível de aninhamento 0 e, em seguida, combinar o colchete fechado.
As etapas 2, 3 e 4 correspondem às [^{}]*(\{[^{}]*\}[^{}]*)?
quais podem ser repetidas para que você possa combinar coisas como\textbf{bla\bla{bla}bla\bla{bla}bla}
Então, em suma, o nível máximo do ninho = 2 regex se parece com isso
\\textbf\{(([^{}]*(\{[^{}]*\}[^{}]*)?)*)\}
Podemos extrapolar o esquema para ninho máximo = N maior que 2:
\\textbf\{(([^{}]*(\{RN\}[^{}]*)?)*)\}
onde
R1 = [^{}]*
RN = ([^{}]*(\{R(N-1)\}[^{}]*)?)*
Então, por exemplo, com max nest = 3 você obtém
\\textbf\{(([^{}]*(\{(([^{}]*(\{[^{}]*\}[^{}]*)?)*)\}[^{}]*)?)*)\}
o que é suficiente para capturar todos os casos mencionados na pergunta.
Responder2
se você puder usar quantificadores não gananciosos,
substituir \\textbf\{(.*?)\}
com\1
Ok, como Werner mencionou, isso só funciona com comandos não aninhados. Eu acho que não existe uma solução simples para isso e é um trabalho de analisador.
Se você quiser fazer isso de qualquer maneira com Regex, você pode substituir os não- \textbf
colchetes por um símbolo não usado e, no final, remover os \textbf
-colchetes e alterar os símbolos de volta para colchetes:
1) Substitua todos os colchetes de fechamento \textbf
pelo }
Símbolo A,
2) Substitua todos os não \textbf
colchetes de abertura {
pelo Símbolo B,
3) Substitua o restante \textbf{
e }
(de \textbf
) por nada,
4) Substitua o Símbolo A por {
e o Símbolo B por }
@Etapas 1 e 2:
Passo 1: }
-> Smybol A, no meu exemplo alemão ö
:
(?<=(?<!\\textbf)\{(?!.*?\{)).*?\}
Substitua esta expressão por \1ö
(não encontrei uma solução melhor para esta expressão)
Então faça o Passo 2: {
-> Símbolo B, no meu exemplo alemãoä
(?<!\\textbf)\{(?!.*?\{)
Substitua esta expressão por ä
.
Refaça essas etapas quantos níveis aninhados você tiver. Em seguida, siga as etapas restantes.
Bem, isso é mais uma macro regex e uma solução alternativa do que uma regex sólida, mas deve funcionar.