5 ms·
> Git is consistent: a merge will always produce the same result for the same files I thought the point was that if you pull the exact same commits in differen
by Peaker 16y ago
> Git is consistent: a merge will always produce the same result for the same files
I thought the point was that if you pull the exact same commits in different order the merge will produce a different result for the same files, meaning that in git the history does matter. Whereas darcs/etc will always produce the same result, such that history does not matter?
- riffraff 16y agomore precisely, I believe, the history of the merges counts, not the history of the files per their original edits.
- davidmathers 16y agopull the exact same commits in different order Sort of. The OP doesn't write clearly. He's also confused about how git works. What he means is.. Say Bob has 2 commits (B1-B2) and Alice has 1 (A1) Scenario 1: Alice merges each of Bob's commits in sequence (i.e. she replays his commit history onto her repo: A1-B1-B2). Scenario 2: Alice merges only B2 (A1-B2). The point is that, with git, Alice's repo will be different in each scenario. Because in scenario 2 git doesn't examine commit B1 and use that info to try and figure out what the content in commit B2 "means". With darcs, on the other hand, her scenario 1 repo will be identical to her scenario 2 repo. The flip side is that in scenario 2 git will always produce the same result for the same B2, because B1 is irrelevant. With darcs a change in B1 will change the result. NOTE: "git pull --rebase" actually does "replay commit history" instead of "merge" when pulling code into your repo (result: B1-B2-A1). I use it as my default. The outcome is the same as darcs, the difference is that everything is explicit.
- knowtheory 16y agoThat's what i don't get. I don't understand where or how you could encounter a circumstance where this would matter. This complaint seems to be an abstract theoretical point (maybe to support git alternatives? dunno) that even esoteric usage of a DSCV would never come across. I dunno, maybe i'm not being creative enough in my use of histories. EDIT: Okay this explains everything in a considerably more concise fashion than the article does: http://news.ycombinator.com/item?id=2456529 http://news.ycombinator.com/item?id=2456529
- Groxx 16y agoIt would matter in this situation: In the beginning: function A(){ return 1; } Now commit this in one branch: function B(){ return 1; } function A(){ return 1; } then this: function A(){ return 1; } function B(){ return 1; } function A(){ return 1; } And then this in another branch off the base: function A(){ return 2; } Now merge the two end points. Which is correct? This, assuming a purely line-based diff: function A(){ return 2; } function B(){ return 1; } function A(){ return 1; } or this, assuming knowledge of the history of events? function A(){ return 1; } function B(){ return 1; } function A(){ return 2; } In Javascript, where such code is acceptable, `A()` now returns 1 or 2. In Git, or by applying patches manually, it depends on the order in which you merge. If you merge the `B()A()` branch with the `return 2` branch and then the `A()B()A()` one, you'll get the second result. But if you merge the `A()B()A()` directly with the `return 2` branch, you'll get first one. The same set of changes producing different outcomes. In Darcs, the history between `A()`, `B()A()`, and `A()B()A()` are checked, and it's seen that the second `A()` is the "original" one, so the `return 2` is applied to that one. Which means that you won't necessarily get the same behavior merging two Darcs patches as you would merging it within the repository, where there is a history. Git behaves exactly as if you were dealing with patches. I side with Git on this, personally, but it's a valid point - you have history, why not use it?
- saalweachter 16y agoYou know, I suspect that in many production cases, neither merge is "correct". The example involves a lot code duplication, and a change to the block of code which was duplicated. The probable case is something like: function foo(){ do_something_complex_but_not_correct(); } with one person making the change to: function foo(){ something_else(); do_something_complex_but_not_correct(); } and then: function foo(){ do_something_complex_but_not_correct(); something_else(); do_something_complex_but_not_correct(); } in the stated two-step change, while another author makes the change to: function foo(){ do_something_complex_and_also_correct(); } The correct "merge" is going to be to apply the second change to both blocks of code, not just the first or the second: function foo(){ do_something_complex_and_also_correct(); something_else(); do_something_complex_and_also_correct(); }
- etherealG 16y agocommits are not commutative in the general case. darcs algo is commutative for the merged commits, and gits is not, in this example. the git people are arguing that the speed lost by gaining this commutative nature is just not worth it. i agree.