So erstellen Sie ein nützliches Diff einer Markdown-Schreibprojektiteration

Ich habe ein Theaterstück geschrieben, das ich diesen Sommer aufgeführt habe, und für eine bevorstehende zweite Aufführungsserie bedeutende Umschreibungen vorgenommen. Um mir zu helfen, meine Zeilen neu zu lernen, wäre es meiner Meinung nach nützlich zu sehen , welche alle zusammen geändert/entfernt/hinzugefügt wurden, anstatt nur die neue Version durchzulesen und zu hoffen, dass sie bestehen bleibt.

Ich habe mein Stück in Markdown geschrieben (mit iaWriter). und ich habe beide Versionen separat gespeichert.

Ich bin auch Programmierer und an Versionskontrolle gewöhnt, also habe ich versucht, ein Git-Repository zu erstellen, in dem ich mit einer txt-Datei mit der Originalversion begonnen habe, dann die neue Version darüber eingefügt und die Änderungen übernommen habe. Ich hatte gehofft, das Diff wäre nützlicher als es war ... aber es ist immerhin etwas! (Ich hatte zum Beispiel gehofft, dass 95 % identische Linien als dieselbe Linie identifiziert werden, aber oft war dies nicht der Fall, weil mehrere Linien zwischen ihnen auftauchen.

Ich frage mich also, ob es einen besseren Weg gibt, einen nützlichen Unterschied von 2 Nur-Text-Dateien zu erhalten, der in Bezug auf die Identifizierung von eher wortbasierten als zeilenbasierten Unterschieden verbessert würde.

Und wenn ja (auch nur für Git-Diffs), ob es eine Möglichkeit gäbe, dies so auszugeben, dass es in nützliche Leseformate gespeichert werden kann.

Antworten (2)

Ich nehme an, Sie haben bereits die Flags --minimal und --ignore-all-space ausprobiert.

Wenn Zeilenumbrüche aufgrund von hinzugefügten/gelöschten/geänderten Wörtern das Problem mit diff verursachen (was es so aussehen lässt, als wären Änderungen aufgetreten, die nur Formatänderungen sind), würde ich vorschlagen (da Sie dies leicht selbst programmieren können), dass Sie beide Dateien vorverarbeiten. um zwei neue Dateien zum Vergleich zu erzeugen.

Die Idee ist, EINE Zeile zu haben, die diff pro Element verarbeitet : Wenn es also nur eine Geschichte wäre, würde ich sagen, kombinieren Sie alle Zeilen in jedem Absatz als eine einzige Zeile, selbst wenn Tausende von Zeichen lang sind, also vergleicht diff jeden Absatz für Änderungen, nicht jede Zeile .

(Verwenden Sie für diff das Flag --width=nnn , um sicherzustellen, dass alle Zeichen ausgegeben werden, ich würde --width=16384 oder so setzen.)

Sie müssen anhand Ihrer Formatierung erkennen, wo jeder Elementtyp beginnt und endet. Ich bin nicht mit der Spielformatierung vertraut, aber in einem Drehbuch würde ich Schlagzeilen (Einstellung), Expositionsabsätze, Charakterdialogbezeichnungen und den Charakterdialog selbst vergleichen wollen.

In einem Drehbuch denke ich, dass diese Identifizierungen wahrscheinlich erfolgen könnten, indem führende Leerzeichen gezählt und/oder auf GROSSBUCHSTABEN oder Schlüsselwörter (INT., EXT. usw.) dann ignorieren Sie eine einzelne Leerzeile, aber zwei hintereinander signalisieren das Ende eines Elements). Ich würde eine einfache Zustandsmaschine schreiben (jeder Zustand ist, welche Art von Element ich für die Ausgabe baue oder dass ich Text für den Beginn eines anderen Elements suche usw.), aber die Logik ist ziemlich einfach, egal wie Sie sie codieren.

So werden fünf Dialogzeilen zu einer einzigen Zeile in der Ausgabedatei. In der Ausgabe könnte eine neue Szene also Zeilenumbrüche wie diese haben:

