The answer by OriginalGriff is very good. I only want to add an idea what is essential to know: you need to understand that compilation is divided between two major phases: compilation into byte code (CIL code; this is what a .NET compilers do) and Just In Time compilation (JIT) which is done after loading of the byte code and interlaced with run-time.
In fact, JIT compiler compiles into native (CPU) code on per-method basis; as a result, even if some dead code is present in the assembly, it will be never JIT-compiled; and even non-dead code may or may not be compiled if the call depends on run-time conditions.
This is a good reading for to start with:
http://en.wikipedia.org/wiki/Common_Language_Runtime[
^]