Твърде много опции правят кода объркан в Swift

Анализирам малко JSON и това е първият път, когато го правя на Swift. Напоследък избягвам използването на принудителни понижавания, тъй като това е лоша практика.

За съжаление, недостатъкът на това е, че кодът ми стана много по-объркан, особено в този конкретен случай на опит за анализиране на JSON.

Това е моят код:

if let dic = try NSJSONSerialization.JSONObjectWithData(currentData!, options: NSJSONReadingOptions.AllowFragments) as? [String: AnyObject] {
    student["roll"] = dic["roll"] as? Int
    student["firstName"] = dic["name"]?.componentsSeparatedByString(" ").first
    student["lastName"] = dic["name"]?.componentsSeparatedByString(" ").last

    var subjects = [[String: AnyObject?]]()

    if let dicSubs = dic["subs"] as? [AnyObject] {
        for dicSub in dicSubs {
            var sub = [String: AnyObject?]()

            sub["name"] = dicSub["name"] as? String

            if let code = dicSub["code"] as? String {
                sub["code"] = Int(code)
            }
            if let theory = dicSub["theory"] as? String {
                sub["theory"] = Int(theory)
            }
            if let prac = dicSub["prac"] as? String {
                sub["prac"] = Int(prac)
            }

            subjects.append(sub)
        }
    }

    student["subjects"] = subjects
}

По този начин произведеният изход е пълен с опции, което го прави почти неизползваем. Имам чувството, че правя нещо нередно, тъй като версията на Objective C на този код е много по-чиста и по-кратка.

Има ли някакъв начин да подобря това?

Ако е необходимо, ето получения резултат:

[  
  roll:Optional(1234567),
  firstName:Optional("FIRSTNAME"),
  lastName:Optional("LASTNAME"),
  subjects:Optional(  [  
    [  
      "code":Optional(123),
      "theory":Optional(73),
      "name":Optional(REDACTED)
    ],
    [  
      "code":Optional(123),
      "theory":Optional(76),
      "name":Optional(REDACTED)
    ],
    [  
      "code":Optional(123),
      "theory":Optional(48),
      "name":Optional(REDACTED)
    ],
    [  
      "code":Optional(123),
      "theory":Optional(75),
      "prac":Optional(19),
      "name":Optional(REDACTED)
    ],
    [  
      "code":Optional(123),
      "theory":Optional(69),
      "prac":Optional(18),
      "name":Optional(REDACTED)
    ],
    [  
      "code":Optional(123),
      "theory":Optional(63),
      "prac":Optional(28),
      "name":Optional(REDACTED)
    ]
  ]  )
])

person duci9y    schedule 17.07.2015    source източник
comment
Бихте ли добавили разширение към речниците на Swift, което превръща възможен низ в незадължителен Int?   -  person gnasher729    schedule 17.07.2015
comment
@gnasher729 Да, хрумна ми, но това ми се струва хакерско решение, така че се чудех дали хората ще имат по-добри предложения.   -  person duci9y    schedule 17.07.2015


Отговори (2)


Разопаковайте опциите (вече го правите за някои от тях, направете го за всички):

if let roll = dic["roll"] as? Int {
    student["roll"] = roll
}

Също така, инициализаторът Int(...) връща опция, така че трябва да го разопаковате също с незадължително обвързване:

if let code = dicSub["code"] as? String, let myInt = Int(code) {
    sub["code"] = myInt
}
person Eric Aya    schedule 17.07.2015
comment
Това ли е най-добрият начин? Това би добавило 3 реда код за всеки ключ, който анализирам, и се чудех дали може да бъде по-кратък. - person duci9y; 17.07.2015
comment
Да, това е начинът да го направите на ръка. Ако го намирате за тромаво, можете да използвате библиотека като SwiftyJSON, която ще разопакова всичко вместо вас автоматично, но ще добави шаблон и режийни на други места, така че... ваш избор. :) И двата начина са ок. Лично аз предпочитам на ръка, когато JSON не е твърде сложен, по този начин знам точно какво се случва. - person Eric Aya; 17.07.2015
comment
Благодаря! Харесва ми разсъждението ти за това, че знаеш какво се случва. Предполагам, че ще отида по този начин, но ще опитам SwiftyJSON. - person duci9y; 17.07.2015
comment
Моля. :) Наистина декодирането на JSON на ръка в Swift понякога може да бъде многословно, но намирам, че всъщност не е проблем: с времето ще добавите свои собствени разширения и методи, за да избегнете въвеждането на едни и същи неща отново и отново. - person Eric Aya; 17.07.2015

В зависимост от скоростите, от които се нуждаете, бих ви предложил да използвате библиотека на трета страна за JSON комуникация. Добър пример е:

SwiftyJSON

Можете да разгледате урок за това тук:

http://www.raywenderlich.com/82706/working-with-json-in-swift-tutorial

person hris.to    schedule 17.07.2015
comment
SwiftyJSON ще ви спести безброй часове. Това прави анализирането на JSON толкова лесно, колкото сравняването на две числа. - person lagoon; 17.07.2015