Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    primarykey
    data
    text
    <p>Thank you Greg for your answer it happens the way you describe it. However, I am not pleased with this situation because it means that I have to place </p> <pre><code>if(this == nullptr) throw gcnew ArgumentException("this"); </code></pre> <p>at the beginning of every method. Only this would guarantee that my method won't appear at the top of stack-trace as a faulty piece of code without argument validation. </p> <p>I have never come across (this == null) when I was writing in C#. Therefore, I decided to find out how is it different from C++/CLI. I created a sample application in C++/CLI:</p> <pre><code>namespace ThisEqualsNull{ public ref class A { public: void SampleMethod() { System::Diagnostics::Debug::Assert(this != nullptr); } }; public ref class Program{ public: static void Main(array&lt;System::String ^&gt; ^args) { A^ a = nullptr; a-&gt;SampleMethod(); } }; } </code></pre> <p>And a small program in C# that uses the C++/CLI classes with the same Main method:</p> <pre><code>class Program { static void Main(string[] args) { A a = null; a.SampleMethod(); } } </code></pre> <p>Then I disassembled them with Red Gate's .NET Reflector:</p> <pre><code>C++/CLI .method public hidebysig static void Main(string[] args) cil managed { .maxstack 1 .locals ( [0] class ThisEqualsNull.A a) L_0000: ldnull L_0001: stloc.0 L_0002: ldnull L_0003: stloc.0 L_0004: ldloc.0 L_0005: call instance void ThisEqualsNull.A::SampleMethod() L_000a: ret } C# .method private hidebysig static void Main(string[] args) cil managed { .entrypoint .maxstack 1 .locals init ( [0] class [ThisEqualsNull]ThisEqualsNull.A a) L_0000: nop L_0001: ldnull L_0002: stloc.0 L_0003: ldloc.0 L_0004: callvirt instance void [ThisEqualsNull]ThisEqualsNull.A::SampleMethod() L_0009: nop L_000a: ret } </code></pre> <p>The important parts are:</p> <pre><code>C++/CLI L_0005: call instance void ThisEqualsNull.A::SampleMethod() C# L_0004: callvirt instance void [ThisEqualsNull]ThisEqualsNull.A::SampleMethod() </code></pre> <p>Where:</p> <ul> <li>call - Calls the method indicated by the passed method descriptor.</li> <li>callvirt - Calls a late-bound method on an object, pushing the return value onto the evaluation stack.</li> </ul> <p>And now the final conclusion: </p> <h3>C# compiler in VS 2008 treats every method as if it was virtual, thus it it always safe to assume that (this != null). In C++/CLI every method is called as it should so it is necessary to pay attention to the non-virtual method calls.</h3>
    singulars
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. VO
      singulars
      1. This table or related slice is empty.
    2. VO
      singulars
      1. This table or related slice is empty.
    3. VO
      singulars
      1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload