Eliminar la funcionalidad de la macro mediante una expresión regular

Eliminar la funcionalidad de la macro mediante una expresión regular

Quiero encontrar todo \textbfen mi .texarchivo y eliminarlo, junto con sus llaves de argumento {}. Por ejemplo, quiero cambiar:

  1. \textbf{text}atext

  2. \textbf{text \textit{textbis}}atext \textit{textbis}

  3. \textbf{\textit{\textls[-5]{textbis}} text}a\textit{\textls[-5]{textbis}} text

  4. \textbf{\textit{X{textbis}} text}a \textit{X{textbis}} text(donde Xhay un salto de párrafo).

Intenté usarlo \\textbf\{([^}]*)\}pero \1no funcionó porque se detiene al principio }.

Respuesta1

Como ya mencionó @David Carlisle, no puedes igualar unarbitrario{ }número de pares bien anidados . Pero, desde una perspectiva práctica, es posible que conozca un límite superior en el nivel máximo de anidación. Si se conoce este límite, entonces es posible escribir una expresión regular que reconozca expresiones bien entre paréntesis hasta el nivel máximo de anidamiento.

Para reconocer \texbf{normal text}(nido máximo = 1) puedes hacer

\textbf{([^{}]*)}

prohibir {dentro de los corchetes es una precaución para nunca hacer coincidir cosas con un nivel de anidamiento mayor que el máximo.

Para hacer coincidir cosas con nido máximo = 2, puedes hacer lo siguiente:

  1. primero coincides\\textbf\{
  2. luego combinas cualquier carácter que no sea paréntesis con[^{}]*
  3. ahora es posible que haya terminado de hacer coincidir los contenidos (el nivel de anidación real es 1) y felizmente haga coincidir el final\}
  4. o podría estar en una posición con un soporte abierto. En este caso, debe hacer coincidir algo con el nivel de anidación 0 y luego hacer coincidir el corchete cerrado.

Los pasos 2, 3 y 4 corresponden a [^{}]*(\{[^{}]*\}[^{}]*)?los cuales pueden repetirse para que puedas unir cosas como\textbf{bla\bla{bla}bla\bla{bla}bla}

Entonces, en general, el nivel máximo de nido = 2 expresiones regulares se ve así

\\textbf\{(([^{}]*(\{[^{}]*\}[^{}]*)?)*)\}

Podemos extrapolar el esquema para nido máximo = N mayor que 2:

\\textbf\{(([^{}]*(\{RN\}[^{}]*)?)*)\}

dónde

R1 = [^{}]*
RN = ([^{}]*(\{R(N-1)\}[^{}]*)?)*

Entonces, por ejemplo, con nido máximo = 3 obtienes

\\textbf\{(([^{}]*(\{(([^{}]*(\{[^{}]*\}[^{}]*)?)*)\}[^{}]*)?)*)\}

lo cual es suficiente para captar todos los casos que mencionas en la pregunta.

Respuesta2

si puedes usar cuantificadores no codiciosos,

reemplazar \\textbf\{(.*?)\}con\1

Ok, como mencionó Werner, esto solo funciona con comandos no anidados. Creo que no existe una solución sencilla para esto y es un trabajo de analizador.

Si desea hacerlo de todos modos con Regex, puede reemplazar los \textbfcorchetes que no son con un símbolo no utilizado y, al final, eliminar los \textbfcorchetes y cambiar los símbolos nuevamente a corchetes:

1) Reemplace todos los soportes de cierre \textbfcon }el Símbolo A,

2) Reemplace todos \textbflos soportes de apertura que no sean soportes {con el símbolo B,

3) Reemplace el resto \textbf{y }(de \textbf) con nada,

4) Reemplace el símbolo A con {el símbolo B con }


@Paso 1 y 2:

Paso 1: }-> Smybol A, en mi ejemplo alemán ö:

(?<=(?<!\\textbf)\{(?!.*?\{)).*?\}

Reemplace esta expresión con \1ö(no encontré una solución mejor para esta expresión)


Luego haga el Paso 2: {-> Símbolo B, en mi ejemplo alemánä

(?<!\\textbf)\{(?!.*?\{)

Reemplace esta expresión con ä.


Repita estos pasos tantos niveles anidados como tenga. Luego siga los pasos restantes.


Bueno, esto es más una macro de expresiones regulares y una solución alternativa que una expresión regular sólida, pero debería funcionar.

información relacionada