Бокс на присвоение ValueType?

2

Если я присваиваю простой тип значения (например, int) атрибуту типа ValueType, это значение затем помещается в коробку?

Например, если я это сделаю:

int i = 4;
ValueType test = i;

Будет ли введено значение?

Теги:

3 ответа

6
Лучший ответ

Да, будет. Это связано с тем, что каждый тип занимает постоянный объем памяти во время выполнения (int занимает, например, 4 байта). Структура будет занимать столько места, сколько требуется для размещения всех полей в памяти.

Поскольку вы можете сохранить любой тип значения в ValueType, а так как ValueType должен быть точно того же размера, что и тип, который вы назначаете test, тип ValueType на самом деле является ссылочным типом.

Рассмотрим:

int a = 0;
long b = 1;

ValueType test;

test = a;
test = b;

Это абсолютно правильный код. test должен занимать фиксированный размер в стеке, а a и b - разные размеры. Надеюсь, это объясняет, почему именно ValueType не может быть типом значения. (Это связано с тем, почему вы не можете выводить типы значений.)

  • 0
    Хорошее объяснение того, почему ValueType является ссылочным типом.
4

Да, это будет в коробке - ValueType является ссылочным типом (классом), достаточно запутанным:) Это просто тип от который каждый тип значения "наследует" (непосредственно в случае структур и косвенно в случае перечислений).

Бокс происходит в любое время, когда вы присваиваете значение типа значения переменной ссылочного типа, включая object, ValueType, Enum и любые интерфейсы. (Это также происходит при использовании значения типа значения в качестве аргумента, где параметр является одним из этих типов и т.д.)

  • 0
    Сегодня я узнал.
  • 0
    Рад, что я не единственный, кого немного смущает, что ValueType является ссылочным типом. Я понимаю почему, но это все же смутило меня ненадолго.
Показать ещё 2 комментария
0

ValueType является ссылочным типом. IL, сгенерированный в этом назначении, фактически блокирует структуру.

Вот пример командной строки при назначении объекту:

void Main()
{
    object o = 1;

    Console.Write(o);
}

IL_0000:  ldc.i4.1    
IL_0001:  box         System.Int32
IL_0006:  stloc.0     
IL_0007:  ldloc.0     
IL_0008:  call        System.Console.Write

И при назначении ValueType:

void Main()
{
    ValueType o = 1;

    Console.Write(o);
}

IL_0000:  ldc.i4.1    
IL_0001:  box         System.Int32
IL_0006:  stloc.0     
IL_0007:  ldloc.0     
IL_0008:  call        System.Console.Write

Ещё вопросы

Сообщество Overcoder
Наверх
Меню