EXT. Park Park, NACHT

[fünf Ausstellungszeilen hier kombiniert, DIANE und EDGAR beim Joggen aufstellen, kurz davor, überfallen zu werden]

DIANE

[zehn Dialogzeilen in dieser Zeile zusammengefasst, eine Geschichte über die Arbeit]

EDGAR

[hier zwei oder drei Zeilen kombiniert]

Das sollte Reflow-Änderungen ignorieren, die der Editor vorgenommen hat, und nur identifizieren, wo Wortänderungen aufgetreten sind.

Es wird jedoch schwieriger zu identifizieren, wo in den Originaldateien der Text erschienen ist. Um das zu lösen, würde ich mehr zur Ausgabedatei hinzufügen und ein anderes Flag von diff verwenden: --ignore-matching-lines=RE

RE ist hier ein regulärer Ausdruck. Die Idee ist also, vor (oder nach Ihrer Wahl) der Ausgabe eines aufgebauten Elements in einer separaten Zeile die ursprünglichen Zeilennummern aus der Originaldatei und der geänderten Datei mit einer Markierung anzugeben, die nicht gefunden wird der Text: Wie das Hashtag '#' oder ein Paar davon. Da Sie wissen, dass dies mit dem ersten Zeichen der Zeile „Notation“ beginnt, setzen Sie Ihren regulären Ausdruck auf „^#“ und diese Zeilen werden ignoriert. So könnte die Zeile in der Ausgabe aussehen

# 1023 1027

bedeutet Zeile 1023 in der ersten Datei, Zeile 1027 in der zweiten. Wenn Sie es vorziehen, machen Sie es komplexer, indem Sie auch die Seiten zählen. Ich habe es nicht ausprobiert, aber ich denke, diese sollten als Teil des Kontexts ausgegeben werden, wenn eine geänderte Zeile gemeldet wird.

Sie können diff auch anweisen, nur Änderungen auszugeben, --suppress-common-lines .

Das ist vielleicht nicht genau das, was Sie wollen; Aber sobald Sie die Änderungen identifiziert haben, können Sie sie möglicherweise im neuen Skript irgendwie hervorheben (Farbe oder Fettdruck oder was auch immer) als Übungsskript.

Da Sie Elemente identifizieren und insbesondere geänderte Dialoge isolieren möchten, wäre es in Ihrem Code einfach, all dies zu tun, aber die Ausgabe (in den beiden zu vergleichenden Dateien) von allem außer dem Dialog Ihres einen Charakters zu unterdrücken. Der Hashtag für die Zeilennummern der Originaldatei würde unverändert bleiben.

Wenn Sie den Zeichennamen zu einer Variablen oder einem Argument für Ihr Vorverarbeitungsprogramm machen, das Sie schreiben, können Sie Übungsskripts für jedes Zeichen erstellen.

Viel Spaß beim Codieren.

Ich bin mir nicht sicher, ob ich Git-Commit verwenden soll. Ich benutze es nicht viel.

Wie wäre es mit der Tokenisierung Ihres Textes in Python? Berechnen Sie dann die Entropie pro Satz. Dies würde den Unterschied zwischen den Sätzen zeigen. Alternativ können Sie dies auch für Wörter oder Ngrams tun. Die Ausgabe kann in Listen- und TXT-Dateien gespeichert werden.

# py3 algo for calculating entropy
# import math
from collections import Counter
p, lns = Counter(s), float(len(s))
return -sum( count/lns * math.log(count/lns, 2) for count in p.values())

Oder verwenden Sie vielleicht einen der Fuzzy-Suchalgorithmen, um Sätze zu finden, die nicht genau sind, aber eine Fuzzy-Übereinstimmung sind (z. B. ein ersetztes Zeichen).

Vielleicht noch einfacher, aber nicht so leistungsstark, hat Google Docs einen Versionsverlauf, in dem Sie alle Änderungen für jeden Tag anzeigen können, an dem Sie die Datei bearbeitet haben. Auch ein Export nach Markdown ist möglich.

Teilen Sie uns Ihre Lösung mit.