Эта страница описывает Топаз v5.17. Прежде чем считать её актуальной, сверьте поле version в /version.json со значением 5.17.
Типы позволяют проверяющему ответить до запуска программы на практический вопрос: какие значения разрешено передавать через эту границу? Для большинства локальных значений тип писать не нужно. Аннотация полезна там, где она поясняет важный вход, результат или выбор предметной области.
Начните с одной проверяемой программы
Сохраните этот код в файле types.tpz:
type Стадия = "draft" | "ready"
function описать(стадия: Стадия, проверки: int) -> string {
"{стадия} after {проверки} checks"
}
let проверки = 3
let текущая: Стадия = "ready"
let показать: (Стадия, int) -> string = описать
print(показать(текущая, проверки))Сначала проверьте границы типов, затем запустите программу:
topaz check types.tpz
topaz run types.tpz
Результат:
ready after 3 checksПрочитайте типы по коду и результату
У проверки нет аннотации. Начальное значение — целое число, поэтому Топаз выводит тип int. У текущая аннотация есть: программе требуется именно Стадия, а не любая строка string.
Стадия — прозрачный псевдоним для объединения литералов "draft" | "ready". Такое объединение разрешает одно из двух перечисленных значений и отклоняет любую другую строку. Псевдоним даёт выбору понятное имя, но не создаёт отдельной сущности во время выполнения.
У показать указан тип функции. Запись (Стадия, int) -> string означает «функция принимает Стадия и int, а возвращает string». Именованная функция описать имеет именно такую форму, поэтому её можно сохранить в привязке и вызвать позднее.
Названия базовых типов пишутся строчными буквами: int, float, bool, string и единичный тип (). Для контейнеров используются именованные конструкторы Array<T>, Map<K, V> и Set<T>. Ожидаемое отсутствие значения выражается через Option<T>, а восстанавливаемая ошибка — через Result<T, E>.
Выберите форму, которая передаёт намерение
| Задача | Что выбрать | Почему |
|---|---|---|
| Очевидное локальное значение | Вывод типа | Начальное значение уже ясно показывает тип. |
| Публичный вход, результат или важная локальная граница | Аннотацию | Проверяющий и читатель сразу видят задуманный контракт. |
| Одно значение из закрытого набора вариантов | Объединение или псевдоним объединения литералов | Все допустимые варианты перечислены явно. |
| Значение, которое позже будут вызывать | Тип функции, например (int) -> bool | Типы параметров и результата хранятся вместе с функцией. |
| Самостоятельная сущность предметной области, поля или именованные варианты | record, enum или newtype | Номинальные объявления остаются разными, даже если устроены похоже. |
Псевдоним type делает код понятнее, но остаётся прозрачным. Если смешение двух похожих по форме значений было бы настоящей ошибкой, выбирайте номинальные данные. На странице Записи и номинальные данные сопоставлены создание и сопоставление для record, enum и newtype.
Дайте пустому значению контекст
Некоторые значения сами по себе не сообщают достаточно сведений. Пустой массив не показывает тип элемента, а None — тип отсутствующего значения. Контекст можно задать аннотацией, параметром функции, объявленным результатом или окружающим типом:
let имена: Array<string> = []
let выбранное: Option<int> = NoneЗдесь канонические формы показаны как текст. Проверяемой программой этой страницы остаётся полный пример выше.
Частая ошибка: перенос записи типов из целевого языка
Типы коллекций Топаза записываются как Array<T>, Map<K, V> и Set<T>. В типе функции параметры заключаются в круглые скобки, после чего -> отделяет тип результата. Единая запись помогает проверяющему и создаваемым целевым программам опираться на один исходный контракт.
Точные ограничения
- Между
intиfloatнет неявного преобразования. - Параметры обобщённых типов инвариантны: разные аргументы типов не становятся совместимыми лишь из-за сходства содержимого.
- Ограничения обобщённого типа допускаются только у параметров именованной функции. Разрешённая форма первого ранга описана на странице Функции и обобщения.
- Рекурсивные псевдонимы, аннотации вариантности, полиморфизм высших рангов и более широкая рефлексия пока отложены.
- Если контекст так и не определил параметры пустого обобщённого значения, это статическая ошибка, а не повод угадывать тип во время выполнения.
Если вывод типов, аннотации и изменяемость ещё непривычны, вернитесь к уроку Значения и функции. Выбор между отсутствием, восстанавливаемой ошибкой и сбоем разобран на странице Null, Option, Result и ошибки.