Почему указатели ссылаются на типы? - PullRequest
19 голосов
/ 23 июля 2010

На этой неделе я работал над некоторым основанным на отражении кодом и во время модульного тестирования обнаружил неожиданное условие: указатели являются ссылочными типами. Код C # typeof(int).MakePointerType().IsClass возвращает true.

Я зарегистрировал свой только что прибывший аннотированный стандарт CLI, и, безусловно, указатели четко определены как ссылочные типы.

Это меня удивило, пришло из C ++ фона. Я только что предположил, что указатели будут типами значений.

Есть ли конкретная причина, по которой типы указателей являются ссылочными типами, а не типами значений?

Обновление (уточнение)

Когда речь идет об указателях и ссылках, часто возникает путаница в отношении "указателя" и "указателя". Итак, вот некоторые пояснения.

Типы могут быть ссылочными типами или типами значений, но переменные немного отличаются. (Извините, у меня не было возможности прочитать мой стандарт CLI, поэтому терминология и концепции могут быть неправильными - поправьте меня, пожалуйста!)

Учитывая этот код (концепции локальных переменных для ссылочных типов):

var x = new MyClass();
var y = x;

Переменные x и y на самом деле не являются ссылочными типами, но они являются ссылками на объект, который является ссылочным типом (MyClass является ссылочным типом). Другими словами, x и y не являются экземплярами ссылочного типа; они относятся только к экземпляру ссылочного типа.

С учетом этого кода (понятия локальных переменных для типов значений):

var x = 13;
var y = x;

Переменные x и y являются типами значений экземпляров (или, по крайней мере, действуют как экземпляры).

Итак, мы приходим к этому коду:

var i = 13;
var x = &i;
var y = x;

Если указатель тип является ссылочным типом , то я так интерпретирую оператор x = &i:

  1. Создается экземпляр типа int*, указывающий на i.
  2. Поскольку указатели являются ссылочными типами, этот экземпляр создается в куче (при условии, что все ссылочные типы размещены в куче, подробности реализации).
  3. x является ссылкой на этот экземпляр указателя.
  4. Экземпляр указателя будет в конечном итоге собираться мусором, как и другие ссылочные типы.
  5. Когда выполняется y = x, ссылка копируется. И y, и x ссылаются на один и тот же экземпляр объекта указателя.

Возможно, я совершенно не прав в этой интерпретации.

Исходя из фона C ++, для меня было бы более разумно, чтобы указатели были типами значений, поэтому оператор x = &i просто присваивает адрес i экземпляру типа значения x, и y = x копирует это значение адреса в y. «Объект-указатель» не будет создан в куче.

Ответы [ 5 ]

4 голосов
/ 01 июля 2011

Я не видел полного ответа, поэтому сейчас закрываю этот вопрос.

Я вынужден сделать вывод: указатели (например, int *) на самом деле являются типами значений ; тот факт, что их Type s возврат true для IsClass является ошибкой в ​​спецификации. Я подозреваю, что никто не заметил этого, потому что получение типа указателя - очень редкая операция.

3 голосов
/ 23 июля 2010

typeof (int) .MakePointerType (). IsPointer

кажется, что есть различие.

1 голос
/ 23 июля 2010

Это всего лишь теория, но будет ли это как-то связано с тем, что из-за системы сбора мусора и сжатия кучи указатели должны корректироваться, когда объекты перемещаются в памяти. Создавая ссылочные типы управляемых указателей, они могут быть переназначены так же, как любая другая ссылка, вместо того, чтобы делать их особым случаем.

Обновление

Отличная статья Wesner Moise: " Указатели не раскрыты ".

В статье он описывает, как настраиваются управляемые указатели при сжатии кучи.

0 голосов
/ 23 июля 2010

Рассмотрим:

MyClass x = new MyClass();

Здесь MyClass является ссылочным типом, и если вы посмотрите через отражение, x будет называться ссылочным типом. Но под капотом x на самом деле является указателем.

0 голосов
/ 23 июля 2010

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

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...