Зачем вызывать некоторые функции класса объекта, на примитивном экземпляре типа нужны бокс?

StackOverflow https://stackoverflow.com/questions/2179366

  •  24-09-2019
  •  | 
  •  

Вопрос

Я обнаружил, что если у меня будет следующие строки кода.

int i = 7;
i.GetHashCode(); //where GetHashCode() is the derived
                 //function from System.Object

Без бокса не сделано, но если я позвоню i.GetType() (другая производная функция из System.Object) на месте GetHashCode(), Бокс потребуется позвонить GetType(), Почему его невозможно позвонить GetType() на примитивный тип экземпляра напрямую, без бокса, в то время как можно позвонить GetHashCode() Без бокса?

Это было полезно?

Решение

Ключ вот что GetType() не виртуально и не может быть переопределен. Так как структура эффективно sealed, методы не могут быть переопределены любой более чем структуру, поэтому время выполнения и компилятор могут лечить методы структуры которые были переопределены как статические звонки.

Если вы пишете структуру (редко) вы должен переопределить все методы, такие как ToString(), Equals(), GetHashCode() Именно по этой причине. Если вы этого не сделаете, не должен. Однако, GetType() не можем быть переопределенным, таким образом, нуждается в боксе.

Это на самом деле приводит к каким-то нечетным краям Nullable<T> и бокс, так как пустой Nullable<T> коробки к null, так:

int i = obj.GetHashCode(); // fine
Type t = obj.GetType(); // boom

Другие советы

Я думаю, что причина в том, что GetHashCode реализуется на System.int32 напрямую, вы называете System.int32 :: GetHashCode (). Нет необходимости в коробке, если вы называете известную функцию члена в типе значений.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top