Utilizzando una tabella o uno script in sed per sostituire molti caratteri speciali con i caratteri di escape?

Se si desidera sostituire caratteri speciali utilizzando sed, è ansible utilizzare diversi modi, ma il problema è che è necessario sostituire molti caratteri speciali (100+) con caratteri di escape in molti file.

così ha bisogno: (grazie a Peter)

^^ per sfuggire a un singolo ^
^| per fuggire. |
\& per uscire &
\/ per scappare /
\\ per sfuggire \

Supponiamo di avere esempi di 100+ stringhe in molti file:

 sed.exe -i "s/{\*)(//123/ sed -i "s/\\/123/g;" 1.txt sed.exe -i "s/{\*)(//123/ sed -i "s/\\/123/g;" 1.txt ..... ..... 

queste stringhe contenenti molti personaggi speciali per sfuggire (abbiamo 100+ stringhe).
Scappare manualmente è un lavoro molto lungo..so ho bisogno di creare uno script di tabella simile a wReplace per call il prompt dei comandi per fuggire i caratteri speciali e poi sostituirli con le mie parole.
Come posso fare?

Si noti che ^^ ^ per ^ , e ^| per | , e ^& per & … non sono requisiti di sed . Il ^ escape-character è richiesto dalla shell CMD. Se il tuo text non è esposto né alla row di command né a un parametro di command in uno script di command .cmd / .bat, devi solo considerare il carattere di escape di sed, che è un backslash \​ Sono due ambiti ben distinti (che possono sovrapporsi, quindi spesso è meglio mantenerlo senza limiti, come segue.

Ecco uno script di sed che sostituirà qualsiasi numero di stringhe di ricerca che si sepcificano, con la loro sostituzione-string complementare. Il formato generale delle stringhe è una croce tra un command di sostituzione sed ( s / abc / xyz / p ) e un formato tabulare. Puoi "allungare" il delimitatore centrale in modo da poter allineare le cose.
È ansible utilizzare un model di string FX ( F / … ) o un normale pattern di espressione regolare ( s / … ) … e puoi regolare sed -n e ciascuno /p (in table.txt ) come necessario.

Hai bisogno di 3 file per una corsa minima (e un quarto, ottenuto dynamicmente da table.txt):

  1. la tabella principale di script -to-regex.sed
  2. il file tabella table.txt
  3. il file di destinazione file -to-chanage.txt
  4. script -derrived tabella-derrived.sed

Per eseguire una tabella contro un file di destinazione.

 sed -nf table-to-regex.sed table.txt > table-derrived.sed # Here, check `table-derrived.sed` for errors as described in the example *table.txt*. sed -nf table-derrived.sed file-to-change.txt # Redirect *sed's* output via `>` or `>>` as need be, or use `sed -i -nf` 

Se si desidera eseguire table.txt su molti file, basta inserire lo snippet di codice sopra indicato in un semplice loop in base alle tue esigenze. Posso farlo trivialmente in bash , ma qualcuno più consapevole della shell di CMD di Windows sarebbe più adatto di me a metterlo in su.


Ecco lo script: table-to-regex.sed

 s/[[:space:]]*$// # remove trailing whitespace /^$\|^[[:space:]]*#/{p; b} # empty and sed-style comment lines: print and branch # printing keeps line numbers; for referencing errors /^\([Fs]\)\(.\)\(.*\2\)\{4\}/{ # too many delims ERROR s/^/# error + # /p # print a flagged/commented error b } # branch /^\([Fs]\)\(.\)\(.*\2\)\{3\}/{ # this may be a long-form 2nd delimiter /^\([Fs]\)\(.\)\(.*\2[[:space:]]*\2.*\2\)/{ # is long-form 2nd delimiter OK? s/^\([Fs]\)\(.\)\(.*\)\2[[:space:]]*\2\(.*\)\2\(.*\)/\1\2\n\3\n\4\n\5/ t OK # branch on true to :OK }; s/^/# error L # /p # print a flagged/commented error b } # branch: long-form 2nd delimiter ERROR /^\([Fs]\)\(.\)\(.*\2\)\{2\}/{ # this may be short-form delimiters /^\([Fs]\)\(.\)\(.*\2.*\2\)/{ # is short-form delimiters OK? s/^\([Fs]\)\(.\)\(.*\)\2\(.*\)\2\(.*\)/\1\2\n\3\n\4\n\5/ t OK # branch on true to :OK }; s/^/# error S # /p # print a flagged/commented error b } # branch: short-form delimiters ERROR { s/^/# error - # /p # print a flagged/commented error b } # branch: too few delimiters ERROR :OK # delimiters are okay #============================ h # copy the pattern-space to the hold space # NOTE: /^s/ lines are considered to contain regex patterns, not FIXED strings. /^s/{ s/^s\(.\)\n/s\1/ # shrink long-form delimiter to short-form :s; s/^s\(.\)\([^\n]*\)\n/s\1\2\1/; ts # branch on true to :sp; b } # print and branch # The following code handles FIXED-string /^F/ lines s/^F.\n\([^\n]*\)\n.*/\1/ # isolate the literal find-string in the pattern-space s/[]\/$*.^|[]/\\&/g # convert the literal find-string into a regex of itself H # append \n + find-regex to the hold-space g # Copy the modified hold-space back into the pattern-space s/^F.\n[^\n]*\n\([^\n]*\)\n.*/\1/ # isolate the literal repl-string in the pattern-space s/[\/&]/\\&/g # convert the literal repl-string into a regex of itself H # append \n + repl-regex to the hold-space g # Copy the modified hold-space back into the pattern-space # Rearrange pattern-space into a / delimited command: s/find/repl/... s/^\(F.\)\n\([^\n]*\)\n\([^\n]*\)\n\([^\n]*\)\n\([^\n]*\)\n\([^\n]*\)$/s\/\5\/\6\/\4/ p # Print the modified find-and-replace regular expression line 

Ecco un esempio di file di tabella, con una descrizione di come funziona: table.txt

 # The script expects an input table file, which can contain # comment, blank, and substitution lines. The text you are # now reading is part of an input table file. # Comment lines begin with optional whitespace followed by # # Each substitution line must start with: 's' or 'F' # 's' lines are treated as a normal `sed` substitution regular expressions # 'F' lines are considered to contain `FIXED` (literal) string expressions # The 's' or 'F' must be followed by the 1st of 3 delimiters # which must not appear elsewhere on the same line. # A pre-test is performsd to ensure conformity. Lines with # too many or too few delimiters, or no 's' or 'F', are flagged # with the text '# error ? #', which effectively comments them out. # '?' can be: '-' too few, '+' too many, 'L' long-form, 'S' short-form # Here is an example of a long-form error, as it appears in the output. # error L # s/example/(7+3)/2=5/ # 1st delimiter, eg '/' must be a single character. # 2nd (middle) delimiter has two possible forms: # Either it is exactly the same as the 1st delimiter: '/' (short-form) # or it has a double-form for column alignment: '/ /' (long-form) # The long-form can have any anount of whitespace between the 2 '/'s # 3rd delimiter must be the same as the 1st delimiter, # After the 3rd delimiter, you can put any of sed's # substitution commands, eg. 'g' # With one condition, a trailing '#' comment to 's' and 'F' lines is # valid. The condition is that no delimiter character can be in the # comment (delimiters must not appear elsewhere on the same line) # For 's' type lines, it is implied that *you* have included all the # necessary sed-escape characters! The script does not add any # sed-escape characters for 's' type lines. It will, however, # convert a long-form middle-delimiter into a short-form delimiter. # For 'F' type lines, it is implied that both strings (find and replace) # are FIXED/literal-strings. The script does add the necessary # sed-escape characters for 'F' type lines. It will also # convert a long-form middle-delimiter into a short-form delimiter. # The result is a sed-script which contains one sed-substitution # statement per line; it is just a modified version of your # 's' and 'F' strings "table" file. # Note that the 1st delimiter is *always* in column 2. # Here are some sample 's' and 'F' lines, with comments: # F/abc/ABC/gp #-> These 3 are the same for 's' and 'F', s/abc/ABC/gp #-> as no characters need to be escaped, s/abc/ /ABC/gp #-> and the 2nd delimiter shrinks to one F/^F=Fixed/ /\1okay/p # \1 is okay here, It is a FIXED literal s|^s=sed regex||\1FAIL|p # \1 will FAIL: back-reference not defined! F|\\\\|////| # this line == next line F|\\\\| |////|p # this line == previous line s|\\\\| |////|p # this line is different; 's' vs 'F' F_Hello! ^.&`//\\*$/['{'$";"`_ _Ciao!_ # literal find / replace 

Ecco un file di input di esempio il cui text si desidera modificare: file-to-chanage.txt

 abc abc ^F=Fixed s=sed regex \\\\ \\\\ \\\\ \\\\ Hello! ^.&`//\\*$/['{'$";"` some non-matching text