Что на самом деле означает ключевое слово `type` при использовании в определении типа?

Недавно я прочитал несколько строк исходного кода VCL и нашел определение типа TCaption:

TCaption = type string;

Я всегда думал, что это просто другое имя для типа string, и я думал, что оно определяется следующим образом:

TCaption = string;

Поэтому я искал документацию о ключевом слове type. и я нашел это:

  1. type Name = Existing type
    Ссылается на существующий тип, например string, новым Именем.

  2. type Name = type Existing type
    Это имеет тот же эффект, что и выше, но гарантирует, что во время выполнения переменные этого типа идентифицируются по их новому имени типа, а не существующему имени типа.

После прочтения я все еще в замешательстве и не понимаю, что на самом деле означает "...гарантирует, что во время выполнения переменные этого типа идентифицируются по их новому имени типа..." .

Может ли кто-нибудь пролить свет на это?


person Fabrizio    schedule 19.08.2017    source источник
comment
@Tom Brunberg: Где следует использовать тег VCL, если не здесь?   -  person Fabrizio    schedule 19.08.2017
comment
DelphiBasics похож на W3Schools для веб-разработчиков (он не обновляется). @ExDev, ваш вопрос касается RTL, VCL связан с визуальным управлением.   -  person Victoria    schedule 19.08.2017
comment
Ваш вопрос не связан с Vcl или какой-либо другой библиотекой компонентов. Это больше вопрос о самом языке.   -  person Tom Brunberg    schedule 19.08.2017
comment
@TomBrunberg: Вы правы, на самом деле это был неправильный тег   -  person Fabrizio    schedule 19.08.2017
comment
@Victoria: Вы правы, я сначала поищу документацию embarcadero.   -  person Fabrizio    schedule 19.08.2017
comment
@ Том, как ты думаешь, мы можем говорить о RTL в случае внутренних компонентов компилятора? Наверное, я ошибся в своем комментарии. Я просто разделяю Delphi (более или менее) на две части, визуальную часть и часть времени выполнения, поэтому я подумал, что это может быть связано с частью времени выполнения. Что вы думаете?   -  person Victoria    schedule 19.08.2017
comment
@Victoria IMO, это вопрос об определенном синтаксисе и о том, как он интерпретируется компилятором. Я понимаю ваш спор, особенно с учетом того, что в дело вмешивается RTTI, но все же я утверждаю, что это языковой вопрос.   -  person Tom Brunberg    schedule 19.08.2017
comment
@ Том, определенно есть. Я полностью понимаю ваше правильное удаление тега VCL. Мне просто интересно, могу ли я уточнить такой вопрос как RTL.   -  person Victoria    schedule 19.08.2017
comment
Дорогая @Victoria, тебе не нужно спрашивать моего разрешения ;) Просто... сделай это!   -  person Tom Brunberg    schedule 19.08.2017
comment
@Victoria RTL = Библиотека времени выполнения. Эта языковая функция влияет на компилятор. Вы можете принять ответ Тома: удалить ненужную зависимость от формы и переместить ее в один репродукционный файл DPR с нулевыми зависимостями library. Это должно прояснить, что, хотя это также влияет на RTL, здесь нет серого. Это явно языковой вопрос, а не библиотечный вопрос любого рода. (К сожалению, ссылка OP на ошибочную стороннюю документацию, похоже, создала здесь ненужную путаницу.)   -  person Disillusioned    schedule 20.08.2017


Ответы (2)


Объявление типа как

TCaption = type string;

создает новый тип с другой информацией RTTI. Также его нельзя использовать как var параметр функции, если требуется string тип.

Новая информация RTTI «... гарантирует, что во время выполнения переменные этого типа идентифицируются по их новому имени типа ...». Поэтому, если вы попытаетесь получить имя типа для экземпляра TCaptionSame = string;, вы получите string, а для переменной типа TCaption вы получите TCaption.

Для получения более точной информации лучше обратиться к официальной справке.

person MBo    schedule 19.08.2017

Рассмотрим следующий код и обратите внимание, что процедура Check() имеет параметр var:

type
  Ta = string;       // type alias
  Tb = type string;  // compatible but distinct new type

procedure Check(var s: string);
begin
  ShowMessage(s);
end;

procedure TMain.Button2Click(Sender: TObject);
var
  a: Ta;
  b: Tb;
begin
  a := 'string of type Ta,';
  b := 'string of type Tb.';
  Check(a);
  Check(b);
end;

Check(b) приводит к ошибке компилятора: E2033 Типы фактических и формальных параметров var должны совпадать

В приведенном выше примере тип Tb совместим с string в том смысле, что вы можете f. бывший. назначить a := b, но отличается тем, что type identifier (под капотом) имеет другое значение и, следовательно, не принимается в качестве аргумента для Check(var s: string).

person Tom Brunberg    schedule 19.08.2017
comment
Специализация типа поможет сделать код более надежным и безопаснее. Одной из самых больших неудач в истории НАСА был Mars Climate Orbiter. Ошибка переменного типа сожгла проект стоимостью 327,6 миллиона долларов за считанные минуты, когда одна группа инженеров, работавшая над двигателями, измеряла в английских единицах фунт-сила-секунды, тогда как другие использовали метрические ньютон-секунды. Результат этого невнимания теперь потерян в пространстве, возможно, на куски. - person Arnaud Bouchez; 20.08.2017
comment
Обратите внимание, что помощники Delphi по работе со строками настолько несовершенны, что если вы определите собственный type string то вы не сможете получить доступ к string вспомогательным псевдометодам. Они сломали богатую особенность программирования на Паскале за десятилетия, чтобы добавить функцию, подобную C#/Java. - person Arnaud Bouchez; 20.08.2017