Have you ever had to laboriously cherry-pick a series of commits solving some bug between branches (e.g., from stable to dev or vice-versa)? It's painful, and then later on you get conflicts because when you cherry-pick, git doesn't "understand" what's happening. Pijul solves that.
At a fundamental level, imagine I'm editing two files A and B, that have nothing to do with each other. Because git's level of dependency is the entire repo, if I switch back and forth between editing A and B, git inserts a series of arbitrary and not-actually-real dependencies between those edits. Then, as a consequence, there's no easy way for me to decide, say, I would like to merge my changes to A somewhere, but not my changes to B.
Or how about the entire controversy(/complexity) of whether to rebase or merge when pulling? The choice is an artifact of git's model, really a question of "in which way would we like git to represent some not-real constraints". This difficulty doesn't exist in Pijul, where dependencies are more fine-grained and real.
Another pain point you may have hit w/ git is when you do a merge, but somehow actually the changes were not included; this usually happens as a result of confusion regarding a conflict. Then you have to do painful repo surgery to try to convince git to actually include the changes you want.
In general large conflicts are quite painful in git: for the duration of the conflict, you are in a special state, and cannot commit. In pijul, conflicts are a first-class state of the repo, so you can iteratively work towards resolving your conflicts, using all of the normal VC tools to checkpoint along the way.
Disclaimer: I've only played with Pijul, not used it in anger. I definitely see a lot of potential though.
The main thing I believe is intrinsically superior to Git (I use Pijul a lot) is patch commutation, not just patches. Pijul guarantees that two patches that could be written independently always commute.
This has important consequences:
- You can push patches from the same branch in any order (provided they don't depend on each other). This wont change their identity, meaning that if you decide to push the other patches later, you can do it without having to rebase, and review/test the new order.
- Conflicts happen between patches, and conflict resolutions are modeled as patches. This means that if you solve a conflict once, you can push your resolution, even if you have your own, private patches on the same branch.
and the linked "badmerge" example: