2015-01-04 6 views
0

у меня есть это:нильполугруппы коалесцирование: Использование дополнительных типов в качестве значения по умолчанию в Swift

let queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0) 

     dispatch_async(queue, { 
      if let data = NSURLConnection.sendSynchronousRequest(self.buildRequestForVenueLocation(location, identifier), returningResponse: &response, error: &error) { 
       let responseDictionary: AnyObject? = NSJSONSerialization.JSONObjectWithData(data, options: .allZeros, error:&error) ?? error?.localizedDescription 
       dispatch_async(dispatch_get_main_queue(), { 
        completion(venues: responseDictionary, error: error) 
       }) 
      } else { 
       println("There was a problem with the request...") 
      } 
     }) 

Мой вопрос относительно этой линии, в частности:

let responseDictionary: AnyObject? = NSJSONSerialization.JSONObjectWithData(data, options: .allZeros, error:&error) ?? error?.localizedDescription 

Является ли это правильное использование nil coalescing?

Согласно документации Apple, это равносильна:

a != nil ? a! : b 

Если будет ноль, а возвращается, но это дело, если б это необязательный тип?

EDIT

В случае, если кто задавался вопросом, вот на что это похоже, когда я вызываю функцию:

v.performVenueLocationRequest(l.location, identifier: "4d4b7105d754a06374d81259") { 
     if let result = $0 as? [String: AnyObject] ?? $1 { 
      println(result) 
     } 
    } 

ответ

1

Это зависит от того, что вы имеете в виду «материи». Это будет работать. Это просто не может быть, что вы хотите - если b не является обязательным, то результат будет также опциональный то есть даже если a имеет значение все равно не будет: без упаковки

let a: Int? = 2 
let b: Int? = 3 
let c = i ?? j 
// c is {Some 2} 

против:

let i: Int? = nil 
let j: Int? = 3 
let k = i ?? j 
// k is {Some 3} 

См. this article, возможно, больше, чем вы хотите узнать о причинах, но, в общем, результат должен быть зафиксирован как определенный тип во время компиляции независимо от того, что значения a и b находятся во время выполнения. Поскольку b является необязательным, a! неявно завернута в опцию, чтобы сделать эти два типа совместимыми. Положите это так - если результат не был необязательным, и b были nil, каков был бы результат?

Имейте в виду, что вы можете связать ??, чтобы вы могли поместить третье значение на конец, которое не является необязательным, что сделает результат не факультативным.

+0

Понравилось, спасибо! В моем случае, хотя - словарь, который передается в закрытие, в любом случае принимает два необязательных аргумента, затем я разворачиваю в вызове фактической функции –

0

Это нулевой коалесцирующий.

Если b не является факультативным:
a ?? b вернет развернутый a, если a не равен нулю. Если a равно нулю, оно вернет b.

Если b не является необязательным:
a ?? b вернет a, если a не является нулем. Если a равно нулю, оно вернет b.

Этот код будет работать. Но поскольку вы все равно произвольно регистрируете ошибку, я бы рекомендовал оставить responseDictionary как nil вместо присвоения ему error.localDescription (если он не сработает). Это просто лучший дизайн. Как показано ниже.

let responseDictionary: AnyObject? = NSJSONSerialization.JSONObjectWithData(data, options: .allZeros, error:&error) 
+1

«Это объединение нуля. A? B вернет разворачивание a, если a не равно нулю. Если a равно нулю, он вернет b. «Нет, если' b' является необязательным, это не будет ... –

+0

спасибо.Я не знал, что произойдет, если b не является обязательным. но имеет смысл. – rakeshbs