Why Mercurial > Git, or How I Learned To Stop Censoring Myself and Participate in Flamewars.
After reading Five Features from Mercurial That Would Make Git Suck Less, found via Hacker News, I have a simple explanation (something I’ve thought for a long while now).
So, Git’s written in C, and Mercurial’s written in Python (well, except for a few bottlenecks, like a binary diff, written in C). No wonder Mercurial has some nice features and intelligent DWIM behavior.
Applications written in higher-level, dynamic languages (like Python and Ruby) are always going to be more ‘intelligent’ than those written in low-level, static languages (like C and Java). A website built on top of Ruby on Rails or Django is going to feel smoother to use than one built on plain CGI, or even frameworks like Struts or WebObjects. Why?
Because these dynamic, expressive tools stop you from having to worry about the every-day issues that all applications have to deal with, so that you can concentrate on making your many Interfaces (User, Developer or otherwise) simple and intelligent, and the usage and development experience smooth.
The people programming Git don’t just have to know how to build a source-control tool. They also have to deal with the particular nuances of each operating system—the reason why, so far, Git only works properly on POSIX-based platforms—down to the types of integer supported, memory management, sockets, filesystems and character encodings.
The developers of Mercurial can concentrate 100% on building the best damn source-control utility they’re able to. Python handles the stuff like garbage collection, character en/de-coding, networking and filesystems, so that the Mercurial devs can handle the stuff like branching and merging, pushing and pulling, committing and reverting.
The terms ‘accidental complexity’ and ‘essential complexity’ have been brought to my attention.Just out of interest, here’s the result of running ohcount
(http://labs.ohloh.net/ohcount) on the source code for Git itself (minus the
Documentation/ and git-gui/ directories):
Language Files Code Comment Comment % Blank Total ---------------- ----- --------- --------- --------- --------- --------- c 326 88337 12440 12.3% 13930 114707 shell 440 48546 3676 7.0% 12177 64399 perl 26 20243 3134 13.4% 3333 26710 tcl 1 9926 430 4.2% 841 11197 autoconf 2 8146 20 0.2% 1005 9171 python 5 2937 276 8.6% 670 3883 emacslisp 2 1621 152 8.6% 222 1995 make 6 1517 264 14.8% 205 1986 cpp 5 1438 423 22.7% 356 2217 css 1 420 5 1.2% 101 526 assembler 2 220 136 38.2% 51 407 bat 1 1 0 0.0% 0 1 ---------------- ----- --------- --------- --------- --------- --------- Total 817 183352 20956 10.3% 32891 237199
And the results for Mercurial (just the mercurial directory within the actual
repo itself, which represents the bulk of the core code):
Language Files Code Comment Comment % Blank Total ---------------- ----- --------- --------- --------- --------- --------- python 77 19147 4208 18.0% 3558 26913 c 6 1646 175 9.6% 304 2125 ---------------- ----- --------- --------- --------- --------- --------- Total 83 20793 4383 17.4% 3862 29038
One has nearly 10 times as many files, and 10 times as many lines of code as the other. Can you guess which one?
In a spirit of irony, `ohcount` has been rewritten from Ruby to C. A couple of people might get a little hung up about the inclusion of these code metrics. I’m not trying to make a scientific or absolute statement about the quality of the code or tools, and I didn’t expect anyone to construe it as such. It’s funny how the most controversial bit of the blog post is the part which was something of an afterthought.