Взаимодействие с APIs C
Как часть его функциональной совместимости с Objective C, Swift поддерживает совместимость со многими типами языка C и функциями. Swift также предоставляет методам работы общие конструкции C и образцы, в случае, если Ваш код требует его.
Типы примитивов
Swift обеспечивает эквиваленты примитивных целых типов C — например, char, int, float, и double. Однако нет никакого неявного преобразования между этими типами и базовыми целыми типами Swift, такой как Int. Поэтому используйте эти типы, если Ваш код в частности требует их, но использовать Int по мере возможности иначе.
C тип |
Тип Swift |
|---|---|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
Перечисления
Swift импортирует как перечисление Swift любое перечисление C-стиля, отмеченное с NS_ENUM макрос. Это означает, что префиксы к именам перечислимой величины являются усеченными, когда они импортируются в Swift, определяются ли они в системных платформах или в пользовательском коде. Например, посмотрите это перечисление Objective C:
Objective C
typedef NS_ENUM(NSInteger, UITableViewCellStyle) {UITableViewCellStyleDefault,UITableViewCellStyleValue1,UITableViewCellStyleValue2,UITableViewCellStyleSubtitle};
В Swift это импортируется как это:
Swift
enum UITableViewCellStyle: Int {case Defaultcase Value1case Value2case Subtitle}
Когда Вы обратитесь к перечислимой величине, используйте имя значения с ведущей точкой (.).
Swift
let cellStyle: UITableViewCellStyle = .Default
Swift также импортирует опции, отмеченные с NS_OPTIONS макрос. Принимая во внимание, что опции ведут себя так же к импортированным перечислениям, опции могут также поддерживать некоторые битовые операции, такой как &, |, и ~.
В Objective C Вы представляете пустой набор опции с постоянным нулем (0). В Swift использовать nil представлять отсутствие любых опций. Например:
Swift
let myString = myData.base64EncodedStringWithOptions(nil)
Указатели
Каждый раз, когда возможно, Swift избегает предоставлять Вам прямой доступ к указателям. Существуют, однако, различные типы указателей, доступные для Вашего использования при необходимости в прямом доступе к памяти. Использование следующих таблиц Type как имя типа заполнителя для указания синтаксиса для отображений.
Для типов возврата, переменных и параметров, применяются следующие отображения:
C синтаксис |
Синтаксис Swift |
|---|---|
|
|
|
|
Для типов классов применяются следующие отображения:
C синтаксис |
Синтаксис Swift |
|---|---|
|
|
|
|
|
|
Постоянные указатели
Когда функция объявляется как берущий a UnsafePointer<Type> параметр, это может принять любое следующее:
nil, который передается как нулевой указательUnsafePointer<Type>,UnsafeMutablePointer<Type>, илиAutoreleasingUnsafeMutablePointer<Type>значение, преобразовывающееся вUnsafePointer<Type>при необходимостиВ - выражение, операнд которого является lvalue типа
Type, который передается как адрес lvalueA
[Type]значение, передающееся как указатель на запуск массива и расширяющееся до времени жизни на время вызова
Если Вы объявили функцию как этот:
Swift
func takesAPointer(x: UnsafePointer<Float>) { /*...*/ }
Можно вызвать его любым из следующих способов:
Swift
var x: Float = 0.0var p: UnsafePointer<Float> = niltakesAPointer(nil)takesAPointer(p)takesAPointer(&x)takesAPointer([1.0, 2.0, 3.0])
Когда функция объявляется как берущий a UnsafePointer<Void> параметр, это может принять те же операнды как UnsafePointer<Type> для любого типа Type.
Если Вы объявили функцию как этот:
Swift
func takesAVoidPointer(x: UnsafePointer<Void>) { /* ... */ }
Можно вызвать его любым из следующих способов:
Swift
var x: Float = 0.0, y: Int = 0var p: UnsafePointer<Float> = nil, q: UnsafePointer<Int> = niltakesAVoidPointer(nil)takesAVoidPointer(p)takesAVoidPointer(q)takesAVoidPointer(&x)takesAVoidPointer(&y)takesAVoidPointer([1.0, 2.0, 3.0] as [Float])let intArray = [1, 2, 3]takesAVoidPointer(intArray)
Непостоянные указатели
Когда функция объявляется как взятие UnsafeMutablePointer<Type> параметр, это может принять любое следующее:
nil, который передается как нулевой указательUnsafeMutablePointer<Type>значениеВ - выражение, операнд которого является сохраненным lvalue типа
Type, который передается как адрес lvalueВ -
[Type]значение, передающееся как указатель на запуск массива и расширяющееся до времени жизни на время вызова
Если Вы объявили функцию как этот:
Swift
func takesAMutablePointer(x: UnsafeMutablePointer<Float>) { /*...*/ }
Можно вызвать его любым из следующих способов:
Swift
var x: Float = 0.0var p: UnsafeMutablePointer<Float> = nilvar a: [Float] = [1.0, 2.0, 3.0]takesAMutablePointer(nil)takesAMutablePointer(p)takesAMutablePointer(&x)takesAMutablePointer(&a)
Когда функция объявляется как взятие UnsafeMutablePointer<Void> параметр, это может принять те же операнды как UnsafeMutablePointer<Type> для любого типа Type.
Если Вы объявили функцию как этот:
Swift
func takesAMutableVoidPointer(x: UnsafeMutablePointer<Void>) { /* ... */ }
Можно вызвать его любым из следующих способов:
Swift
var x: Float = 0.0, y: Int = 0var p: UnsafeMutablePointer<Float> = nil, q: UnsafeMutablePointer<Int> = nilvar a: [Float] = [1.0, 2.0, 3.0], b: [Int] = [1, 2, 3]takesAMutableVoidPointer(nil)takesAMutableVoidPointer(p)takesAMutableVoidPointer(q)takesAMutableVoidPointer(&x)takesAMutableVoidPointer(&y)takesAMutableVoidPointer(&a)takesAMutableVoidPointer(&b)
Автовыпуск указателей
Когда функция объявляется как взятие AutoreleasingUnsafeMutablePointer<Type>, это может принять любое следующее:
nil, который передается как нулевой указательAutoreleasingUnsafeMutablePointer<Type>значениеВ - выражение, операнд которого примитивно скопирован во временный буфер невладения. Адрес того буфера передается вызываемому, и по возврату, значение в буфере загружается, сохраняется и повторно присваивается в операнд.
Обратите внимание на то, что этот список не включает массивы.
Если Вы объявили функцию как этот:
Swift
func takesAnAutoreleasingPointer(x: AutoreleasingUnsafeMutablePointer<NSDate?>) { /* ... */ }
Можно вызвать его любым из следующих способов:
Swift
var x: NSDate? = nilvar p: AutoreleasingUnsafeMutablePointer<NSDate?> = niltakesAnAutoreleasingPointer(nil)takesAnAutoreleasingPointer(p)takesAnAutoreleasingPointer(&x)
Типы, на которые указывают, не соединяются мостом. Например, NSString ** приезжает в Swift как AutoreleasingUnsafeMutablePointer<NSString?>, нет AutoreleasingUnsafeMutablePointer<String?>.
Указатели функции
C указатели функции импортируются в Swift как CFunctionPointer<Type>, где Type тип функции Swift. Например, указатель функции, имеющий тип int (*)(void) в C импортируется в Swift как CFunctionPointer<() -> Int32>.
Глобальные константы
Глобальные константы, определенные в C и исходных файлах Objective C, автоматически импортируются компилятором Swift как глобальные константы Swift.
Директивы препроцессору
Компилятор Swift не включает препроцессор. Вместо этого это использует в своих интересах атрибуты времени компиляции, конфигурации сборки и функции языка для выполнения той же функциональности. Поэтому директивы препроцессору не импортируются в Swift.
Простые макросы
Где Вы обычно использовали #define директива для определения примитивной константы в C и Objective C в Swift Вы используете глобальную константу вместо этого. Например, постоянное определение #define FADE_ANIMATION_DURATION 0.35 может быть лучше выражен в Swift с let FADE_ANIMATION_DURATION = 0.35. Поскольку простые подобные константе макросы отображаются непосредственно на глобальные переменные Swift, компилятор автоматически импортирует простые макросы, определенные в исходных файлах Objective C и C.
Сложные макросы
Сложные макросы используются в C и Objective C, но не имеют никакого дубликата в Swift. Сложные макросы являются макросами, которые не определяют константы, включая заключенные в скобки, подобные функции макросы. Вы используете сложные макросы в C и Objective C, чтобы избежать проверяющих тип ограничений или избежать перепечатывать большие суммы шаблонного кода. Однако макросы могут сделать отладку и рефакторинг трудными. В Swift можно использовать функции и обобщения для достижения тех же результатов без любых компромиссов. Поэтому сложные макросы, которые находятся в C и исходных файлах Objective C, не сделаны доступными для Вашего Кода SWIFT.
Конфигурации сборки
Код SWIFT и код Objective C условно компилируются по-разному. Код SWIFT может быть условно скомпилирован на основе оценки конфигураций сборки. Конфигурации сборки включают литерал true и false значения, флаги командной строки и тестирующие платформу функции, перечисленные в таблице ниже. Можно указать, что командная строка отмечает использование -D <#flag#>.
Функция |
Допустимые параметры |
|---|---|
|
|
|
|
Простой оператор условной компиляции принимает следующую форму:
#if build configurationstatements
#elsestatements
#endif
Операторы состоят из нуля или большего количества допустимых операторов Swift, которые могут включать выражения, операторы и операторы управления. Можно добавить дополнительные требования конфигурации сборки к оператору условной компиляции с && и || операторы, инвертируйте конфигурации сборки с ! оператор, и добавляет блоки условия с #elseif:
#if build configuration && !build configurationstatements
#elseif build configurationstatements
#elsestatements
#endif
В отличие от операторов компиляции условия в препроцессоре C, операторы условной компиляции в Swift должны полностью окружить блоки кода, которые являются автономными и синтаксически допустимыми. Это вызвано тем, что весь Код SWIFT является проверенным синтаксисом, даже когда это не компилируется.
