There is a simple reason why MS does not like this model - if any program contains its own version of the .NET framework DLLs, Windows Update would not effectively be able to supply any security updates / bug fixes any more for the .NET framework DLLs. And this is not a hypothetical issue: every few months, a new patch or security update for the framework DLLs was deployed by MS in the past.
The situation that MS gave specific run time DLLs to the application vendors, and let the vendors be responsible for deploying and updating the DLLs themselves, is not a new one. For example, the MFC-DLLs, the GDI+ DLLs and some other libraries were often deployed that way. But this almost always lead to a situation where users had troubles in getting important updates for these DLLs. See, for example, here, for the case from 2004 where gdiplus.dll had to be updated - and what trouble that meant for the users, compared to a relatively flawless update using the "Windows Update" mechanisms. From that experience I guess MS came to the conclusion not to give the responsibility for updates out of their hands.
To your arguments:
1) We often don't use all the dlls but we force customers to install the entire .NET framework. It would be great to just deploy the dlls we need.
Newer Windows version already contain .NET FW 3.5 or 4.0 And if not, the framework has to be installed once per machine (ok, 3.5 once and 4.0 once), not again and again for every application which needs it
2) We often want to update our application and the framework but that sometimes requires a machine reboot because other applications are using it.
You typically don't want to update the framework by yourself, Windows Update does that for you. And if you are going to use a newer framework version which so far is not installed on the machine, there obviously cannot be another application using the newer framework so far.
3) A full .NET installation usually takes quite a bit of time. An xcopy type private deployment could be much faster.
Yes, but only once per machine, not once per application.
@BryantB's answer is also true. Especially, because the execution model of .NET assemblies does not check if all needed assemblies are installed before the JITer compiles a function call to one of those assemblies. This means, if you forget to deploy a framework DLL, your program might start flawlessly, but will crash later when the first feature is used which needs the forgotten DLL. This behaviour is quite different from native DLLs (not delay-loaded ones, of course), and would be a dangerous error-trap.