Last time we saw how type markers can result in code optimizations because .NET knows types with structs and can get rid of some code. Today we are going to see that it can actually devirtualize calls.
Let’s get this code:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
using System;
publicclassClass{
publicstaticvoidMain(string[]args){
Bar(newA());
Bar(newB());
Bar(newC());
}
publicstaticvoidBar<T>(Tval)whereT:IFoo{
val.Foo();
}
}
publicinterfaceIFoo{
voidFoo();
}
publicclassA:IFoo{
publicvoidFoo(){
Console.WriteLine("A");
}
}
publicclassB:IFoo{
publicvoidFoo(){
Console.WriteLine("B");
}
}
publicstructC:IFoo{
publicvoidFoo(){
Console.WriteLine("C");
}
}
Generic method for value types must be JITted differently than for normal reference types. This is the code of Main method: