Referring to the previous/next commit in git?

16,135

Solution 1

You have a very clear explanation of how this works in the chapter on Acenstry References in Pro Git:

  • ~ is used to get the first parent.
  • ^ can be used to get the other parents (^2, for example, for a merge).

But you don't have a simple way to reference the next commit, even if there are more convoluted ways to get it.

Solution 2

To simply answer the question from title (since that's what got me here from Google):

To checkout the previous commit:

git checkout HEAD^

To checkout the next commit (assuming there's no branching):

git checkout `git log --reverse --ancestry-path HEAD..master | head -n 1 | cut -d \  -f 2`

Solution 3

Inspired by @cexbrayat's answer, I find it useful to think of it this way:

How to refer to something in a commit's ancestry, where a commit can have multiple parents:

  • ^n specifies which parent

  • ~n specifies which generation

Both default to one.

Solution 4

To refer to most recent commit on the branch you can also use @~1

git checkout @~1
Share:
16,135

Related videos on Youtube

HelloGoodbye
Author by

HelloGoodbye

Updated on June 20, 2022

Comments

  • HelloGoodbye
    HelloGoodbye about 2 years

    I have seen git commands use a syntax such as HEAD~, but I haven't been able to find this syntax in the Git Reference Manual.

    Here is what I have understood: <commit>~<n> refers to the commit <n> steps earlier than <commit> (where <n> is an integer number), and commit~ simply means the same and that <n> implicitly is one.

    Now, is this correct? In that case, does this always work? What if <commit> is the result of a merge between two branches, which commit will then <commit>~ refer to? Is there some corresponding syntax for referring to the next commit or the commit <n> steps later?

  • HelloGoodbye
    HelloGoodbye about 11 years
    Thanks. The reference manual was apparently not the right place to look — I thought it would cover Git's syntax as well.
  • HelloGoodbye
    HelloGoodbye over 8 years
    That's a quite good rule :) Although it breaks down when neither ^n nor ~n is specified.
  • Jon Carter
    Jon Carter over 8 years
    That just leaves the commit hash itself, which refers to.. itself. I suppose I should have specified that a commit hash should be included as well. Is that what you mean?
  • HelloGoodbye
    HelloGoodbye over 8 years
    I guess you mean that they default to one, like arguments to a function in programming can have default values if you don't specify them? I'm thinking that if you have a function that takes both which generation and which parent and returns a commit reference, and if you don't specify any of them, you will just have the commit you start out with. So in this case the generation would be 0 even though you don't specify which generation. Although I realize that which parent is really only relevant when the generation in 1, so the two having such a function doesn't make so much sense.
  • HelloGoodbye
    HelloGoodbye over 8 years
    In other words, the default value of the generation would be 0 if you don't specify which parent.
  • Jon Carter
    Jon Carter over 8 years
    Well, what I mean by 'default to one': Consider the expression '<SHA1>^'. There is no specific value given for which parent you mean, so the first parent is returned. Same with '<SHA1>~'. No number is specified, so the first generation back is what it acts upon.
  • dvalentine314
    dvalentine314 almost 3 years
    not sure if this the case everywhere, but in PowerShell on Windows that is git checkout "@~1"