Имеет ли Swift оператор нулевой коалесценции, а если нет, то какой пример пользовательского оператора? - программирование
Подтвердить что ты не робот

Имеет ли Swift оператор нулевой коалесценции, а если нет, то какой пример пользовательского оператора?

Общей особенностью на многих языках, Null Coalescing Operator, является двоичный оператор, часто используемый для сокращения выражений типа:

x = possiblyNullValue NCO valueIfNull

... где NCO является заполнителем для оператора нулевой коалесценции языков.

Objective C Null Coalescing Operator ?:, поэтому выражение будет:

x = possiblyNullValue ?: valueIfNull

Вышеприведенное выражение также эквивалентно использованию третичного оператора:

 x =  someTestForNotNull( possiblyNullValue ) ? possiblyNullValue : valueIfNull

Преимущества оператора Null Coalescing

  • Более читаемый код (особенно с длинными именами описательных переменных)
  • Уменьшенная возможность типографских ошибок (проверенный var вводится только один раз)
  • Нет двойной оценки тестируемой переменной, где тестируемая переменная является получателем, поскольку ее доступ один раз (или необходимость кэшировать ее, чтобы умышленно избегать двойной оценки).
4b9b3361

Ответ 1

С Swift 2.2 (Xcode 6, beta 5) it ??

var x: Int?
var y: Int? = 8

var z: Int = x ?? 9000
// z == 9000

z = y ?? 9001
// z == 8

a ?? b эквивалентен следующему коду:

a != nil ? a! : b

И с Beta 6 вы можете сделать это:

x ?? y ?? 1 == 8

Ответ 2

(Также см. сообщение в блоге)

Нет, Swift в настоящее время не поддерживает нулевой оператор коалесценции.

Определение пользовательского оператора Null Coales для Swift

Пользовательский оператор может быть определен для Swift со следующими соображениями относительно языка Swift:

Swift и Nil

Swift поддерживает нулевую концепцию через свой Необязательный тип (Дискриминационный Союз сортов), который либо содержит значение базового типа, либо не имеет значения (указано nil) и должен быть явно определен как необязательный:

var a : String?

Необязательный тип никогда не может быть nil или назначен nil. Поэтому можно ожидать, что пользовательский двоичный NCO-инфикс примет необязательный параметр в качестве своего первого параметра.

Доступные символы для пользовательских операторов в Swift

В Swift пользовательские операторы могут состоять только из следующих символов:

/ = - + * % < > ! & | ^ . ~

Оператор

Учитывая выбор доступных символов, ||| (три трубы, без интервала) не страшны (аналогично двойной трубе ИЛИ в Javascript, которая используется как NCO):

Использование оператора

var a = String?
var z = a ||| "it nil!"
println(z) //Output: it nil!

Определение оператора

operator infix ||| {}

@infix func |||<T> (left: T?, right: T) -> T  {
  if let l = left { return l }
  return right
}

Ответ 3

То, что говорит Венкат, является правильным: нет, но вы можете его определить. Однако его реализация не идеальна, потому что он забыл использовать @auto_closure.

Также я считаю, что вы можете перегрузить || без необходимости определять новый оператор.

У меня нет компилятора здесь, но я постараюсь дать вам код из памяти:

func |||<T> (maybe: Optional<T>, defaultValue: @auto_closure () -> T) -> T {
    if let some = maybe { 
      return some 
    }
    return defaultValue()
}

Edit: Спасибо Martin R за тестирование этого с помощью компилятора. См. Комментарии. Очевидно, что перегрузка || возможна, но может работать не так, как ожидалось, из-за того, что Swift обрабатывает разрешение перегруженных операторов (что недокументировано, и поэтому я понятия не имею, можно ли его обойти или нет). Я изменил функцию выше, чтобы использовать |||.

Ответ 4

Я написал о пользовательской функции оператора, которая обеспечивает nil-coalescing здесь: http://ijoshsmith.com/2014/07/24/nil-coalescing-operator-in-swift/

Мой выбор оператора был !!, который объединяет логический не оператор (!) и оператор разворота (!) для семантики "если не могу развернуть". Кажется, я опоздал на вечеринку, учитывая, что эта тема уже старше месяца. В любом случае, здесь моя реализация в случае, если вам интересно...

operator infix !! {}

@infix func !! <T> (
    value: T?,
    defaultValue: @auto_closure () -> T)
    -> T
{
    return value ? value! : defaultValue()
}

Ответ 5

надеюсь, что это поможет вам

  • да, теперь он добавлен в быстрый

  • немного Объяснение

           var anumber:Int? = someValue
           var banumber = 2
           anumber =   ( anumber != nil) ? anumber : banumber ------- (a)
           println(anumber!)
    

теперь вместо того, чтобы писать все (а), мы можем просто использовать это →

        anumber = anumber ?? banumber

и

Оператор также может использоваться несколько раз в одном выражении. как

     firstNumber ?? secondNumber ?? thirdNumber. 

Ответ 6

Вы можете проверить код детской площадки ниже.

import UIKit
var personalSite : String?
let defaultSite = "http://www.google.com"

var website = personalSite ?? defaultSite