Подтвердить что ты не робот

Что более эффективно: myType.GetType() или typeof (MyType)?

Предположим, что у меня есть класс MyType:

sealed class MyType
{
    static Type typeReference = typeof(MyType);
    //...
}

С учетом следующего кода:

var instance = new MyType();
var type1 = instance.GetType();
var type2 = typeof(MyType);
var type3 = typeReference;

Какое из этих назначений переменных будет наиболее эффективным?

Является ли производительность GetType() или typeof() достаточной, чтобы было полезно сохранить тип в статическом поле?

4b9b3361

Ответ 1

typeof(SomeType) - простой поиск токенов метаданных

GetType() - виртуальный вызов; на стороне плюса вы получите производный тип, если он является подклассом, но на минусовой стороне вы получите производный класс, если он является подклассом. Если вы понимаете, что я имею в виду. Кроме того, GetType() требует бокса для структур и не подходит для нулевых структур.

Если вы знаете тип в compiletime, используйте typeof().

Ответ 2

Я бы пошел с type2. Это не требует создания экземпляра экземпляра для получения типа. И это самый читаемый человеком.

Ответ 3

Единственный способ узнать - измерить.

Вариант "type1" не является надежным или рекомендуемым каким-либо образом, поскольку не все типы могут быть построены. Хуже того, он выделяет память, которая должна быть сборщиком мусора и вызывает конструкторы объектов.

Для оставшихся двух параметров на моей машине "type3" примерно в два раза быстрее, чем "type1" в обоих режимах отладки и выпуска. Помните, что это справедливо только для моего теста - результаты могут быть неверными для других типов процессоров, типов машин, компиляторов или версий .NET.

        var sw = System.Diagnostics.Stopwatch.StartNew();
        for (int i = 0; i < 10000000; i++)
        {
            var y = typeof(Program).ToString();
        }
        sw.Stop();
        Console.WriteLine(sw.ElapsedMilliseconds);

        sw.Restart();
        for (int i = 0; i < 10000000; i++)
        {
            var y = typeReference.ToString();
        }
        sw.Stop();
        Console.WriteLine(sw.ElapsedMilliseconds);

Тем не менее, это немного тревожит этот вопрос, который задают без четкого требования. Если вы заметили проблему с производительностью, вы, вероятно, уже профилировали ее и знали, какой вариант лучше. Это говорит мне о том, что это, вероятно, преждевременная оптимизация - вы знаете высказывание: "преждевременная оптимизация - это корень всего зла".

Код программирования не измеряется только производительностью. Он также измеряется правильностью, производительностью разработчиков и ремонтопригодностью. Увеличение сложности вашего кода без причины strong просто переносит стоимость в другое место. То, что могло быть без проблем, теперь превратилось в серьезную потерю производительности, как сейчас, так и будущих сторонников приложения.

Моя рекомендация заключалась бы в том, чтобы всегда использовать вариант "type1" . Перечисленный мной код измерения не является реальным сценарием. Кэширование typeof для ссылочной переменной, вероятно, имеет массу побочных эффектов, особенно вокруг того, как .NET загружает сборки. Вместо того, чтобы загружать их только тогда, когда это необходимо, это может привести к загрузке их всех при каждом использовании приложения - превращение теоретической оптимизации производительности в очень реальную проблему с производительностью.

Ответ 4

Они совсем другие.

typeof(MyType) получает объект Type, описывающий тип MyType, разрешенный в компиляторе, с помощью команды ldtoken.

myInstance.GetType() получает объект Type, описывающий тип выполнения переменной myInstance.

Оба предназначены для разных сценариев.

Вы не можете использовать typeof(MyType), если вы не знаете тип во время компиляции и имеете к нему доступ.

Вы не можете использовать myInstance.GetType(), если у вас нет экземпляра этого типа.

typeof(MyType) всегда более эффективен, но вы не можете использовать, если вы не видите тип во время компиляции. Вы не можете использовать typeof(MyType), чтобы узнать реальный тип выполнения некоторой переменной, потому что вы не знаете тип.

Ответ 5

Оба в основном то же самое. Хотя typeof можно использовать в классе без экземпляра, например

typeof(MyClass);

Но

MyClass.GetType();

даже не будет создан, так как вам нужно иметь экземпляр класса.

Короче говоря, они выполняют одну и ту же работу в разных контекстах.