Compiling your .NET application results in output assemblies that contain a great deal of meta information. This information makes it very easy to reconstruct something very close to the original code. An excellent free tool called .NET Reflector can be used to do exactly that and is a popular way to examine how the base class libraries work. Download and use that tool to view reconstructed C#/VB.NET versions of assembly contents.
If you're a commerical organization then you do not want people to find it easy to look at your expensive to produce code. A popular method is to use Obfuscation to scramble the contents in a way that does not alter how it runs but does make it hard to understand. Obfuscation uses techniques such as renaming variables and methods. Working out the purpose of methods 'a1', 'a2', 'a3' is much harder than the original 'GetName', 'UpdateInterestRate' and 'SetNewPassword'.
So using obfuscation makes it much harder for people to understand what you code is doing and the algorithms it uses. It does not however make it impossible. In the same way C++ code can still be understood by an assembler expert who is willing to spent time working through your binary, an MSIL expert can eventually work out your obfuscated code. But it increases the barrier to the point where few will bother trying.