4 ms·
In my experience, Rust compiles orders of magnitude faster than similar C++ code for initial compiles. For incremental compiles, Rust is infinitely faster. C++,
by fluffything 6y ago
In my experience, Rust compiles orders of magnitude faster than similar C++ code for initial compiles. For incremental compiles, Rust is infinitely faster. C++, even if you use Modules, needs to re-compile, re-instantiate, re-check all the templates all the time. I speculate that this alone is what probably is responsible for the largest difference in compile-times.
Comparing Rust with C here is hard. As others have mentioned, with C, you typically only use libraries that are installed in your system. Rust does not have a global system cache for libraries, and I don't think there is any package manager installing pre-compiled Rust libraries, so at least for the initial compiles, Rust needs to do much more work than C, for Rust dependencies at least. If your Rust project only depends on C libraries, then there is no work to be done of course.
For incremental compiles with C, it is hit or miss. If your C project is properly "modularized" (split into a lot of small enough TUs), then when you change a TU, C only needs to recompile that one TU. In our benchmarks, Rust is faster for that situation, and speculating, this is because the Rust compiler only recompiles the parts of a TU that actually changed.
In practice, however, Rust is much slower than C, because people do not write small Rust TUs, but absurdly huge ones, at least, by C standards. A Rust TU (crate) usually is mapped 1:1 to a C library, which often contains dozens or hundreds of TUs. Just the cost of testing what changed in a Rust crate is often larger than the cost of blindly recompiling the C TU that has a newer timestamp.
If people would split Rust code like they do with C, then this wouldn't happen. But Rust people are too optimistic in that one day the compiler will be able to somehow auto-magically split a crate into multiple TUs as good or even better than what people do for C manually. And do that determination + the incremental compile faster than what takes a C compiler to blindly recompile a tiny amount of code.
- Nullabillity 6y ago> Rust does not have a global system cache for libraries, and I don't think there is any package manager installing pre-compiled Rust libraries, so at least for the initial compiles, Rust needs to do much more work than C, for Rust dependencies at least. FWIW, Nix can do this (via Carnix). But it turns out not to be too useful anyway, because any feature flags that you use will invalidate the cache for everything that depends (transitively) on that crate.
- Mic92 6y agocrate2nix is better maintained alternative to carnix: https://github.com/kolloch/crate2nix https://github.com/kolloch/crate2nix The cache is still useful though if you think about CI builds or having a common project in a team.
- jfkebwjsbx 6y ago> Rust compiles orders of magnitude faster than similar C++ code for initial compiles Please avoid misleading statements like "orders of magnitude faster". If that were true, even super-complex projects would compile in a few seconds, given it would be at least 100x faster than compiling C++. > For incremental compiles, Rust is infinitely faster. Please avoid obvious exaggerations... Incremental compiles of C++ take as low as modular is the code. Same for Rust. If you make huge TUs, you get huge incremental compile times. > C++, even if you use Modules Modules are not even used yet by any big project nor properly supported yet, and they are not expected to speed up compilation much anyway. > Comparing Rust with C here is hard. It isn't hard: C can be compiled way faster than either C++ or Rust because the code and type system is much simpler. > As others have mentioned, with C, you typically only use libraries that are installed in your system C code can be anything. C++ libraries are also included with the system. > Rust does not have a global system cache for libraries It does have a cache per user/project/etc., which is basically the same and without it the speed would be atrocious.
- Kaze404 6y agoThis type of comment is the worst. What did you add to the conversation besides a bunch of useless "well ackshually"? If you want to respond to a comment, respond to it in full, not only conveniently out of context sentences.
- mlthoughts2018 6y agoThe comment makes good points that need to be considered and helps mitigate the unrealistic exaggerations of the parent comment. This does not fit the “well akshually” trope at all.
- fluffything 6y ago> Please avoid misleading statements like "orders of magnitude faster". If that were true, even super-complex projects would compile in a few seconds, given it would be at least 100x faster than compiling C++. The tests of my Rust range-v3 like library compile in ~12 seconds. The tests of C++'s range-v3 take ~320 seconds to compile. > Please avoid obvious exaggerations... The incremental compile of the same library takes in Rust ~1 second. In C++, it still takes ~320 seconds, zero improvement because C++ header-only generic libraries do not benefit from incremental compilation. > Modules are not even used yet by any big project nor properly supported yet, and they are not expected to speed up compilation much anyway. I maintain a ~500kLOC C++ project that uses modules. C++ Modules did not speed up compilation at all over simple PCHs. > It does have a cache per user/project/etc., which is basically the same and without it the speed would be atrocious. No it does not. Check out any project from crates.io into a subdirectory, do a cargo build. Check it out into another sub-director, do a cargo build. All dependencies are re-built. You'd need to go way out of your way and set up like sscache to get something similar, but Rust and cargo do not do this. > It isn't hard: C can be compiled way faster than either C++ or Rust because the code and type system is much simpler. Citation needed. On my machine, rustc spends ~80% of its time in LLVM, which is slow, because the translation units are huge. The other 20% is split into ~5% parsin, ~5% type checking, and ~10% LLVM-IR generation. Even rustc's synthetic trait metaprogramming benchmarks do not spend even 10% of the compile-time in type checking. So if you have a test for which rustc spends most of its compile-time in type checking, go ahead, and post a link. We'd love to add it to rustc's benchmark suite. Also, on my machine, while clang spends less time in code generation, it is still over ~60%. Clang spends more time in parsing and type checking, and that's because C++ overload resolution scales with the number of visible overloads, and the more header files you have, the more overloads there are (e.g. an error with operator<< on a ~500kLOC project produces ~2000 "potential candidates"). While that's part of the slowdown, still 60% of the time is spent in LLVM. The reason is that idiomatic C++ just produces more code than C due to templates, inlining, etc. for similarly-sized TUs. Parallelizing compilation within a TU is hard to do well. Rustc tries without much success and clang does not. In C, you can simply parallelize by using more compiler processes to compile fully independent TUs in parallel. These TUs are also smaller because idiomatic C code doesn't use many macros to generate code, most functions are linked opaquely, generics also generate few code via void*, and the worst culprit of long compilation times in C, which is including too many header files, can properly be cached using PCHs.