Ich habe viele XML-Dateien, über 50000 davon.
In einigen XML-Dateien sind einige Dateien so geschrieben
<filename>abc.JPEG<^Lilename>
^L
ist nur ein Zeichen, aber ich kann nicht finden, was ^L
mit Google bedeutet.
Wenn ich cat
den Inhalt einer Datei drucke, wird Folgendes angezeigt
<filename>abc.JPEG<
ilename>
Wie auch immer, möchte ich ändern <filename>abc.JPEG<^Lilename>
zu<filename>abc.JPEG</filename>
Ich habe bereits einen Befehl zum Ändern eines Wortes in vielen Dateien gefunden, z
find . -exec perl -pi -e 's/[find_word]/[change_word]/g' {} \;
Aber dieser Befehl funktioniert in meinem Fall nicht, weil er das Suchwort nicht erkennen kann, wenn ich nur tippe ^L
.
Wie kann ich ändern , <filename>abc.JPEG<^Lilename>
um <filename>abc.JPEG</filename>
in vielen Dateien?
<\filename>
anstatt</filename>
in einem Kontext, in dem\f
dies als Formular-Feed-Zeichen interpretiert wird. Sie sollten wahrscheinlich die Quelle dieser Dateien ausfindig machen und den Entwickler auf das Problem mit dem Generierungswerkzeug hinweisen. Zum Reparieren der Dateien ist die akzeptierte Antwort in Ordnung.Antworten:
Strg-L (dargestellt als
^L
) ist das Zeichen "Formularvorschub". In ASCII hat es den Dezimalwert 12 (L
ist der 12. Buchstabe des Alphabets) oder den Hexadezimalwert 0c:Sie können es mit Tools wie sed ersetzen, indem Sie den hexadezimalen Escape-Code angeben:
Alternativ können Sie auch
^L
direkt mit der Tastatursequenz CTRL+ V CTRL+ komponierenLFür Ihren spezifischen Ersatz angegeben
dann
(Der
g
Modifikator wird hinzugefügt, falls mehr als eine Instanz pro Zeile vorhanden ist.)quelle
find
, die diese 50000 XML-Dateien durchläuft und jede automatisch verarbeitet (und auch ein Backup erstellt).Wie Hans-Martin Mosner in den Kommentaren ausführt, scheint es, dass jemand beim Generieren des XML Backslashes anstelle von Forward Slashes verwendet hat (oder möglicherweise den gesamten
<filename>
Abschnitt durch einen Unix-zu-Windows-Konverter geführt hat, der über Schrägstriche hinweg war).\f
ist eine selten verwendete Escape-Sequenz für ein Formular-Feed-Zeichen, auch bekannt als U + 0C oder ^ L. Ein späterer Schritt der Pipeline ersetzte dann das\f
durch wörtliche U + 0C-Zeichen.Glücklicherweise ist U + 0C ein äußerst seltenes Zeichen, das in keiner Art von XML absichtlich vorkommt . Und da nur
\f
würde dies produzieren, im Gegensatz zu (sagen wir)\g
oder\k
eine universelle Suchen und ersetzen nicht nur reparieren ,</filename>
sondern auch</folder>
,</file>
oder irgendetwas anderes , das verstümmelt wurde.Das ist es, was das Sed-Skript von Steeldriver macht. Ich würde es nur etwas allgemeiner machen:
Dies bedeutet "(s) wap alle Instanzen von
\x0c
(dh U + 0C) auf/f
(g) lobally".quelle
\f
ist das Formular-Feed-Zeichen in Perl. Es sieht so aus, als ob diese fehlerhaften Dateien von jemandem erstellt wurden, der sowohl in Perl als auch in XML neu ist.Hier ist ein viel früherer Fix - der auch die Ziele des OP erfüllt, die Aktualisierung aller Dateien zu automatisieren, im Gegensatz zu der akzeptierten Antwort mit sed, die jeweils nur für eine Datei funktioniert, da sie nicht mit gekoppelt ist
find
.\f
kann einfach selbst anstelle des Hexadezimalcodes verwendet werdenx0c
.Hier habe ich
-type f
zu tel hinzugefügt ,find
um nur einfache Dateien zurückzugeben - andernfallsfind
wird.
in der Liste zurückgegeben und eine Warnung ausgelöst, wenn Sie versuchen, sie zu bearbeiten, obwohl alles andere weiterhin funktioniert.Ich habe es auch einfacher gemacht, den regulären Ausdruck zu sehen, indem ich das
x
Flag verwendet habe, das echte Leerzeichen ignoriert, sodass Sie die Elemente Ihres regulären Ausdrucks entfernen können. Wenn Ihnen das nicht gefällt, ist es hier ohne:Und in dem wahrscheinlichen Fall, dass alle Formularvorschubzeichen falsch sind und alle durch ersetzt werden sollten
/f
, können Sie den Einzeiler noch weiter verkleinern:Sie müssen keine Schrägstriche verwenden, um die Elemente (
s///
) Ihres Regex-Ersetzungsbefehls in Perl zu umgeben. Sie können ein beliebiges Symbol verwenden. Wenn Sie sich jedoch für die Verwendung eines gepaarten klammerartigen Symbols entscheiden, müssen Sie beide verwenden:s[old][new]
zum Beispiel.Da ich keine Schrägstriche verwende, muss ich keinen Schrägstrichen entkommen.
Wie für
-i.bkp
:perl -pi -e
Ermöglicht das Bearbeiten vor Ort. Wenn Sie jedoch eine zusätzliche Versicherung wünschen, falls Ihr Perl-Programm zum Suchen und Ersetzen falsch ist, können Sie eine Dateierweiterung eingeben, damit eine Kopie der Originaldateien für erstellt wird Du. Hier habe ich benutzt.bkp
.In den neuesten Perl-Versionen wurde die direkte Bearbeitung aktualisiert, um die Ausfallsicherheit zu erhöhen, falls auf Ihrem System ein ernstes Problem wie Stromausfall oder Speicherplatzmangel auftritt. Hier ist der Perl-Autor Brian D Foy über die verbesserte In-Place-Bearbeitung in den letzten Perls.
Sie sollten mit Perl für diese Art von Aufgaben betrachten, weil es eine extrem leistungsstarke und dennoch unterbewertet Allzweck- Programmiersprache ist, von deren ursprünglichen Entwurfsziele war zu ersetzen
sed
undawk
mit etwas viel besser.Perl 5 regex Matching - Fähigkeiten und verbesserte regex Syntax weit über die von
sed
,awk
und in der Tat jeder anderen Programmiersprache abgesehen von Perl 6, so dass Perl die vernünftigste Wahl für einfache und erweitern Regex Manipulationen.Zur Verdeutlichung: Funktioniert auch
sed
mit OKfind
und Sie können auchsed -i.bkp
eine Sicherungskopie jeder bearbeiteten Datei erstellen, aber soweit ich weiß, bietet sie nicht die zusätzliche Ausfallsicherheit in Perl 5.28 und höher. Es verwendet auch die klobigere und weitaus weniger leistungsfähige traditionelle UNIX ® -Regex-Syntax.quelle