text.diff - Calculate difference of text streams ¶This module calculates the difference of two text streams or strings,
using util.lcs (see util.lcs - The longest common subsequence).
{text.diff}
Generates an "edit list" from text sources src-a and src-b.
Each of text sources, src-a and src-b, can be either an input
port or a string. If it is a string, it is converted to a string input
port internally. Then, the text streams from both sources are converted
to sequences by calling reader repeatedly on them; the default
of reader is read-line, and those sequences are
passed to lcs-edit-list to calculate the edit list.
The equality function eq-fn is also passed to lcs-edit-list.
An edit list is a set of commands that turn the text sequence
from src-a to the one from src-b.
See the description of lcs-edit-list for
the detailed explanation of the edit list.
(diff "a\nb\nc\nd\n" "b\ne\nd\nf\n") ⇒ (((- 0 "a")) ((- 2 "c") (+ 1 "e")) ((+ 3 "f")))
{text.diff}
A convenience procedure to take the diff of two text sources
and display the result nicely. This procedure calls lcs-fold
to calculate the difference of two text sources. The meanings of
src-a, src-b, reader and eq-fn are the
same as diff’s.
Writer is a procedure that takes two arguments, the text element
and a type, which is either a symbol +,
a symbol -, or #f. If the text element is only
in src-a, writer is called with the element and
-. If the text element is only in src-b,
it is called with the element and +. If the text element
is in both sources, it is called with the element and
#f. The default procedure of writer prints
the passed text element to the current output port
in unified-diff-like format:
(diff-report "a\nb\nc\nd\n" "b\ne\nd\nf\n")
displays:
- a b - c + e d + f
{text.diff}
Produce a human-friendly difference of two text sources like
diff-report, but in the “context diff” format.
(diff-report/context "a\nb\nc\nd\n" "b\ne\nd\nf\n")
displays:
*************** *** 1,4 **** - a b ! c d --- 1,4 ---- b ! e d + f
This calls lcs-edit-list/context to get a context diff of lines,
then format it in the same way as diff -c output.
(See util.lcs - The longest common subsequence, for the details of
lcs-edit-list/context.)
Each “hunk” (a chunk containing difference)
is preceded by a separater ***************,
followed by the excerpt from src-a, then the excerpt form src-b,
each preceded by the header showing the line number of that excerpts
(start and end line, inclusive, 1-based).
In the excerpts, the line that’s deleted from src-a is prefixed
with -, the line that’s inserted into src-b is prefixed
with +, and the line changed is prefixed with !.
If the hunk only consists of either insertions or deletions, the other side of excerpt is omitted.
(diff-report/context "a\nb\nc\n" "a\nc\n")
prints:
***************
*** 1,3 ****
a
- b
c
--- 1,2 ----
As a special case, if one of the source is empty, its header is shown as zero-th line:
(diff-report/context "" "a\nb\nc\n")
prints:
***************
*** 0 ****
--- 1,3 ----
+ a
+ b
+ c
The reader, writer and eq-fn keyword arguments are the
same as diff-report. The context-size keyword argument
specifies the maximum unchanged lines attached to each hunk to show the
context.
{text.diff}
Like diff-report/context, but use “unified diff” format,
same as diff -u.
(diff-report/unified "a\nb\nc\nd\n" "a\nx\nd\n")
prints:
@@ -1,4 +1,3 @@
a
-b
-c
+x
d
Each “hunk” begins with the header:
@@ -p,q +r,s @@
where p is the start line number in src-a, q is the length of the hunk in src-a, r is the start line number in src-b, and s is the length of the hunk in src-b.
The line-number is 1-based. If the length of the hunk is 1, it is omitted.
The lines deleted from src-a has - prefix,
the ones inserted into src-b has + prefix,
and unchanged lines has a space prefix.
As a special case, if either of sources is empty, both of its start index and
length are shown as 0.
(diff-report/unified "a\nb\nc\n" "")
prints:
@@ -1,3 +0,0 @@
-a
-b
-c
The reader, eq-fn, writer, and context-size
keyword arguments are the same as diff-report/context.
This is used to show the difference of test results in test*/diff
(see gauche.test - Unit Testing).