Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Think Sharp, Write Swift

Think Sharp, Write Swift

A talk about Swift for C# developers

Pascal Batty

May 12, 2016
Tweet

Other Decks in Technology

Transcript

  1. C# Swift Object Oriented ✓ ✓ Type Inference ✓ ✓

    Generics ✓ ✓ Tuples ✓ ✓ Lambdas ✓ ✓ Optional Chaining ✓ ✓ String Interpolation ✓ ✓ SWIFT VS C# FEATURE COMPARISON CHART
  2. String Interpolation ✓ ✓ Operator overloading ✓ ✓ Null Coalescing

    ✓ ✓ Variadic Parameters ✓ ✓ Optional Parameters ✓ ✓ Extensions ✓ ✓ Auto-Properties ✓ ✓ Try/Catch ✓ ✓ Cool Logo ✓
  3. THE GOOD OLD FIBONACCI SEQUENCE LET’S COMPARE CODE func fib(n:

    Int) -> Int { var fib0 = 0, fib1 = 1 for var i = 2; i <= n; i++ { var tmp = fib0 fib0 = fib1 fib1 = tmp + fib1 } return n > 0 ? fib1 : 0 } static int fib(int n) { int fib0 = 0, fib1 = 1; for (int i = 2; i <= n; i++) { int tmp = fib0; fib0 = fib1; fib1 = tmp + fib1; } return (n > 0 ? fib1 : 0); } C# Swift as found on Wikibooks
  4. C# Swift Garbage Collection Reference Counting Interface Protocol Constructor Initializer

    const let Linq MapReduce Lambda Closure func<> -> SWIFT AND C# ARE KINDA SORTA SIMILAR
  5. THE GOOD OLD FIBONACCI SEQUENCE A FEW ADJUSTMENTS func fib(n:

    Int) -> Int { var fib0 = 0, fib1 = 1 for var i = 2; i <= n; i++ { var tmp = fib0 fib0 = fib1 fib1 = tmp + fib1 } return n > 0 ? fib1 : 0 } Variable was never mutated; consider changing to ‘let’ constant
  6. THE GOOD OLD FIBONACCI SEQUENCE A FEW ADJUSTMENTS func fib(n:

    Int) -> Int { var fib0 = 0, fib1 = 1 for var i = 2; i <= n; i++ { let tmp = fib0 fib0 = fib1 fib1 = tmp + fib1 } return n > 0 ? fib1 : 0 } ++ is deprecated: it will be removed in Swift 3
  7. THE GOOD OLD FIBONACCI SEQUENCE A FEW ADJUSTMENTS func fib(n:

    Int) -> Int { var fib0 = 0, fib1 = 1 for var i = 2; i <= n; i += 1 { let tmp = fib0 fib0 = fib1 fib1 = tmp + fib1 } return n > 0 ? fib1 : 0 } C-Style for statement is deprecated and will be removed…
  8. THE GOOD OLD FIBONACCI SEQUENCE A FEW ADJUSTMENTS func fib(n:

    Int) -> Int { var fib0 = 0, fib1 = 1 for i in 2...n { let tmp = fib0 fib0 = fib1 fib1 = tmp + fib1 } return n > 0 ? fib1 : 0 } Immutable value ‘i’ was never used; consider replacing with ‘_’
  9. THE GOOD OLD FIBONACCI SEQUENCE A FEW ADJUSTMENTS func fib(n:

    Int) -> Int { var fib0 = 0, fib1 = 1 for _ in 2...n { let tmp = fib0 fib0 = fib1 fib1 = tmp + fib1 } return n > 0 ? fib1 : 0 }
  10. LET US DIVE IN A LITTLE DEEPER BUILDING BLOCKS Class

    Properties Initializers Instance Methods Class Methods Struct Properties Initializers Instance methods Static methods Enum Properties Initializers Instance methods Static methods
  11. I CAN’T ASK YOU TO JUST BELIEVE ME ON THIS

    VALUE TYPES ARE AWESOME ▸ Immutability ensured by ‘let’ ▸ No expensive boxing/unboxing ▸ Code is more thread-safe ▸ Performance is better ▸ Functional Programming is more convenient
  12. LET US DIVE IN A LITTLE DEEPER STANDARD TYPES ▸

    Int, Float, Double ▸ Bool ▸ String, Character ▸ Array<T>, Dictionary<K: Hashable, V>, Set<T: Hashable> THESE ARE ALL STRUCTS!
  13. BRACE YOURSELVES… ENUMERABLES AS YOU MAY KNOW THEM enum Land

    { case Forest case Mountain case Swamp case Plains case Island } enum Error : Int { case NotFound = 404 case ServerError = 500 case Forbidden = 403 case Teapot = 418 } Raw value can be String, Character or any numeric type
  14. HERE COMES! ENUMERABLES WITH ASSOCIATED VALUES! enum PaymentMethod { case

    Cash case Check (Int) case CreditCard (CardType, Int) enum CardType { case Visa, MasterCard, Electron } func display() { switch self { case Cash: print("Paid by cash") case let Check(number): print("Paid by check #\(number)") case let CreditCard(type, number): print("Paid by \(type) #\(number)") } } } let method = PaymentMethod.CreditCard(.Visa, 995423) method.display()
  15. NOT OVER YET! … AND GENERICS! enum Result<T, U> {

    case Success(T) case Error(U) } enum Optional<T> { case Some(T) case None } indirect enum Tree<T> { case Empty case Node(T, left: Tree<T>, right: Tree<T>) }
  16. WHAT YOU MAY END UP DOING… OPTIONALS IN THE WILD

    let answer: String = "42" let numericAnswer = Int(answer) let byOneThousand = numericAnswer * 1000 let nineThousand: Float = 9 * 1000 let vegetaSays: String = "It's over \(nineThousand) !!" let nappaSays: String = "What!? " + String(nineThousand) + "?!" VALUE OF OPTIONAL TYPE ‘INT?’ NOT UNWRAPPED; DID YOU MEAN TO USE ‘!’ OR ‘?’ ? Int?
  17. BEAR WITH ME THERE OPTIONALS ▸ Like nullables for all

    types! ▸ Variables, constants, arguments, properties or return values ▸ You can’t use its value unless you unwrap it first ▸ If it is not Optional, it can never be nil
  18. DO YOU KNOW THE ‘MAYBE’ MONAD ? UNWRAPPING THE OPTIONAL

    42 let answer: String = getAnswer() let numericAnswer: Int? = Int(answer) processNumericAnswer(numericAnswer) ??? Int? Int nil
  19. DO YOU KNOW THE ‘MAYBE’ MONAD ? UNWRAPPING THE OPTIONAL

    42 let answer: String = getAnswer() let numericAnswer: Int? = Int(answer) if let realAnswer: Int = numericAnswer { processNumericAnswer(realAnswer) } else { print("Please give a number") } nil Int? Int?
  20. NOT EVERYTHING IS COMPULSORY OPTIONAL PROPERTIES struct Contact { var

    firstName:String var middleName:String? var lastName:String var emailAddress:String var emailVerified:Bool }
  21. THAT’S A LOT OF PUNCTUATION! NULL COALESCING AND OPTIONAL CHAINING

    let answer: String = getAnswer() let numericAnswer: Int? = Int(answer) let sanitizedAnswer: Int = numericAnswer ?? 1 processNumericAnswer(sanitizedAnswer) let contact: Contact? = getContact() let email: String? = contact?.emailAddress ?? ?.
  22. FAMOUS LAST WORDS… FORCE UNWRAP & IMPLICITLY UNWRAPPED OPTIONALS !

    « I KNOW WHAT I’M DOING. IF YOU ENCOUNTER AN UNEXPECTED NIL JUST CRASH AT RUNTIME »
  23. PUT SOME LOGIC INSIDE YOUR TYPES! FUN WITH PROPERTIES struct

    Contact { var firstName: String var middleName: String? var lastName: String let securityNumber: Int var fullName: String { if let initial = middleName?.characters.first { return "\(firstName) \(initial). \(lastName)" } else { return "\(firstName) \(lastName)" } } var emailVerified: Bool var emailAddress: String { didSet { emailVerified = false } } }
  24. MAP, FILTER, REDUCE, SORT CLOSURES let people:[Contact] = getContacts() let

    targetNames:[String] = people .filter({ contact in contact.lastName.hasPrefix("G") }) .map({ contact in contact.fullName }) .sort() func multipleOf(factor: Int) -> Int -> Bool { return { (number: Int) in number % factor == 0 } } let isEven = multipleOf(2) isEven(4) // Get the sum of multiples of 3 up to 100 (1...100) .filter(multipleOf(3)) .reduce(0, combine: +) https://github.com/mythz/swift-linq-examples
  25. IMAGINE THE POSSIBILITIES… EXTENSIONS & PROTOCOLS extension Contact { func

    composeEmailBoilerplate() -> String { … } var abbreviatedName: String { … } } protocol StringSerializable { func serialize() -> String } extension StringSerializable { func serialize() -> String { return "" } } extension Contact: StringSerializable { func serialize() -> String { … } }
  26. YOU’VE GOT TO START SOMEWHERE YOUR LEARNING ENVIRONMENT OS X

    Ubuntu Windows Xcode
 Playground REPL Ubuntu
 Bash
  27. BECAUSE WE DON’T HAVE THE TIME TO SEE EVERYTHING LEARN

    ▸ Updated eBook from Apple ▸ Available for free ▸ on iBooks ▸ on swift.org ▸ swiftdoc.org is a nice and fast documentation website
  28. A CONVENTION-CREATING KEYWORD GUARD func multipleOf(factor: Int) -> Int ->

    Bool { return { (number: Int) in number % factor == 0 } }
  29. A CONVENTION-CREATING KEYWORD GUARD func multipleOf(factor: Int) -> Int ->

    Bool { guard factor != 0 else { return { _ in false } } return { (number: Int) in number % factor == 0 } }