Jeff King <peff@xxxxxxxx> writes: > Git's index and trees only understand whole files, so at some point you > must generate the final file content. A diff is an easy way to represent > the changes, apply them to the existing state, and then get that final > content. But it doesn't _have_ to be. You could make some modifications > to what is in the working tree and then say "OK, now stage this.". > > BUT. That is probably not what the user wants, if the content in the > index actually has some modifications that are not in the working tree > (i.e., you wouldn't want to overwrite them). Hence we tend to work with > diffs, saying "make these changes to what is already in the index, and > if they conflict, then bail". > > So "git add -p", for example, also works by creating diffs, modifying > them, and feeding the result to "apply". You can see the implementation > in git-add--interactive.perl, where it literally calls diff and apply > commands. > > And that leads us to the answer to the first question. That script > implements "add -p", but also "checkout -p" (which is what you want), > "reset -p", "stash -p", etc. They differ only in what we diff and how we > apply the result; the main engine of slicing and dicing the diff through > user interaction is the same. See the %patch_modes hash for the list. I was about to respond but you said everything I wanted to say and said it a lot better than I could ;-)