What do the numbers on a Git Diff header mean? [duplicate]

Every time I run git diff, for each single changes I made, I get some sort of header with numbers, for example:

@@ -169,14 +167,12 @@ function Browser(window, document, body, XHR, $log) {.....

I wonder what does the four numbers mean? I guess -169 means that this particular line of code that follows was originally in line 169 but now is in 167? And what do 14 and 12 mean?


This header is called set of change, or hunk. Each hunk starts with a line that contains, enclosed in @@, the line or line range from,no-of-lines in the file before (with a -) and after (with a +) the changes. After that come the lines from the file. Lines starting with a - are deleted, lines starting with a + are added. Each line modified by the patch is surrounded with 3 lines of context before and after.

An addition looks like this:

@@ -75,6 +103,8 @@
 foo
 bar
 baz
+line1
+line2
 more context
 and more
 and still context

That means, in the original file before line 78 (= 75 + 3 lines of context) add two lines. These will be lines 106 (= 103 + 3 lines of context) through 107 after all changes.
Note the difference in from numbers (-75 vs +103), this means that there were other changes in this file before this particular hunk, that added 28 (103 - 75) lines of code.

A deletion looks like this:

@@ -75,7 +75,6 @@
 foo
 bar
 baz
-line1
 more context
 and more
 and still context

That means, delete line 78 (= 75 + 3 lines of context) in the original file. The unchanged context will be on lines 75 to 80 after all changes.
Note that from numbers in this hunk are equal (-75 and +75), this means that either there were no changes before this hunk, or amount of added and deleted lines in previous changes are the same.

Finally, a change looks like this:

@@ -70,7 +70,7 @@
 foo
 bar
 baz
-red
+blue
 more context
 and more
 still context

That means, change line 73 (= 70 + 3 lines of context) in the file before all changes, which contains red to blue. The changed line is also line 73 (= 70 + 3 lines of context) in the file after all changes.

Credit goes to Markus Bertheau.


I wonder what does the four numbers mean?

Let's analyze a simple example

The format is basically the same the diff -u unified diff.

We start with numbers from 1 to 16 and remove 2, 3, 14 and 15:

diff -u <(seq 16) <(seq 16 | grep -Ev '^(2|3|14|15)$')

Output:

@@ -1,6 +1,4 @@
 1
-2
-3
 4
 5
 6
@@ -11,6 +9,4 @@
 11
 12
 13
-14
-15
 16

@@ -1,6 +1,4 @@ means:

  • -1,6 means that this piece of the first file starts at line 1 and shows a total of 6 lines. Therefore it shows lines 1 to 6.

    1
    2
    3
    4
    5
    6
    

    - means "old", as we usually invoke it as diff -u old new.

  • +1,4 means that this piece of the second file starts at line 1 and shows a total of 4 lines. Therefore it shows lines 1 to 4.

    + means "new".

    We only have 4 lines instead of 6 because 2 lines were removed! The new hunk is just:

    1
    4
    5
    6
    

@@ -11,6 +9,4 @@ for the second hunk is analogous:

  • on the old file, we have 6 lines, starting at line 11 of the old file:

    11
    12
    13
    14
    15
    16
    
  • on the new file, we have 4 lines, starting at line 9 of the new file:

    11
    12
    13
    16
    

    Note that line 11 is the 9th line of the new file because we have already removed 2 lines on the previous hunk: 2 and 3.


Summary:

  • Assume git diff will output [0-3] lines of context [before/after] [first/last] changes

@@ -[original file's number of first line displayed],[context lines + removed lines] +[changed file's number of first line displayed],[context lines + added lines] @@