Jawaban:
Ini harus menjawab pertanyaan itu, dan kemudian beberapa.
Baris kedua,, if (obj.GetType() == typeof(ClassA)) {}lebih cepat, bagi mereka yang tidak ingin membaca artikel.
(Ketahuilah bahwa mereka tidak melakukan hal yang sama)
typeof(string).TypeHandledengan ldtokeninstruksi CIL, tetapi sepertinya CLR mengurusnya di JIT. Masih membutuhkan beberapa opcodes tambahan tetapi ini merupakan aplikasi optimisasi yang lebih umum.
GetType, isselalu merupakan pilihan yang lebih aman sejauh menyangkut kinerja. Tentu saja mereka melakukan hal yang berbeda.
object obj;variabel, bukankah sudah boxed ketika ini cenderung diuji? Apakah ada kasus di mana Anda perlu menguji jenis sesuatu dan itu belum dikotakkan sebagai objek?
Apakah penting yang lebih cepat, jika mereka tidak melakukan hal yang sama? Membandingkan kinerja pernyataan dengan makna berbeda sepertinya ide yang buruk.
ismemberi tahu Anda jika objek mengimplementasikan ClassAdi mana saja dalam jenis heirarki. GetType()memberi tahu Anda tentang jenis yang paling diturunkan.
Bukan hal yang sama.
Mereka tidak melakukan hal yang sama. Yang pertama berfungsi jika obj adalah tipe ClassA atau beberapa subclass dari ClassA. Yang kedua hanya akan cocok dengan objek bertipe ClassA. Yang kedua akan lebih cepat karena tidak harus memeriksa hierarki kelas.
Bagi mereka yang ingin tahu alasannya, tetapi tidak ingin membaca artikel yang dirujuk adalah vs typeof .
Saya melakukan benchmarking di mana mereka melakukan jenis yang sama - disegel.
var c1 = "";
var c2 = typeof(string);
object oc1 = c1;
object oc2 = c2;
var s1 = 0;
var s2 = '.';
object os1 = s1;
object os2 = s2;
bool b = false;
Stopwatch sw = Stopwatch.StartNew();
for (int i = 0; i < 10000000; i++)
{
b = c1.GetType() == typeof(string); // ~60ms
b = c1 is string; // ~60ms
b = c2.GetType() == typeof(string); // ~60ms
b = c2 is string; // ~50ms
b = oc1.GetType() == typeof(string); // ~60ms
b = oc1 is string; // ~68ms
b = oc2.GetType() == typeof(string); // ~60ms
b = oc2 is string; // ~64ms
b = s1.GetType() == typeof(int); // ~130ms
b = s1 is int; // ~50ms
b = s2.GetType() == typeof(int); // ~140ms
b = s2 is int; // ~50ms
b = os1.GetType() == typeof(int); // ~60ms
b = os1 is int; // ~74ms
b = os2.GetType() == typeof(int); // ~60ms
b = os2 is int; // ~68ms
b = GetType1<string, string>(c1); // ~178ms
b = GetType2<string, string>(c1); // ~94ms
b = Is<string, string>(c1); // ~70ms
b = GetType1<string, Type>(c2); // ~178ms
b = GetType2<string, Type>(c2); // ~96ms
b = Is<string, Type>(c2); // ~65ms
b = GetType1<string, object>(oc1); // ~190ms
b = Is<string, object>(oc1); // ~69ms
b = GetType1<string, object>(oc2); // ~180ms
b = Is<string, object>(oc2); // ~64ms
b = GetType1<int, int>(s1); // ~230ms
b = GetType2<int, int>(s1); // ~75ms
b = Is<int, int>(s1); // ~136ms
b = GetType1<int, char>(s2); // ~238ms
b = GetType2<int, char>(s2); // ~69ms
b = Is<int, char>(s2); // ~142ms
b = GetType1<int, object>(os1); // ~178ms
b = Is<int, object>(os1); // ~69ms
b = GetType1<int, object>(os2); // ~178ms
b = Is<int, object>(os2); // ~69ms
}
sw.Stop();
MessageBox.Show(sw.Elapsed.TotalMilliseconds.ToString());
Fungsi generik untuk menguji tipe generik:
static bool GetType1<S, T>(T t)
{
return t.GetType() == typeof(S);
}
static bool GetType2<S, T>(T t)
{
return typeof(T) == typeof(S);
}
static bool Is<S, T>(T t)
{
return t is S;
}
Saya mencoba jenis kustom juga dan hasilnya konsisten:
var c1 = new Class1();
var c2 = new Class2();
object oc1 = c1;
object oc2 = c2;
var s1 = new Struct1();
var s2 = new Struct2();
object os1 = s1;
object os2 = s2;
bool b = false;
Stopwatch sw = Stopwatch.StartNew();
for (int i = 0; i < 10000000; i++)
{
b = c1.GetType() == typeof(Class1); // ~60ms
b = c1 is Class1; // ~60ms
b = c2.GetType() == typeof(Class1); // ~60ms
b = c2 is Class1; // ~55ms
b = oc1.GetType() == typeof(Class1); // ~60ms
b = oc1 is Class1; // ~68ms
b = oc2.GetType() == typeof(Class1); // ~60ms
b = oc2 is Class1; // ~68ms
b = s1.GetType() == typeof(Struct1); // ~150ms
b = s1 is Struct1; // ~50ms
b = s2.GetType() == typeof(Struct1); // ~150ms
b = s2 is Struct1; // ~50ms
b = os1.GetType() == typeof(Struct1); // ~60ms
b = os1 is Struct1; // ~64ms
b = os2.GetType() == typeof(Struct1); // ~60ms
b = os2 is Struct1; // ~64ms
b = GetType1<Class1, Class1>(c1); // ~178ms
b = GetType2<Class1, Class1>(c1); // ~98ms
b = Is<Class1, Class1>(c1); // ~78ms
b = GetType1<Class1, Class2>(c2); // ~178ms
b = GetType2<Class1, Class2>(c2); // ~96ms
b = Is<Class1, Class2>(c2); // ~69ms
b = GetType1<Class1, object>(oc1); // ~178ms
b = Is<Class1, object>(oc1); // ~69ms
b = GetType1<Class1, object>(oc2); // ~178ms
b = Is<Class1, object>(oc2); // ~69ms
b = GetType1<Struct1, Struct1>(s1); // ~272ms
b = GetType2<Struct1, Struct1>(s1); // ~140ms
b = Is<Struct1, Struct1>(s1); // ~163ms
b = GetType1<Struct1, Struct2>(s2); // ~272ms
b = GetType2<Struct1, Struct2>(s2); // ~140ms
b = Is<Struct1, Struct2>(s2); // ~163ms
b = GetType1<Struct1, object>(os1); // ~178ms
b = Is<Struct1, object>(os1); // ~64ms
b = GetType1<Struct1, object>(os2); // ~178ms
b = Is<Struct1, object>(os2); // ~64ms
}
sw.Stop();
MessageBox.Show(sw.Elapsed.TotalMilliseconds.ToString());
Dan jenisnya:
sealed class Class1 { }
sealed class Class2 { }
struct Struct1 { }
struct Struct2 { }
Kesimpulan:
Memanggil GetTypedi structs lebih lambat. GetTypedidefinisikan pada objectkelas yang tidak dapat diganti dalam sub tipe dan dengan demikian structperlu dikotak untuk dipanggil GetType.
Pada instance objek, GetTypelebih cepat, tetapi sangat marginal.
Pada jenis generik, jika Tyaitu class, maka isjauh lebih cepat. Jika Tini struct, maka isjauh lebih cepat daripada GetTypetetapi typeof(T)jauh lebih cepat dari keduanya. Dalam kasus Tsedang class, typeof(T)tidak dapat diandalkan karena berbeda dari tipe yang mendasarinya sebenarnya t.GetType.
Singkatnya, jika Anda memiliki sebuah objectinstance, gunakan GetType. Jika Anda memiliki classtipe generik , gunakan is. Jika Anda memiliki structtipe generik , gunakan typeof(T). Jika Anda tidak yakin apakah tipe generik adalah tipe referensi atau tipe nilai, gunakan is. Jika Anda ingin konsisten dengan satu gaya selalu (untuk tipe tertutup), gunakan is..