Indeed, a JIT compiler will always be able to take advantage of something that isn't possible for something that is compiled once and set in stone.
However, that's not to say that upfront compilation is doomed never to compete.
Profiling C compilers can mimic this behaviour to an extent, although they can only profile for the situtations they experience during their training phase so they can't adapt to unforeseen scenarios or dramatic shifts in the input stream.
C compilers could be extended to implement several/many variants of each function based on different possible code paths and, using information gained from on the fly timings it could switch between different variants in order to optimise execution. Combinatorics would place a low limit on the number of percentage of possible variants implemented though.
Finally, no-one ever said that C has to be a compiled language. There's nothing stopping someone writing a JIT C interpreter and getting the best of both worlds. (Ugh!)
True, I should have been clearer that I meant only C under the mainstream implementation style. If you get creative there are so many wonderful options. I know there's already TCC and a variety of REPLs.
Comments
You can carefully design an interpreter to mitigate these issues.
You can also have a JIT compiler remove branches altogether based on experimental data, something completely impossible in C.
Don't point at one thing and claim it makes a language class faster or slower.
Indeed, a JIT compiler will always be able to take advantage of something that isn't possible for something that is compiled once and set in stone.
However, that's not to say that upfront compilation is doomed never to compete.
Profiling C compilers can mimic this behaviour to an extent, although they can only profile for the situtations they experience during their training phase so they can't adapt to unforeseen scenarios or dramatic shifts in the input stream.
C compilers could be extended to implement several/many variants of each function based on different possible code paths and, using information gained from on the fly timings it could switch between different variants in order to optimise execution. Combinatorics would place a low limit on the number of percentage of possible variants implemented though.
Finally, no-one ever said that C has to be a compiled language. There's nothing stopping someone writing a JIT C interpreter and getting the best of both worlds. (Ugh!)
True, I should have been clearer that I meant only C under the mainstream implementation style. If you get creative there are so many wonderful options. I know there's already TCC and a variety of REPLs.
C++/CLI probably comes close to "C with JIT"
Isn't it possible to JIT C code with LLVM?
It's not impossible in C. It's impossible statically.
There is nothing that stops you from JIT'ing C/C++. LLVM includes a JIT that functions just fine on C/C++ programs.