Что такое $ {type} Var в Kotlin / Native? - PullRequest
2 голосов
/ 19 марта 2019

Эта документация мне очень непонятна, когда она пытается сказать, что такое ${type}Var.

... для перечислений Kotlin это называется ${type}Var

wat ?!Что такое перечисления Kotlin?Обычные перечисления Kotlin?

enum class MyEnum {
    FIRST, SECOND
}

Не думаю, что это подразумевается.

Хорошо, давайте посмотрим на примеры в этой документации:

struct S*сопоставлен с CPointer<S>, int8_t* сопоставлен с CPointer<int_8tVar>

Хорошо, все ясно

char** сопоставлен с CPointer<CPointerVar<ByteVar>>

Почему char** отображается на CPointer<CPointerVar<ByteVar>>, а не на CPointer<CPointer<Byte>>?

Итак, наконец, возникает вопрос: что такое IntVar, LongVar, CPointerVar<T> и другиетакие вещи, как ${type}Var?

Ответы [ 2 ]

2 голосов
/ 19 марта 2019

Вы должны снова внимательно прочитать весь абзац.

Все поддерживаемые типы C имеют соответствующие представления в Kotlin:

  • Перечисления могут быть сопоставлены с перечислением Kotlin

Также в C есть lvalue и rvalue (в C ++ эквивалент равен Type & для lvalue и Type для rvalue).Основное отличие состоит в том, что для lvalues ​​может быть установлено какое-то значение, тогда как rvalues ​​не может быть изменено после инициализации.Таким образом, для каждого типа в C вам нужен свой собственный тип Kotlin для lvalue и для rvalue.

В теме

Все поддерживаемые типы C имеют соответствующие представления в Kotlin:

учитываются только значения.Но для lvalues ​​вам нужно только добавить Var в конец типа.Единственное исключение:

Для структур (и typedefs для структур) это представление является основным и имеет то же имя, что и сама структура

Теперь давайте вернемся к перечислениям,Регулярные перечисления Kotlin отображаются в регулярные перечисления C.Так что на самом деле FIRST и SECOND имеют тип MyEnum на обоих языках.Но что, если вы хотите создать переменную, содержащую MyEnum, например:

// This is C Code
MyEnum a = FIRST;

a имеет тип MyEnum в C, но это lvalue (в C ++ это MyEnum &), поэтому вKotlin a будет иметь тип MyEnumVar, потому что это именно то, что сказано в документации: ${type}Var, где ${type} = MyEnum.

На следующие вопросы:

ТипАргумент T CPointer должен быть одним из типов "lvalue"

Так что для struct S* это должно быть CPointer<SVar>, но помните, что struct s являются исключениями, и мы не должны добавлять Var, так что это просто CPointer<S>.

  • int8_t* - это CPointer<int_8tVar> - здесь не исключение.
  • char* - это CPointer<ByteVar> - опять не исключение (только lvalue-типы, кроме структур).
  • char** - это CPointer<CPointerVar<ByteVar>>, поскольку нам нужно lvalue для CPointer<ByteVar>, и это точно CPointerVar<ByteVar>.

Наконец: IntVar, LongVar, CPointerVar<T>и другие вещи являются значениями типов int, long, CPointer.Это может понадобиться, если вы хотите изменить объект в функции.Что-то вроде Ref<${type}> в Java.

1 голос
/ 19 марта 2019

что такое IntVar, LongVar, CPointerVar<T> и другие вещи, такие как ${type}Var?

Это начало предложения, конец которого вы процитировали:

тип Kotlin, представляющий lvalue этого типа, т. Е. Значение, находящееся в памяти, а не простое неизменное автономное значение

«находится в памяти» означает, что вы можете взять их адрес (используя оператор & в C или .ptr в Kotlin).

wat ?!Что такое перечисления Kotlin?Обычные перечисления Kotlin?

Да, поэтому, когда Kotlin / Native видит MyEnum, он также генерирует MyEnumVar.

Почему char** отображается на CPointer<CPointerVar<ByteVar>> но не до CPointer<CPointer<Byte>>?

CPointer<CPointer<Byte>> недопустимо: параметр типа CPointer должен расширяться CPointed, а Byte и CPointer<T>нет.И причина, по которой им нужно расширить CPointed, заключается в том, что разыменование указателя дает lvalue: что-то с адресом!

См. https://docs.microsoft.com/en-us/cpp/c-language/l-value-and-r-value-expressions или https://eli.thegreenplace.net/2011/12/15/understanding-lvalues-and-rvalues-in-c-and-c/ для получения дополнительной информации о lvalues ​​вC (и C ++).

...