Considering code below:
// Component code:
class B
{
public int Val
{
get {return 1;}
}
}
class D : B
{
public new int Val
{
set {value;}
}
}
// Client code:
// C#
D d = new D();
int i = d.Val; // compile error
// C++/CLI
D^ d = gcnew D();
int i = d->Val; // ok
Why is there this diversity? As we know, all .net program would output to IL code, so the code and its metadata should be same as each other, but why the get accessor is available in C++/CLI but invalid in C#? In addition, is it valid if from perspective of CLR?
Then I used IL disasembler to get IL of above code and found that B class includes a Val property definition with get accessor, D includes a Val property definition with set accessor, and get and set methods are marked as hide sig respectively. d->Val in C++/CLI is compiled to code like below:
int i = d->B::Val::get()
I guessed C++/CLI compiler try its best to query get method, so it invokes base class's in case of no get method definition in child class's metadata, while C# prefer treating the property as an integrity, so it is invalid when compiler find the property without get accessor hides base on.
The fact that child class doesn't include get definition can be proven by reflection:
// C#
D d = new D();
int i = (int)typeof(B).GetProperty("Val").GetValue(d); //ok
i = (int)typeof(D).GetProperty("Val").GetValue(d); // an exception will be thrown
We can get the same result if using C++/CLI as expected, since reflection is independent with concrete languages.
Conclusion:
As a basic grammar in C# and CLR, property is considered as an elements, which include one or two methods definition but not equal to methods. However, since standard c++ doesn't define property, C++/CLI designer may prefer treating it as one or two seperate methods. This case demonstrates the different philosophy between two languages in the face of the same issue, interesting!