├── .gitattributes ├── DesignPatterns ├── Week 5 - Design Patterns.playground │ ├── Contents.swift │ ├── contents.xcplayground │ └── Pages │ │ ├── Day 3 - Factory Method Pattern.xcplaygroundpage │ │ └── Contents.swift │ │ ├── Day 2 - Observer Pattern.xcplaygroundpage │ │ └── Contents.swift │ │ ├── Day 1 - Stategy Pattern.xcplaygroundpage │ │ └── Contents.swift │ │ └── Day 4 - Abstract Factory Pattern.xcplaygroundpage │ │ └── Contents.swift ├── StrategyPattern.playground │ ├── contents.xcplayground │ └── Contents.swift ├── DecoratorPattern.playground │ ├── contents.xcplayground │ └── Contents.swift └── Week 6 - Design Patterns.playground │ ├── contents.xcplayground │ └── Pages │ ├── Day 2 - Facade Pattern.xcplaygroundpage │ └── Contents.swift │ ├── Day 1- Decorator Pattern.xcplaygroundpage │ └── Contents.swift │ └── Day 2 - Proxy Pattern.xcplaygroundpage │ └── Contents.swift ├── DataStructures ├── Tries │ ├── Tries │ │ ├── Assets.xcassets │ │ │ ├── Contents.json │ │ │ └── AppIcon.appiconset │ │ │ │ └── Contents.json │ │ ├── Info.plist │ │ ├── Base.lproj │ │ │ ├── LaunchScreen.storyboard │ │ │ └── Main.storyboard │ │ ├── AppDelegate.swift │ │ └── ViewController.swift │ └── Tries.xcodeproj │ │ ├── project.xcworkspace │ │ ├── contents.xcworkspacedata │ │ └── xcshareddata │ │ │ └── IDEWorkspaceChecks.plist │ │ └── project.pbxproj ├── Week 2 - Data Structures.playground │ ├── Pages │ │ ├── Day 4 - Trees, Binary Trees.xcplaygroundpage │ │ │ ├── Sources │ │ │ │ ├── New File.swift │ │ │ │ └── Queue.swift │ │ │ └── Contents.swift │ │ ├── Day 3 - Dictionaries, HashMap.xcplaygroundpage │ │ │ └── Contents.swift │ │ ├── Day 2 - Queue, Priority Queue, Stack.xcplaygroundpage │ │ │ └── Contents.swift │ │ └── Day 1 - Arrays and Linked Lists.xcplaygroundpage │ │ │ └── Contents.swift │ └── contents.xcplayground ├── Week 2 - Data Structures.playground.zip ├── Week 3 - Data Structures.playground.zip ├── Week 3 - Data Structures.playground │ ├── contents.xcplayground │ └── Pages │ │ ├── Day 3 - Set, Set Theory.xcplaygroundpage │ │ └── Contents.swift │ │ ├── Advanced Binary Search Tree.xcplaygroundpage │ │ ├── Sources │ │ │ └── BinaryNode.swift │ │ └── Contents.swift │ │ ├── Recursive Enum Binary Search Trees.xcplaygroundpage │ │ └── Contents.swift │ │ ├── Day 4 - Graphs.xcplaygroundpage │ │ └── Contents.swift │ │ ├── Day 1 - Basic Binary Search Tree (Teach this One).xcplaygroundpage │ │ └── Contents.swift │ │ └── Day 2 - Heap, Trie.xcplaygroundpage │ │ └── Contents.swift └── DataStructures.playground │ ├── contents.xcplayground │ └── Pages │ ├── GeneralPurposeTree.xcplaygroundpage │ ├── Sources │ │ └── QueueHelper.swift │ └── Contents.swift │ ├── Queue.xcplaygroundpage │ └── Contents.swift │ ├── Stack.xcplaygroundpage │ └── Contents.swift │ ├── BinarySearchTree.xcplaygroundpage │ ├── Sources │ │ └── BinaryNode.swift │ └── Contents.swift │ ├── BasicBinarySearchTree (Teach this in Class).xcplaygroundpage │ └── Contents.swift │ ├── Heaps.xcplaygroundpage │ └── Contents.swift │ └── LinkedList.xcplaygroundpage │ └── Contents.swift ├── Keynotes ├── Queue.pdf ├── Stacks.pdf ├── BigO Day 1.pdf ├── LinkedLists.pdf ├── BinarySearchTree.pdf ├── DecoratorPattern.pdf ├── Factory Pattern.pdf ├── ObserverPattern.pdf ├── Proxy Pattern.pdf ├── StrategyPattern.pdf ├── DataStructureOverview.pdf └── Abstract Factory Pattern.pdf ├── BigO └── Week 1 - Big O.playground │ ├── contents.xcplayground │ └── Pages │ ├── Day 3 - Practice & Ordering Big O.xcplaygroundpage │ └── Contents.swift │ ├── Day 4 - Time vs. Space.xcplaygroundpage │ └── Contents.swift │ ├── Day 2 - O(log n), O(2^n).xcplaygroundpage │ └── Contents.swift │ └── Day 1 - O(1), O(n), O(n^2).xcplaygroundpage │ └── Contents.swift ├── InterviewQuestions └── Week 4 - Technical Interviews.playground │ ├── contents.xcplayground │ └── Pages │ ├── Day 1 - Interview Questions 1.xcplaygroundpage │ └── Contents.swift │ ├── Day 2 - Interview Questions 2.xcplaygroundpage │ └── Contents.swift │ ├── Day 3 - Interview Questions 3.xcplaygroundpage │ └── Contents.swift │ └── Day 4 - Interview Questions 4.xcplaygroundpage │ └── Contents.swift ├── .gitignore └── README.md /.gitattributes: -------------------------------------------------------------------------------- 1 | *.pdf filter=lfs diff=lfs merge=lfs -text 2 | -------------------------------------------------------------------------------- /DesignPatterns/Week 5 - Design Patterns.playground/Contents.swift: -------------------------------------------------------------------------------- 1 | import UIKit 2 | 3 | var str = "Hello, playground" 4 | -------------------------------------------------------------------------------- /DataStructures/Tries/Tries/Assets.xcassets/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "info" : { 3 | "version" : 1, 4 | "author" : "xcode" 5 | } 6 | } -------------------------------------------------------------------------------- /DataStructures/Week 2 - Data Structures.playground/Pages/Day 4 - Trees, Binary Trees.xcplaygroundpage/Sources/New File.swift: -------------------------------------------------------------------------------- 1 | import Foundation 2 | 3 | -------------------------------------------------------------------------------- /Keynotes/Queue.pdf: -------------------------------------------------------------------------------- 1 | version https://git-lfs.github.com/spec/v1 2 | oid sha256:27ac2f5fcf43e16866cd79eb1a2bce810900339f74731f30e15740fbbf818dfb 3 | size 48575 4 | -------------------------------------------------------------------------------- /Keynotes/Stacks.pdf: -------------------------------------------------------------------------------- 1 | version https://git-lfs.github.com/spec/v1 2 | oid sha256:96413d2f6a62dafad7012cbd15702a6f290fa422b8a14dea75f595c5d60a66fc 3 | size 143667 4 | -------------------------------------------------------------------------------- /Keynotes/BigO Day 1.pdf: -------------------------------------------------------------------------------- 1 | version https://git-lfs.github.com/spec/v1 2 | oid sha256:cd9604f6f951e4f6ebc96cb7962b3941c1fced8779ea9cc32d1934654544a22b 3 | size 550252 4 | -------------------------------------------------------------------------------- /Keynotes/LinkedLists.pdf: -------------------------------------------------------------------------------- 1 | version https://git-lfs.github.com/spec/v1 2 | oid sha256:6e3e2565d7aac7cf61f93bb162bfcdf1146f8d4cbecf2bad733d0da46630a146 3 | size 294549 4 | -------------------------------------------------------------------------------- /Keynotes/BinarySearchTree.pdf: -------------------------------------------------------------------------------- 1 | version https://git-lfs.github.com/spec/v1 2 | oid sha256:5d9dd6a1883a306cf1c6b3db7bd4b8457fcfa74c0f26f49f8092f3b5bf385e99 3 | size 80118 4 | -------------------------------------------------------------------------------- /Keynotes/DecoratorPattern.pdf: -------------------------------------------------------------------------------- 1 | version https://git-lfs.github.com/spec/v1 2 | oid sha256:552b1f651bd51422c63b1f5524bc0940a20951e3e457c4b56222baa29ed1b56f 3 | size 109845 4 | -------------------------------------------------------------------------------- /Keynotes/Factory Pattern.pdf: -------------------------------------------------------------------------------- 1 | version https://git-lfs.github.com/spec/v1 2 | oid sha256:103903eba914c7d273f476c92e149a2a53d29eaa5d66ad44f373aa17780a25ef 3 | size 42247 4 | -------------------------------------------------------------------------------- /Keynotes/ObserverPattern.pdf: -------------------------------------------------------------------------------- 1 | version https://git-lfs.github.com/spec/v1 2 | oid sha256:79f7d33af0fdd0fe2225a7d29266daa825dce9c3412240f2a3098c3b9d5a4647 3 | size 117528 4 | -------------------------------------------------------------------------------- /Keynotes/Proxy Pattern.pdf: -------------------------------------------------------------------------------- 1 | version https://git-lfs.github.com/spec/v1 2 | oid sha256:a665a3324d4e2dbc8498d5e0442c9ada6cb767f2391a30f7483ab07ebd6a3872 3 | size 125316 4 | -------------------------------------------------------------------------------- /Keynotes/StrategyPattern.pdf: -------------------------------------------------------------------------------- 1 | version https://git-lfs.github.com/spec/v1 2 | oid sha256:2ed1f7ba84d1cbe5bc875feddb4a9a1b3db7f8c289176a9511a636934481f766 3 | size 167727 4 | -------------------------------------------------------------------------------- /Keynotes/DataStructureOverview.pdf: -------------------------------------------------------------------------------- 1 | version https://git-lfs.github.com/spec/v1 2 | oid sha256:3117afcbbec196e7245cbdd3b9d8ef5a87ef653bd9a14ce655a1b5671b597537 3 | size 181013 4 | -------------------------------------------------------------------------------- /DataStructures/Week 2 - Data Structures.playground.zip: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/DevMountain/ComputerScienceCrashCourse/HEAD/DataStructures/Week 2 - Data Structures.playground.zip -------------------------------------------------------------------------------- /DataStructures/Week 3 - Data Structures.playground.zip: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/DevMountain/ComputerScienceCrashCourse/HEAD/DataStructures/Week 3 - Data Structures.playground.zip -------------------------------------------------------------------------------- /Keynotes/Abstract Factory Pattern.pdf: -------------------------------------------------------------------------------- 1 | version https://git-lfs.github.com/spec/v1 2 | oid sha256:66cc0eff20e07d2c3759127812a468335d166e47bc23e4af129cfc85a482c9c6 3 | size 55458 4 | -------------------------------------------------------------------------------- /DataStructures/Tries/Tries.xcodeproj/project.xcworkspace/contents.xcworkspacedata: -------------------------------------------------------------------------------- 1 | 2 | 4 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /DesignPatterns/StrategyPattern.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /DesignPatterns/DecoratorPattern.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /DataStructures/Tries/Tries.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | IDEDidComputeMac32BitWarning 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /DesignPatterns/Week 6 - Design Patterns.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | -------------------------------------------------------------------------------- /BigO/Week 1 - Big O.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /DataStructures/Week 3 - Data Structures.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /DesignPatterns/Week 5 - Design Patterns.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /DataStructures/Week 2 - Data Structures.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /InterviewQuestions/Week 4 - Technical Interviews.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /DataStructures/DataStructures.playground/contents.xcplayground: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | -------------------------------------------------------------------------------- /DataStructures/Week 2 - Data Structures.playground/Pages/Day 4 - Trees, Binary Trees.xcplaygroundpage/Sources/Queue.swift: -------------------------------------------------------------------------------- 1 | import Foundation 2 | 3 | //(This Queue is used in the implementation of a Tree) 4 | //public struct Queue { 5 | // 6 | // fileprivate var array = [T]() 7 | // 8 | // public var isEmpty: Bool { 9 | // return array.isEmpty 10 | // } 11 | // 12 | // public mutating func enqueue(_ element: T) { 13 | // array.append(element) 14 | // } 15 | // 16 | // public mutating func dequeue() -> T? { 17 | // if isEmpty { 18 | // return nil 19 | // } else { 20 | // return array.removeFirst() 21 | // } 22 | // } 23 | // 24 | // public mutating func peek() -> T? { 25 | // return array.first 26 | // } 27 | //} 28 | -------------------------------------------------------------------------------- /DataStructures/DataStructures.playground/Pages/GeneralPurposeTree.xcplaygroundpage/Sources/QueueHelper.swift: -------------------------------------------------------------------------------- 1 | import Foundation 2 | 3 | public struct Queue { 4 | 5 | private var leftStack: [T] = [] 6 | private var rightStack: [T] = [] 7 | 8 | public init() {} 9 | 10 | public var isEmpty: Bool { 11 | return leftStack.isEmpty && rightStack.isEmpty 12 | } 13 | 14 | public var peek: T? { 15 | return !leftStack.isEmpty ? leftStack.last : rightStack.first 16 | } 17 | 18 | @discardableResult public mutating func enqueue(_ element: T) -> Bool { 19 | rightStack.append(element) 20 | return true 21 | } 22 | 23 | public mutating func dequeue() -> T? { 24 | if leftStack.isEmpty { 25 | leftStack = rightStack.reversed() 26 | rightStack.removeAll() 27 | } 28 | return leftStack.popLast() 29 | } 30 | } 31 | -------------------------------------------------------------------------------- /DesignPatterns/StrategyPattern.playground/Contents.swift: -------------------------------------------------------------------------------- 1 | import UIKit 2 | 3 | // Superclass 4 | class Pokemon { 5 | 6 | func attack() { 7 | print("Attacking!") 8 | } 9 | 10 | let flyable: Flyable 11 | 12 | var tryToFly: String { 13 | return flyable.fly() 14 | } 15 | 16 | init(fly: Flyable) { 17 | self.flyable = fly 18 | } 19 | } 20 | 21 | // Subclasses 22 | class Butterfry: Pokemon {} 23 | class Pikachu: Pokemon {} 24 | class HoOh: Pokemon {} 25 | 26 | protocol Flyable { // Interface / Protocol 27 | func fly() -> String 28 | } 29 | 30 | class CanNormalFly: Flyable { 31 | func fly() -> String { 32 | return "Is normal flying" 33 | } 34 | } 35 | 36 | class CanLegendaryFly: Flyable { 37 | func fly() -> String { 38 | return "Is flying very fast" 39 | } 40 | } 41 | 42 | class CantFly: Flyable { 43 | func fly() -> String{ 44 | return "Can't fly" 45 | } 46 | } 47 | 48 | let pikachu = Butterfry(fly: CanNormalFly()) 49 | let buttery = Pikachu(fly: CanNormalFly()) 50 | let hooh = Pikachu(fly: CanLegendaryFly()) 51 | 52 | pikachu.tryToFly 53 | buttery.tryToFly 54 | hooh.tryToFly 55 | 56 | -------------------------------------------------------------------------------- /BigO/Week 1 - Big O.playground/Pages/Day 3 - Practice & Ordering Big O.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Big O Day 3 - Practice & Ordering Big O 2 | import Foundation 3 | 4 | // Here are some previous stretch problems and their solutions. We're going to analyze their Big O. 5 | func isPalindrome(_ input: String) -> Bool { 6 | let simpleInput = input.lowercased().components(separatedBy: .whitespacesAndNewlines).joined() 7 | return String(simpleInput.reversed()) == simpleInput 8 | } 9 | 10 | 11 | 12 | 13 | func gcd(_ a: Int, _ b: Int) -> Int { 14 | if b == 0 { 15 | return a 16 | } else { 17 | if a > b { 18 | return gcd(a-b, b) 19 | } else { 20 | return gcd(a, b-a) 21 | } 22 | } 23 | } 24 | 25 | 26 | 27 | 28 | func gcdEuclid(_ a: Int, _ b: Int) -> Int { 29 | let remainder = a % b 30 | print("a: \(a)") 31 | print("b: \(b)") 32 | print("remainder: \(remainder)") 33 | if remainder == 0 { 34 | return b 35 | } else { 36 | return gcdEuclid(b, remainder) 37 | } 38 | } 39 | 40 | gcdEuclid(50, 17) 41 | 42 | 43 | 44 | 45 | 46 | func add(_ numbers: Int...) -> Int { 47 | return numbers.reduce(0, +) 48 | } 49 | 50 | 51 | //: [Previous](@previous) 52 | 53 | //: [Next](@next) 54 | 55 | -------------------------------------------------------------------------------- /DataStructures/Week 3 - Data Structures.playground/Pages/Day 3 - Set, Set Theory.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Week 3 - Day 3 - Set, Set Theory 2 | 3 | 4 | // What is a Set? 5 | // An unorganized group of elements. 6 | // There are NO DUPLICATES!!! 7 | 8 | // When would be use a set? 9 | 10 | // Two variations on Sets. 11 | 12 | // TreeSet vs. HashSet 13 | 14 | // Advantages and Disadvantages 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | // Set Theroy 32 | 33 | // 1. Definitions and Notation 34 | // Set 35 | // Ordered Pairs 36 | // Element 37 | // Subset and Not Subset 38 | // Proper Subset and Not Proper Subset 39 | // Compliment 40 | // Cardinality 41 | // Empty Set 42 | // Power Set 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | // 2. Operations 66 | // Union 67 | // Intersection 68 | // Difference 69 | // Cartesian Product 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | 92 | 93 | 94 | 95 | 96 | 97 | 98 | 99 | 100 | // 3. Infinite Sets 101 | // Universal Set = U 102 | // Natural Numbers 103 | // Integers 104 | // Real Numbers 105 | -------------------------------------------------------------------------------- /BigO/Week 1 - Big O.playground/Pages/Day 4 - Time vs. Space.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Big O Day 4 - Time vs. Space 2 | 3 | 4 | // What is the space complexity of the two following functions? 5 | func factorial(_ n: Int) -> Int { 6 | if n < 0 { 7 | return -1 8 | } else if n == 0 { 9 | return 1 10 | } else { 11 | return n * factorial(n - 1) 12 | } 13 | } 14 | 15 | 16 | 17 | 18 | 19 | // Time Complexity vs. Space Complexity 20 | // What is the difference between time and space complexity? 21 | // How do we count time complexity? How many loops it does. How long it takes. 22 | // How do we count space complexity? How much storage are you using? How much memory are you using? 23 | // - The size of your arrays, or maps, or other data structures. 24 | // - Recursive calls add 1 element of space per call. 25 | 26 | 27 | 28 | func fib(_ n: Int) -> Int { 29 | if n <= 0 { 30 | return 0 31 | } else if n == 1 { 32 | return 1 33 | } else { 34 | return fib(n-1) + fib(n-2) 35 | } 36 | } 37 | 38 | 39 | 40 | 41 | 42 | var memoFibNumbers: [Int:Int] = [1:1, 2:1] 43 | func memoFibNumber(_ number: Int) -> Int { 44 | if let fibNumber = memoFibNumbers[number] { 45 | return fibNumber 46 | } else { 47 | memoFibNumbers[number] = memoFibNumber(number - 1) + memoFibNumber(number - 2) 48 | return memoFibNumbers[number]! 49 | } 50 | } 51 | 52 | //: [Prev](@previous) 53 | 54 | -------------------------------------------------------------------------------- /DesignPatterns/Week 5 - Design Patterns.playground/Pages/Day 3 - Factory Method Pattern.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Week 5 - Day 3 - Factory Method Pattern 2 | 3 | //VIDEO WALKTHROUGH: https://vimeo.com/308815639 4 | 5 | import Foundation 6 | 7 | protocol Currency { 8 | func symbol() -> String 9 | func code() -> String 10 | } 11 | 12 | class Euro : Currency { 13 | func symbol() -> String { 14 | return "€" 15 | } 16 | 17 | func code() -> String { 18 | return "EUR" 19 | } 20 | } 21 | 22 | class UnitedStatesDolar : Currency { 23 | func symbol() -> String { 24 | return "$" 25 | } 26 | 27 | func code() -> String { 28 | return "USD" 29 | } 30 | } 31 | 32 | enum Country { 33 | case unitedStates, spain, uk, greece 34 | } 35 | 36 | enum CurrencyFactory { 37 | static func currency(for country:Country) -> Currency? { 38 | 39 | switch country { 40 | case .spain, .greece : 41 | return Euro() 42 | case .unitedStates : 43 | return UnitedStatesDolar() 44 | default: 45 | return nil 46 | } 47 | 48 | } 49 | } 50 | 51 | let noCurrencyCode = "No Currency Code Available" 52 | 53 | CurrencyFactory.currency(for: .greece)?.code() ?? noCurrencyCode 54 | CurrencyFactory.currency(for: .spain)?.code() ?? noCurrencyCode 55 | CurrencyFactory.currency(for: .unitedStates)?.code() ?? noCurrencyCode 56 | CurrencyFactory.currency(for: .uk)?.code() ?? noCurrencyCode 57 | -------------------------------------------------------------------------------- /DataStructures/Week 2 - Data Structures.playground/Pages/Day 3 - Dictionaries, HashMap.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Week 2 - Day 3 - Dictionaries, HashMap 2 | 3 | 4 | // Generic Dictionary 5 | // 6 | // Properties of a Dictionary 7 | // Key -> Value 8 | // You have to have the key to get the value 9 | // Dictionaries have NO ORDER 10 | 11 | 12 | 13 | 14 | 15 | 16 | // What can you use as a key for a Dictionary? 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | // How can you use a Class in as a key in a dictionary? 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | // What is the Hashable Protocol do? 50 | 51 | var firstName = "Sally" 52 | var lastName = "Watts" 53 | firstName.hashValue 54 | lastName.hashValue 55 | "\(firstName) \(lastName)".hashValue 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | 75 | // How are collisions dealt with in a hash map? 76 | 77 | // 1. Chaining 78 | // 2. Linear Probing 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | 92 | 93 | 94 | 95 | 96 | 97 | 98 | 99 | // What are the two ways to avoid collisions when working with Hash Maps? 100 | 101 | // 1. Make your key as unique as possible 102 | // 2. If you know the size of how many entries you have. Then make sure you have plenty of space so there are fewer collisions. 103 | -------------------------------------------------------------------------------- /DesignPatterns/Week 6 - Design Patterns.playground/Pages/Day 2 - Facade Pattern.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Week 6 - Day 1 - Facade Pattern 2 | 3 | //VIDEO WAlKTHROUGH: - https://vimeo.com/311514133 4 | 5 | import Foundation 6 | 7 | class Navigation{ 8 | static func getMeDirectionsHome(){ 9 | print("Getting directions home") 10 | } 11 | } 12 | 13 | class UberEats{ 14 | static func orderIndianFood(){ 15 | print("Ordering Indian Food") 16 | } 17 | } 18 | 19 | class Messaging{ 20 | static func textMyWifeImHeadingHome(){ 21 | print("Texting your wife I'm heading home") 22 | } 23 | } 24 | 25 | class SiriShortCutFacade{ 26 | 27 | static func siriImHeadingHome(){ 28 | Navigation.getMeDirectionsHome() 29 | UberEats.orderIndianFood() 30 | Messaging.textMyWifeImHeadingHome() 31 | } 32 | 33 | } 34 | 35 | 36 | ///////////////////////////////////////////////////////////////////////////// 37 | //Other Example 38 | 39 | enum Eternal { 40 | 41 | static func set(_ object: Any, forKey defaultName: String) { 42 | let defaults: UserDefaults = UserDefaults.standard 43 | defaults.set(object, forKey:defaultName) 44 | defaults.synchronize() 45 | } 46 | 47 | static func object(forKey key: String) -> AnyObject! { 48 | let defaults: UserDefaults = UserDefaults.standard 49 | return defaults.object(forKey: key) as AnyObject 50 | } 51 | 52 | } 53 | 54 | Eternal.set("Disconnect me. I’d rather be nothing", forKey:"Bishop") 55 | Eternal.object(forKey: "Bishop") 56 | 57 | 58 | -------------------------------------------------------------------------------- /DesignPatterns/Week 5 - Design Patterns.playground/Pages/Day 2 - Observer Pattern.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Week 5 - Day 2 - Observer Pattern 2 | 3 | //VIDEO WALKTHROUGH: https://vimeo.com/308815679 4 | 5 | protocol PropertyObserver : class { 6 | func willChange(propertyName: String, newPropertyValue: Any?) 7 | func didChange(propertyName: String, oldPropertyValue: Any?) 8 | } 9 | 10 | final class TestChambers { 11 | 12 | weak var observer: PropertyObserver? 13 | 14 | private let testChamberNumberName = "testChamberNumber" 15 | 16 | var testChamberNumber: Int = 0 { 17 | willSet(newValue) { 18 | observer?.willChange(propertyName: testChamberNumberName, newPropertyValue: newValue) 19 | } 20 | didSet { 21 | observer?.didChange(propertyName: testChamberNumberName, oldPropertyValue: oldValue) 22 | } 23 | } 24 | } 25 | 26 | final class Observer : PropertyObserver { 27 | func willChange(propertyName: String, newPropertyValue: Any?) { 28 | if newPropertyValue as? Int == 1 { 29 | print("Okay. Look. We both said a lot of things that you're going to regret.") 30 | } 31 | } 32 | 33 | func didChange(propertyName: String, oldPropertyValue: Any?) { 34 | if oldPropertyValue as? Int == 0 { 35 | print("Sorry about the mess. I've really let the place go since you killed me.") 36 | } 37 | } 38 | } 39 | 40 | var observerInstance = Observer() 41 | var testChambers = TestChambers() 42 | testChambers.observer = observerInstance 43 | testChambers.testChamberNumber += 1 44 | -------------------------------------------------------------------------------- /DataStructures/DataStructures.playground/Pages/Queue.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | import Foundation 2 | 3 | //MARK: - VIDEO LINKS 4 | //Conceptual Overview of a Queue: https://vimeo.com/320114616 5 | //Live Walkthrough of this Implementation: https://vimeo.com/320114270 6 | 7 | public struct Queue { 8 | private var array: [T] = [] 9 | public init() {} 10 | 11 | public var isEmpty: Bool { 12 | return array.isEmpty 13 | } 14 | 15 | public mutating func enqueue(value: T){ 16 | array.append(value) 17 | } 18 | 19 | public mutating func dequeue() -> T? { 20 | return isEmpty ? nil : array.removeFirst() 21 | } 22 | 23 | public func peek() -> T?{ 24 | return array.first 25 | } 26 | } 27 | 28 | extension Queue: CustomStringConvertible { 29 | public var description: String { 30 | return array.description 31 | } 32 | } 33 | 34 | extension Queue: ExpressibleByArrayLiteral { 35 | public init(arrayLiteral elements: T...) { 36 | array = elements 37 | } 38 | } 39 | 40 | var queue = Queue() 41 | queue.enqueue(value: "Cow") 42 | queue.enqueue(value: "Rabit") 43 | queue.enqueue(value: "Duck") 44 | queue.enqueue(value: "Lion") 45 | queue.enqueue(value: "Bear") 46 | // 47 | //print(queue.description) 48 | // 49 | //queue.dequeue() 50 | // 51 | //print(queue.description) 52 | // 53 | //queue.peek() 54 | // 55 | //print(queue.description) 56 | 57 | var movieQueue: Queue = ["Star Wars", "Lord of the Rings", "Harry Potter", "The Dark Knight", "Incpetion"] 58 | 59 | print(movieQueue.description) 60 | 61 | movieQueue.dequeue() 62 | 63 | print(movieQueue.description) 64 | 65 | -------------------------------------------------------------------------------- /DataStructures/Tries/Tries/Info.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | $(DEVELOPMENT_LANGUAGE) 7 | CFBundleExecutable 8 | $(EXECUTABLE_NAME) 9 | CFBundleIdentifier 10 | $(PRODUCT_BUNDLE_IDENTIFIER) 11 | CFBundleInfoDictionaryVersion 12 | 6.0 13 | CFBundleName 14 | $(PRODUCT_NAME) 15 | CFBundlePackageType 16 | APPL 17 | CFBundleShortVersionString 18 | 1.0 19 | CFBundleVersion 20 | 1 21 | LSRequiresIPhoneOS 22 | 23 | UILaunchStoryboardName 24 | LaunchScreen 25 | UIMainStoryboardFile 26 | Main 27 | UIRequiredDeviceCapabilities 28 | 29 | armv7 30 | 31 | UISupportedInterfaceOrientations 32 | 33 | UIInterfaceOrientationPortrait 34 | UIInterfaceOrientationLandscapeLeft 35 | UIInterfaceOrientationLandscapeRight 36 | 37 | UISupportedInterfaceOrientations~ipad 38 | 39 | UIInterfaceOrientationPortrait 40 | UIInterfaceOrientationPortraitUpsideDown 41 | UIInterfaceOrientationLandscapeLeft 42 | UIInterfaceOrientationLandscapeRight 43 | 44 | 45 | 46 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Xcode 2 | # 3 | # gitignore contributors: remember to update Global/Xcode.gitignore, Objective-C.gitignore & Swift.gitignore 4 | 5 | ## Build generated 6 | build/ 7 | DerivedData/ 8 | .DS_Store 9 | 10 | ## Various settings 11 | *.pbxuser 12 | !default.pbxuser 13 | *.mode1v3 14 | !default.mode1v3 15 | *.mode2v3 16 | !default.mode2v3 17 | *.perspectivev3 18 | !default.perspectivev3 19 | xcuserdata/ 20 | 21 | ## Other 22 | *.moved-aside 23 | *.xccheckout 24 | *.xcscmblueprint 25 | 26 | ## Obj-C/Swift specific 27 | *.hmap 28 | *.ipa 29 | *.dSYM.zip 30 | *.dSYM 31 | 32 | ## Playgrounds 33 | timeline.xctimeline 34 | playground.xcworkspace 35 | 36 | # Swift Package Manager 37 | # 38 | # Add this line if you want to avoid checking in source code from Swift Package Manager dependencies. 39 | # Packages/ 40 | # Package.pins 41 | # Package.resolved 42 | .build/ 43 | 44 | # CocoaPods 45 | # 46 | # We recommend against adding the Pods directory to your .gitignore. However 47 | # you should judge for yourself, the pros and cons are mentioned at: 48 | # https://guides.cocoapods.org/using/using-cocoapods.html#should-i-check-the-pods-directory-into-source-control 49 | # 50 | # Pods/ 51 | 52 | # Carthage 53 | # 54 | # Add this line if you want to avoid checking in source code from Carthage dependencies. 55 | # Carthage/Checkouts 56 | 57 | Carthage/Build 58 | 59 | # fastlane 60 | # 61 | # It is recommended to not store the screenshots in the git repo. Instead, use fastlane to re-generate the 62 | # screenshots whenever they are needed. 63 | # For more information about the recommended setup visit: 64 | # https://docs.fastlane.tools/best-practices/source-control/#source-control 65 | 66 | fastlane/report.xml 67 | fastlane/Preview.html 68 | fastlane/screenshots/**/*.png 69 | fastlane/test_output 70 | -------------------------------------------------------------------------------- /DataStructures/Tries/Tries/Base.lproj/LaunchScreen.storyboard: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | -------------------------------------------------------------------------------- /DataStructures/DataStructures.playground/Pages/Stack.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | import Foundation 2 | 3 | //MARK: - VIDEO LINKS 4 | //Conceptual Overview of a Stack: https://vimeo.com/devmountain/review/320111190/a55f511fa3 5 | //Live Walkthrough of this Implementation: https://vimeo.com/devmountain/review/320111352/f8f3e0d43a 6 | 7 | 8 | public struct Stack { 9 | private var storage: [Element] = [] 10 | public init() {} 11 | } 12 | 13 | extension Stack: CustomStringConvertible { 14 | public var description: String { 15 | let topDivider = "----top----\n" 16 | let bottomDivider = "\n-----------" 17 | 18 | let stackElements = storage 19 | .map { "\($0)" } 20 | .reversed() 21 | .joined(separator: "\n") 22 | 23 | return topDivider + stackElements + bottomDivider 24 | } 25 | // Initialization 26 | public init(_ elements: [Element]) { 27 | storage = elements 28 | } 29 | 30 | // CRUD 31 | public mutating func push(_ element: Element) { 32 | storage.append(element) 33 | } 34 | 35 | @discardableResult 36 | public mutating func pop() -> Element? { 37 | return storage.popLast() 38 | } 39 | 40 | public func peek() -> Element? { 41 | return storage.last 42 | } 43 | 44 | public var isEmpty: Bool { 45 | return peek() == nil 46 | } 47 | } 48 | 49 | extension Stack: ExpressibleByArrayLiteral { // Makes it so you can initialize a stack like you would an array 50 | public init(arrayLiteral elements: Element...) { 51 | storage = elements 52 | } 53 | } 54 | 55 | // MARK: - Example 56 | var stack: Stack = [1.0, 2.0, 3.0, 4.0] 57 | print(stack, "Before pop") 58 | stack.pop() 59 | print(stack, "After pop") 60 | 61 | -------------------------------------------------------------------------------- /DataStructures/DataStructures.playground/Pages/BinarySearchTree.xcplaygroundpage/Sources/BinaryNode.swift: -------------------------------------------------------------------------------- 1 | import Foundation 2 | 3 | public class BinaryNode { 4 | 5 | public var value: Element 6 | public var leftChild: BinaryNode? 7 | public var rightChild: BinaryNode? 8 | 9 | public init(value: Element) { 10 | self.value = value 11 | } 12 | } 13 | 14 | extension BinaryNode: CustomStringConvertible { 15 | 16 | public var description: String { 17 | return diagram(for: self) 18 | } 19 | 20 | private func diagram(for node: BinaryNode?, 21 | _ top: String = "", 22 | _ root: String = "", 23 | _ bottom: String = "") -> String { 24 | guard let node = node else { 25 | return root + "nil\n" 26 | } 27 | if node.leftChild == nil && node.rightChild == nil { 28 | return root + "\(node.value)\n" 29 | } 30 | return diagram(for: node.rightChild, top + " ", top + "┌──", top + "│ ") 31 | + root + "\(node.value)\n" 32 | + diagram(for: node.leftChild, bottom + "│ ", bottom + "└──", bottom + " ") 33 | } 34 | } 35 | 36 | extension BinaryNode { 37 | 38 | public func traverseInOrder(visit: (Element) -> Void) { 39 | leftChild?.traverseInOrder(visit: visit) 40 | visit(value) 41 | rightChild?.traverseInOrder(visit: visit) 42 | } 43 | 44 | public func traversePreOrder(visit: (Element) -> Void) { 45 | visit(value) 46 | leftChild?.traversePreOrder(visit: visit) 47 | rightChild?.traversePreOrder(visit: visit) 48 | } 49 | 50 | public func traversePostOrder(visit: (Element) -> Void) { 51 | leftChild?.traversePostOrder(visit: visit) 52 | rightChild?.traversePostOrder(visit: visit) 53 | visit(value) 54 | } 55 | } 56 | -------------------------------------------------------------------------------- /DataStructures/Week 3 - Data Structures.playground/Pages/Advanced Binary Search Tree.xcplaygroundpage/Sources/BinaryNode.swift: -------------------------------------------------------------------------------- 1 | import Foundation 2 | 3 | public class BinaryNode { 4 | 5 | public var value: Element 6 | public var leftChild: BinaryNode? 7 | public var rightChild: BinaryNode? 8 | 9 | public init(value: Element) { 10 | self.value = value 11 | } 12 | } 13 | 14 | extension BinaryNode: CustomStringConvertible { 15 | 16 | public var description: String { 17 | return diagram(for: self) 18 | } 19 | 20 | private func diagram(for node: BinaryNode?, 21 | _ top: String = "", 22 | _ root: String = "", 23 | _ bottom: String = "") -> String { 24 | guard let node = node else { 25 | return root + "nil\n" 26 | } 27 | if node.leftChild == nil && node.rightChild == nil { 28 | return root + "\(node.value)\n" 29 | } 30 | return diagram(for: node.rightChild, top + " ", top + "┌──", top + "│ ") 31 | + root + "\(node.value)\n" 32 | + diagram(for: node.leftChild, bottom + "│ ", bottom + "└──", bottom + " ") 33 | } 34 | } 35 | 36 | extension BinaryNode { 37 | 38 | public func traverseInOrder(visit: (Element) -> Void) { 39 | leftChild?.traverseInOrder(visit: visit) 40 | visit(value) 41 | rightChild?.traverseInOrder(visit: visit) 42 | } 43 | 44 | public func traversePreOrder(visit: (Element) -> Void) { 45 | visit(value) 46 | leftChild?.traversePreOrder(visit: visit) 47 | rightChild?.traversePreOrder(visit: visit) 48 | } 49 | 50 | public func traversePostOrder(visit: (Element) -> Void) { 51 | leftChild?.traversePostOrder(visit: visit) 52 | rightChild?.traversePostOrder(visit: visit) 53 | visit(value) 54 | } 55 | } 56 | -------------------------------------------------------------------------------- /InterviewQuestions/Week 4 - Technical Interviews.playground/Pages/Day 1 - Interview Questions 1.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Week 4 - Day 1 - Technical Interviews 2 | 3 | 4 | // 1. Listen/Repeat the question/ Clarify the question. 5 | // 2. Think of good examples/your general approach. 6 | // 3. State the Brute Force method. 7 | // 4. Optimizing 8 | // 5. Walk Through 9 | // 6. Test 10 | // 7. Implement 11 | 12 | 13 | public func inCommon(_ a: [Int], _ b: [Int]) -> [Int] { 14 | if a.count == 0 || b.count == 0 { 15 | return [Int]() 16 | } 17 | if a.count < b.count { 18 | return inCommonOrganized(a, b) 19 | } else { 20 | return inCommonOrganized(b, a) 21 | } 22 | } 23 | 24 | // This is where a is < b 25 | // O(2a) -> O(a) 26 | private func inCommonOrganized(_ a: [Int], _ b: [Int]) -> [Int] { 27 | var inCommonArray = [Int]() 28 | var inCommonDict = [Int: Bool]() 29 | 30 | for num in a { 31 | inCommonDict[a] = false 32 | } 33 | for num in b { 34 | if inCommonDict[b] != nil && inCommonDict[b] == false { 35 | inCommonDict[b] = true 36 | inCommonArray.append(b) 37 | } 38 | } 39 | return inCommonArray 40 | } 41 | 42 | 43 | // String Rotation 44 | // Assume you have a method isSubstring (in swift it's called .contains()) which checks if one word is a substring of another. Given two strings, s1 and s2, write code to check if s2 is a rotation of s1 using only one call to .contains(). 45 | 46 | // For example: "watterbottle" is a rotation of "erbottlewat" 47 | 48 | 49 | // 1. Listen/Repeat the question/ Clarify the question. 50 | // 2. Think of good examples/your general approach. 51 | // 3. Brute Force 52 | // 4. Optimizing 53 | // 5. Walk Through 54 | // 6. Test 55 | // 7. Implement 56 | 57 | extension String { 58 | func isRotation(of other: String) -> Bool { 59 | return (self + self).contains(other) 60 | } 61 | } 62 | 63 | "waterbottle".isRotation(of: "terbottlewa") 64 | -------------------------------------------------------------------------------- /InterviewQuestions/Week 4 - Technical Interviews.playground/Pages/Day 2 - Interview Questions 2.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Week 4 - Day 2 - Technical Interviews 2 | 3 | // One Away: Ther eare three types of edits that can be performed on this array: inserting an element, removing an element, and replacing an element. Given two arrays write a function to check if thy are one edit (or zero) away. 4 | 5 | public func isOneEditAway(_ a1: [Int], _ a2: [Int]) -> Bool { 6 | if a1.count == a2.count { 7 | return checkForReplace(a1, a2) 8 | } else if (a1.count == a2.count + 1) { 9 | return checkForInsert(a1, a2) 10 | } else if (a1.count + 1 == a2.count) { 11 | return checkForInsert(a2, a1) 12 | } else { 13 | return false 14 | } 15 | } 16 | 17 | public func checkForReplace(_ a1: [Int], _ a2: [Int]) -> Bool { 18 | var repeatCount = 0 19 | for (i, num) in a1.enumerated() { 20 | if num != a2[i] { 21 | repeatCount += 1 22 | if repeatCount > 1 { 23 | return false 24 | } 25 | } 26 | } 27 | return true 28 | } 29 | 30 | // The large array is guarenteed to be only 1 larger than the small array. 31 | public func checkForInsert(_ smallArray: [Int], _ largeArray: [Int]) -> Bool { 32 | 33 | var smallIndex = 0 34 | var largeIndex = 0 35 | 36 | while( largeIndex < largeArray.count && smallIndex < smallArray.count ) { 37 | if smallArray[smallIndex] == largeArray[largeIndex] { 38 | smallIndex += 1 39 | largeIndex += 1 40 | } else { 41 | if smallIndex != largeIndex { 42 | return false 43 | } 44 | largeIndex += 1 45 | } 46 | } 47 | 48 | return true 49 | } 50 | 51 | 52 | isOneEditAway([1,2,3,4,5], [1,2,3,4,5]) 53 | isOneEditAway([1,2,3,4,5], [1,2,3,4,6]) 54 | isOneEditAway([1,2,3,4,5], [1,2,4,5]) 55 | isOneEditAway([1,2,4,5], [1,2,3,4,5]) 56 | isOneEditAway([1,2,3,4,5], [1,2,3,4,5,6]) 57 | isOneEditAway([1,2,3,4,5,6], [1,2,3,4,5]) 58 | -------------------------------------------------------------------------------- /DataStructures/Tries/Tries/Assets.xcassets/AppIcon.appiconset/Contents.json: -------------------------------------------------------------------------------- 1 | { 2 | "images" : [ 3 | { 4 | "idiom" : "iphone", 5 | "size" : "20x20", 6 | "scale" : "2x" 7 | }, 8 | { 9 | "idiom" : "iphone", 10 | "size" : "20x20", 11 | "scale" : "3x" 12 | }, 13 | { 14 | "idiom" : "iphone", 15 | "size" : "29x29", 16 | "scale" : "2x" 17 | }, 18 | { 19 | "idiom" : "iphone", 20 | "size" : "29x29", 21 | "scale" : "3x" 22 | }, 23 | { 24 | "idiom" : "iphone", 25 | "size" : "40x40", 26 | "scale" : "2x" 27 | }, 28 | { 29 | "idiom" : "iphone", 30 | "size" : "40x40", 31 | "scale" : "3x" 32 | }, 33 | { 34 | "idiom" : "iphone", 35 | "size" : "60x60", 36 | "scale" : "2x" 37 | }, 38 | { 39 | "idiom" : "iphone", 40 | "size" : "60x60", 41 | "scale" : "3x" 42 | }, 43 | { 44 | "idiom" : "ipad", 45 | "size" : "20x20", 46 | "scale" : "1x" 47 | }, 48 | { 49 | "idiom" : "ipad", 50 | "size" : "20x20", 51 | "scale" : "2x" 52 | }, 53 | { 54 | "idiom" : "ipad", 55 | "size" : "29x29", 56 | "scale" : "1x" 57 | }, 58 | { 59 | "idiom" : "ipad", 60 | "size" : "29x29", 61 | "scale" : "2x" 62 | }, 63 | { 64 | "idiom" : "ipad", 65 | "size" : "40x40", 66 | "scale" : "1x" 67 | }, 68 | { 69 | "idiom" : "ipad", 70 | "size" : "40x40", 71 | "scale" : "2x" 72 | }, 73 | { 74 | "idiom" : "ipad", 75 | "size" : "76x76", 76 | "scale" : "1x" 77 | }, 78 | { 79 | "idiom" : "ipad", 80 | "size" : "76x76", 81 | "scale" : "2x" 82 | }, 83 | { 84 | "idiom" : "ipad", 85 | "size" : "83.5x83.5", 86 | "scale" : "2x" 87 | }, 88 | { 89 | "idiom" : "ios-marketing", 90 | "size" : "1024x1024", 91 | "scale" : "1x" 92 | } 93 | ], 94 | "info" : { 95 | "version" : 1, 96 | "author" : "xcode" 97 | } 98 | } -------------------------------------------------------------------------------- /DesignPatterns/Week 6 - Design Patterns.playground/Pages/Day 1- Decorator Pattern.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | import Foundation 2 | 3 | //VIDEO WAlKTHROUGH: - https://vimeo.com/308815548 4 | 5 | protocol Coffee { 6 | func getCost() -> Double 7 | func getIngredients() -> String 8 | } 9 | 10 | class SimpleCoffee: Coffee { 11 | func getCost() -> Double { 12 | return 1.0 13 | } 14 | 15 | func getIngredients() -> String { 16 | return "Coffee" 17 | } 18 | } 19 | 20 | class CoffeeDecorator: Coffee { 21 | private let decoratedCoffee: Coffee 22 | fileprivate let ingredientSeparator: String = ", " 23 | 24 | required init(decoratedCoffee: Coffee) { 25 | self.decoratedCoffee = decoratedCoffee 26 | } 27 | 28 | func getCost() -> Double { 29 | return decoratedCoffee.getCost() 30 | } 31 | 32 | func getIngredients() -> String { 33 | return decoratedCoffee.getIngredients() 34 | } 35 | } 36 | 37 | final class Milk: CoffeeDecorator { 38 | required init(decoratedCoffee: Coffee) { 39 | super.init(decoratedCoffee: decoratedCoffee) 40 | } 41 | 42 | override func getCost() -> Double { 43 | return super.getCost() + 0.5 44 | } 45 | 46 | override func getIngredients() -> String { 47 | return super.getIngredients() + ingredientSeparator + "Milk" 48 | } 49 | } 50 | 51 | final class WhipCoffee: CoffeeDecorator { 52 | required init(decoratedCoffee: Coffee) { 53 | super.init(decoratedCoffee: decoratedCoffee) 54 | } 55 | 56 | override func getCost() -> Double { 57 | return super.getCost() + 0.7 58 | } 59 | 60 | override func getIngredients() -> String { 61 | return super.getIngredients() + ingredientSeparator + "Whip" 62 | } 63 | } 64 | 65 | 66 | var someCoffee: Coffee = SimpleCoffee() 67 | print("Cost : \(someCoffee.getCost()); Ingredients: \(someCoffee.getIngredients())") 68 | someCoffee = Milk(decoratedCoffee: someCoffee) 69 | print("Cost : \(someCoffee.getCost()); Ingredients: \(someCoffee.getIngredients())") 70 | someCoffee = WhipCoffee(decoratedCoffee: someCoffee) 71 | print("Cost : \(someCoffee.getCost()); Ingredients: \(someCoffee.getIngredients())") 72 | -------------------------------------------------------------------------------- /DataStructures/Tries/Tries/AppDelegate.swift: -------------------------------------------------------------------------------- 1 | // 2 | // AppDelegate.swift 3 | // Tries 4 | // 5 | // Created by DevMountain on 10/23/18. 6 | // Copyright © 2018 trevorAdcock. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | @UIApplicationMain 12 | class AppDelegate: UIResponder, UIApplicationDelegate { 13 | 14 | var window: UIWindow? 15 | 16 | 17 | func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool { 18 | // Override point for customization after application launch. 19 | 20 | 21 | return true 22 | } 23 | 24 | func applicationWillResignActive(_ application: UIApplication) { 25 | // Sent when the application is about to move from active to inactive state. This can occur for certain types of temporary interruptions (such as an incoming phone call or SMS message) or when the user quits the application and it begins the transition to the background state. 26 | // Use this method to pause ongoing tasks, disable timers, and invalidate graphics rendering callbacks. Games should use this method to pause the game. 27 | } 28 | 29 | func applicationDidEnterBackground(_ application: UIApplication) { 30 | // Use this method to release shared resources, save user data, invalidate timers, and store enough application state information to restore your application to its current state in case it is terminated later. 31 | // If your application supports background execution, this method is called instead of applicationWillTerminate: when the user quits. 32 | } 33 | 34 | func applicationWillEnterForeground(_ application: UIApplication) { 35 | // Called as part of the transition from the background to the active state; here you can undo many of the changes made on entering the background. 36 | } 37 | 38 | func applicationDidBecomeActive(_ application: UIApplication) { 39 | // Restart any tasks that were paused (or not yet started) while the application was inactive. If the application was previously in the background, optionally refresh the user interface. 40 | } 41 | 42 | func applicationWillTerminate(_ application: UIApplication) { 43 | // Called when the application is about to terminate. Save data if appropriate. See also applicationDidEnterBackground:. 44 | } 45 | 46 | 47 | } 48 | 49 | -------------------------------------------------------------------------------- /BigO/Week 1 - Big O.playground/Pages/Day 2 - O(log n), O(2^n).xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Big O Day 2 - O(log n), O(2^n) 2 | 3 | 4 | 5 | // What is the big O of the following functions 6 | let array1: [Int] = [1,2,3,5,6,3,4,5,2] 7 | let array2: [Int] = [0,1,2,3,4,5,6,7,8,9,10] 8 | 9 | let sortedArray = [1,2,3,5,7,8,10,13,14,16,20,21] 10 | 11 | func smartFind(num: Int, inArray array: [Int]) -> Bool { 12 | for number in array { 13 | if num == number { 14 | return true 15 | } 16 | } 17 | return false 18 | } 19 | 20 | //dumbFind(num: 3, inArray: sortedArray) 21 | 22 | //func dumbFind(num: Int, inArray array: [Int]) -> Bool{ 23 | // var found: Bool = false 24 | // 25 | //} 26 | 27 | 28 | // ASSUMPTION: The array we're using is sorted 29 | //log(n) Logarithmic Time 30 | func find(num: Int, inArray array: [Int]) -> Bool { 31 | let middleIndex = array.count / 2 32 | 33 | if num == array[middleIndex] { 34 | return true 35 | } else if array.count == 1 { 36 | return false 37 | } 38 | 39 | if num < array[middleIndex] { 40 | return find(num: num, inArray: [Int](array[.. Int{ 50 | // if n == 0{ 51 | // return 1 52 | // } 53 | // print("Calculating Junk n is \(n)") 54 | // return calculateRandomJunk(n: n-1) + calculateRandomJunk(n: n - 2) 55 | //} 56 | // 57 | //calculateRandomJunk(n: 22) 58 | 59 | 60 | 61 | // O(log n) 62 | 63 | // What is the definition of a log? 64 | 65 | // log_x(a) = b -> x^b = a 66 | 67 | // Do we care about what base the log is? 68 | // Why do we use log_2 as a default? 69 | 70 | // Exponential 71 | // O(2^n) and it's variants 72 | 73 | 74 | func f(_ num: Int) -> Int { 75 | if num <= 0 { 76 | return 1 77 | } 78 | return f(num - 1) + f(num - 1) // + f(num - 1) will make it O(3^n) 79 | } 80 | 81 | f(2) 82 | 83 | 84 | 85 | // Assignment 86 | // Give a real life example of both O(log n) and O(2^n) 87 | // What is the detailed and simplified Big O of this function? 88 | func sumDigits(n: Int) -> Int { 89 | var sum = 0 90 | var n = n 91 | while n > 0 { 92 | sum += n % 10 93 | n /= 10 94 | } 95 | return sum 96 | } 97 | 98 | //: [Previous](@previous) 99 | 100 | //: [Next](@next) 101 | -------------------------------------------------------------------------------- /DataStructures/Week 3 - Data Structures.playground/Pages/Recursive Enum Binary Search Trees.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Week 3 - Day 1 - Binary Search Trees 2 | 3 | 4 | public indirect enum BinaryTree { 5 | case node(BinaryTree, T, BinaryTree) 6 | case empty 7 | 8 | public var count: Int { 9 | switch self { 10 | case let .node(left, _, right): 11 | return left.count + 1 + right.count 12 | case .empty: 13 | return 0 14 | } 15 | } 16 | } 17 | 18 | extension BinaryTree: CustomStringConvertible { 19 | public var description: String { 20 | switch self { 21 | case let .node(left, value, right): 22 | return "value: \(value), left = [\(left.description)], right = [\(right.description)]" 23 | case .empty: 24 | return "" 25 | } 26 | } 27 | } 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | // When is a tree Degenerate? 37 | // It's a tree where each node typically has 1 child. 38 | 39 | // When is a tree Balanced? 40 | // It's a tree where the left and right sides have roughly the same number of nodes. 41 | 42 | // When is a tree Complete? 43 | // It's a tree where all of the nodes are inserted in the leftmost position and you don't move to the next layer until the current layer is full. 44 | 45 | // When is a tree Full? 46 | // When each node of the tree has 0 or 2 children. 47 | 48 | // When is a tree Perfect? 49 | // All the leaf nodes have the same depth or differ by at most 1. 50 | 51 | 52 | 53 | // Binary Search Tree 54 | // Rules - The left hand side must be less than the parent. 55 | // - The Right hand side must be more than the parent. 56 | 57 | // Can a BST have duplicate nodes? 58 | // Short answer is yes. 59 | // Using a linked list at the node. 60 | // Or changing the left definition to be <= 61 | 62 | 63 | // Talk about how we search, insert and delete in a Binary Search Tree 64 | 65 | // Assignment 66 | // Make a Degenerate Tree 67 | BinaryTree.node(.empty, "0", BinaryTree.node(.empty, "1", BinaryTree.node(.empty, "2", BinaryTree.node(.empty, "3", .empty)))) 68 | // Make a Perfect Tree 69 | //let threeNode = BinaryTree.node(.empty, "3", .empty) 70 | //let perfectTree = BinaryTree.node(threeNode, "3", threeNode) 71 | BinaryTree.node(BinaryTree.node(.empty, "3", .empty), "3", BinaryTree.node(.empty, "3", .empty)) 72 | 73 | // Make a Binary Seach Tree 74 | let threeNode = BinaryTree.node(.empty, "3", .empty) 75 | let fourNode = BinaryTree.node(.empty, "4", .empty) 76 | let eightNode = BinaryTree.node(.empty, "8", .empty) 77 | 78 | 79 | BinaryTree.node(threeNode, "4", eightNode) 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | -------------------------------------------------------------------------------- /DesignPatterns/Week 5 - Design Patterns.playground/Pages/Day 1 - Stategy Pattern.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Week 5 - Day 1 - Strategy Pattern 2 | import UIKit 3 | 4 | //VIDEO WALKTHROUGH: https://vimeo.com/308815351 5 | 6 | // Strategy Pattern 7 | 8 | // Let's talk pokemon 9 | 10 | // We have to design a program that will represent Pokemon. 11 | // Each Pokemon has an image and when I display that image it just prints that image. 12 | // Each Pokemon has only a way they travel. 13 | // Now let's add one attack to each Pokemon. 14 | 15 | 16 | 17 | class Pokemon { 18 | var image: UIImage 19 | var attackStategy: AttackStategy 20 | var travelStategy: TravelStategy 21 | 22 | func display() { 23 | print(image) 24 | } 25 | 26 | func travel() { 27 | travelStategy.travel() 28 | } 29 | 30 | func attack() { 31 | attackStategy.attack() 32 | } 33 | 34 | init(image: UIImage, attackStategy: AttackStategy, travelStategy: TravelStategy) { 35 | self.image = image 36 | self.attackStategy = attackStategy 37 | self.travelStategy = travelStategy 38 | } 39 | } 40 | 41 | 42 | 43 | 44 | // Magikarp - Swim/Splash 45 | // Pikachu - Walk/Thunder 46 | // Pidgey - Fly/Gust 47 | // Spearow - Peck/Gust 48 | // Zaptos - Fly/Thunder 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | protocol AttackStategy { 58 | func attack() 59 | func run() 60 | func defend() 61 | } 62 | 63 | class SplashAttackStategy: AttackStategy { 64 | func attack() { 65 | print("Splash, Splash, Splash, Splash...not very effective") 66 | } 67 | } 68 | 69 | class ThunderAttackStategy: AttackStategy { 70 | func attack() { 71 | print("Thuuuunder!!!!") 72 | } 73 | } 74 | 75 | class PeckAttackStategy: AttackStategy { 76 | func attack() { 77 | print("Peck peck peck peck peck peck peck peck") 78 | } 79 | } 80 | 81 | class GustAttackStategy: AttackStategy { 82 | func attack() { 83 | print("Gust....") 84 | } 85 | } 86 | 87 | 88 | 89 | 90 | 91 | 92 | 93 | protocol TravelStategy { 94 | func travel() 95 | } 96 | 97 | class SwimTravelStategy: TravelStategy { 98 | func travel() { 99 | print("Just keep swimming...") 100 | } 101 | } 102 | 103 | class WalkTravelStategy: TravelStategy { 104 | func travel() { 105 | print("Walk and walk and walk and walk") 106 | } 107 | } 108 | 109 | class FlyTravelStategy: TravelStategy { 110 | func travel() { 111 | print("Fly away") 112 | } 113 | } 114 | 115 | 116 | 117 | 118 | 119 | 120 | 121 | 122 | 123 | let pikachu = Pokemon(image: UIImage(named: "Pikachu"), attackStategy: ThunderAttackStategy(), travelStategy: WalkTravelStategy()) 124 | 125 | pikachu.attack() 126 | pikachu.travel() 127 | -------------------------------------------------------------------------------- /DataStructures/DataStructures.playground/Pages/GeneralPurposeTree.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | import Foundation 2 | 3 | //MARK: - VIDEO LINKS 4 | //Conceptual Overview and live walkthrough of this implementation: https://vimeo.com/304094785 5 | 6 | 7 | public class TreeNode { 8 | 9 | public var value: T 10 | public var children: [TreeNode] = [] 11 | 12 | public init(_ value: T) { 13 | self.value = value 14 | } 15 | 16 | public func add(_ child: TreeNode) { 17 | children.append(child) 18 | } 19 | } 20 | 21 | extension TreeNode { 22 | public func forEachDepthFirst(visit: (TreeNode) -> Void) { 23 | visit(self) 24 | children.forEach { 25 | $0.forEachDepthFirst(visit: visit) 26 | } 27 | } 28 | } 29 | 30 | extension TreeNode { 31 | public func forEachLevelOrder(visit: (TreeNode) -> Void) { 32 | visit(self) 33 | var queue = Queue() 34 | children.forEach { queue.enqueue($0) } 35 | while let node = queue.dequeue() { 36 | visit(node) 37 | node.children.forEach { queue.enqueue($0) } 38 | } 39 | } 40 | } 41 | 42 | extension TreeNode where T: Equatable { 43 | public func search(_ value: T) -> TreeNode? { 44 | var result: TreeNode? 45 | 46 | forEachDepthFirst { node in 47 | if node.value == value { 48 | result = node 49 | } 50 | } 51 | return result 52 | } 53 | } 54 | 55 | 56 | // MARK: - Example 57 | func makeBeverageTree() -> TreeNode { 58 | let tree = TreeNode("Beverages") 59 | 60 | let hot = TreeNode("hot") 61 | let cold = TreeNode("cold") 62 | 63 | let tea = TreeNode("tea") 64 | let coffee = TreeNode("coffee") 65 | let chocolate = TreeNode("cocoa") 66 | 67 | let blackTea = TreeNode("black") 68 | let greenTea = TreeNode("green") 69 | let chaiTea = TreeNode("chai") 70 | 71 | let soda = TreeNode("soda") 72 | let milk = TreeNode("milk") 73 | 74 | let gingerAle = TreeNode("ginger ale") 75 | let bitterLemon = TreeNode("bitter lemon") 76 | 77 | tree.add(hot) 78 | tree.add(cold) 79 | 80 | hot.add(tea) 81 | hot.add(coffee) 82 | hot.add(chocolate) 83 | 84 | cold.add(soda) 85 | cold.add(milk) 86 | 87 | tea.add(blackTea) 88 | tea.add(greenTea) 89 | tea.add(chaiTea) 90 | 91 | soda.add(gingerAle) 92 | soda.add(bitterLemon) 93 | 94 | return tree 95 | } 96 | 97 | let tree = makeBeverageTree() 98 | 99 | // Depth First 100 | tree.forEachDepthFirst { print($0.value) } 101 | 102 | // Level Order 103 | tree.forEachLevelOrder { print($0.value) } 104 | 105 | 106 | // Search 107 | if let searchResult1 = tree.search("ginger ale") { 108 | print("Found node: \(searchResult1.value)") 109 | } 110 | 111 | if let searchResult2 = tree.search("WKD Blue") { 112 | print(searchResult2.value) 113 | } else { 114 | print("Couldn't find WKD Blue") 115 | } 116 | -------------------------------------------------------------------------------- /DataStructures/Week 3 - Data Structures.playground/Pages/Day 4 - Graphs.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Week 3 - Day 4 - Graphs 2 | 3 | 4 | 5 | // Some inherently complex problems. 6 | // 1. Travel from point A to point B. 7 | // 2. Represent all the friends one has on Facebook, Instagram and Twitter. 8 | // 3. The London Underground. 9 | // 4. All the flights in the world for a particular airline. 10 | // 5. How do I create a World Wide Web and do networking from one side of the world to the other? 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | // What is a Graph? Is a set of vertecies and a set of edges that connects those vertecies. 58 | 59 | // Definitions 60 | // 1. Vertex or Nodes - A dot or a space on the graph that represents a state. 61 | // 2. Edge, links, ties, or relations - Represents some connection between two nodes. 62 | // 3. Adjacency - When two nodes are connected by one edge. 63 | // 4. Path - When a node is connected to another node by one or more edges. 64 | // 5. Loop - An edge that connects one node back to itself. 65 | // 6. Parallel Edges - A duplicate edge that connects the same two nodes. 66 | // 7. Degree of a Vertex - The number of edges out of that node. In Directed Graphs this can be broken into an in degree and an out degree. 67 | // 8. Pendent Vertex - A node that has only one edge. 68 | // 9. Isolated Vertex - A node with zero edges. 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | 92 | 93 | 94 | 95 | 96 | 97 | 98 | 99 | 100 | 101 | 102 | 103 | 104 | 105 | 106 | 107 | 108 | 109 | 110 | 111 | 112 | // Types of Graphs 113 | 114 | // 1. Null Graph - Is a graph with no edges. 115 | // 2. Trivial Graph - A graph with only one node and no edges. 116 | // 3. Non-Directed Graph - Each of the edges are bi-directional. {a,b} 117 | // 4. Directed Graph - Edges only go one way. (a,b) 118 | // 5. Simple Graph - A graph with no loops and no parallel edges. 119 | // 1. The max number of edges possible is n(n-1)/2 where n is the number of vertecies. 120 | // 2. The max number of graphs with n vertecies is 2^(n(n-1)/2) 121 | // 6. Connected Graph - All the nodes are connected in the graph. 122 | // 7. Disconnected Graph - Not all the nodes are connected. 123 | // 8. Regular Graph - A graph where all of the nodes have the same degree. 124 | // 9. Complete Graph - All nodes have a direct connection to every other node. 125 | // 10. Cyclic Graph - 126 | // 11. Acyclic Graph - 127 | 128 | 129 | 130 | 131 | 132 | 133 | 134 | 135 | 136 | 137 | 138 | 139 | 140 | 141 | 142 | 143 | 144 | 145 | 146 | 147 | 148 | 149 | 150 | 151 | 152 | 153 | 154 | 155 | 156 | 157 | 158 | 159 | 160 | 161 | 162 | 163 | 164 | 165 | 166 | 167 | 168 | // What are graphs used for? 169 | // https://www.youtube.com/watch?v=7JlCfKLVEzs 170 | // What is a Turing Machine? 171 | -------------------------------------------------------------------------------- /InterviewQuestions/Week 4 - Technical Interviews.playground/Pages/Day 3 - Interview Questions 3.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Week 4 - Day 3 - Technical Interviews 2 | 3 | 4 | // Remote Directions 5 | // Given a remote A-Z. Make a function that takes in a string and returns an array of strings where each string contains the directions for how to spell the given word. Start your directions from 'A' for the first letter and then subsequent letters from the previous letter. 6 | // 7 | // A - B - C - D 8 | // E - F - G - H 9 | // I - J - K - L 10 | // M - N - O - P 11 | // Q - R - S - T 12 | // U - V - W - X 13 | // Y - Z 14 | // 15 | 16 | 17 | struct Coord { 18 | let col: Int 19 | let row: Int 20 | init(_ row: Int, _ col: Int) { 21 | self.row = row 22 | self.col = col 23 | } 24 | } 25 | 26 | let startingPosition = Coord(0,0) 27 | let coords: [Character: Coord] = ["A":Coord(0,0), 28 | "B":Coord(0,1), 29 | "C":Coord(0,2), 30 | "D":Coord(0,3), 31 | "E":Coord(1,0), 32 | "F":Coord(1,1), 33 | "G":Coord(1,2), 34 | "H":Coord(1,3), 35 | "I":Coord(2,0), 36 | "J":Coord(2,1), 37 | "K":Coord(2,2), 38 | "L":Coord(2,3), 39 | "M":Coord(3,0), 40 | "N":Coord(3,1), 41 | "O":Coord(3,2), 42 | "P":Coord(3,3), 43 | "Q":Coord(4,0), 44 | "R":Coord(4,1), 45 | "S":Coord(4,2), 46 | "T":Coord(4,3), 47 | "U":Coord(5,0), 48 | "V":Coord(5,1), 49 | "W":Coord(5,2), 50 | "X":Coord(5,3), 51 | "Y":Coord(6,0), 52 | "Z":Coord(6,1)] 53 | 54 | func getDirections(for word: String) -> [String] { 55 | let word = word.uppercased() 56 | var directions = [String]() 57 | var currentPosition: Coord = startingPosition 58 | for letter in word { 59 | directions.append(getDirection(to: letter, with: currentPosition)) 60 | if let position = coords[letter] { 61 | currentPosition = position 62 | } 63 | } 64 | return directions 65 | } 66 | 67 | func getDirection(to letter: Character, with currentPosition: Coord) -> String { 68 | guard let nextPosition = coords[letter] else { 69 | return "" 70 | } 71 | var direction = "" 72 | let rowDiff = currentPosition.row - nextPosition.row 73 | let colDiff = currentPosition.col - nextPosition.col 74 | 75 | if rowDiff > 0 { 76 | direction += String(repeating: "U", count: rowDiff) 77 | } else if rowDiff < 0 { 78 | direction += String(repeating: "D", count: rowDiff * -1) 79 | } 80 | if colDiff > 0 { 81 | direction += String(repeating: "L", count: colDiff) 82 | } else if colDiff < 0 { 83 | direction += String(repeating: "R", count: colDiff * -1) 84 | } 85 | return direction 86 | } 87 | 88 | getDirections(for: "DOG") 89 | -------------------------------------------------------------------------------- /BigO/Week 1 - Big O.playground/Pages/Day 1 - O(1), O(n), O(n^2).xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Big O Day 1 - O(1)-Constant, O(n)-Linear, O(n^2)-Quadratic 2 | 3 | 4 | // Constant Time 5 | // O(1) 6 | // O(6) == O(1) 7 | 8 | var array: [Int] = [1,2,3,4,5,6,7,8,9,10] 9 | 10 | func constantLoop() { 11 | for i in 0...5 { 12 | print(array[i]) 13 | } 14 | } 15 | 16 | constantLoop() 17 | 18 | 19 | // O(n) 20 | func linearLoop(_ array: [Int]) { 21 | // Print Each Element 22 | for a in array { 23 | print(a) 24 | } 25 | } 26 | 27 | linearLoop(array) 28 | 29 | // O(n^2) 30 | func quadraticLoop(_ array: [Int]) { 31 | // Prints pairs 32 | for a in array { 33 | for b in array { 34 | print("\(a), \(b)") 35 | } 36 | } 37 | } 38 | 39 | quadraticLoop(array) 40 | 41 | // Adding big O together 42 | // O(n + n) = O(2n) = O(n) 43 | func linearLoop(_array: [Int]) { 44 | for i in array { 45 | print(i) 46 | } 47 | // + 48 | for i in array { 49 | print(i) 50 | } 51 | } 52 | 53 | // Adding Quadratic Loops 54 | // Below example is O(n^2)+(n^2) == O2(n^2) 55 | func doubledQuadraticLoop(_ array: [Int]) { 56 | for i in array { 57 | // * 58 | for j in array { 59 | print("\(i)\(j)") 60 | } 61 | } 62 | //+ 63 | for i in array { 64 | // * 65 | for j in array { 66 | print("\(i)\(j)") 67 | } 68 | } 69 | } 70 | 71 | // Gotcha with algorithms 72 | /// The average time for goodLinearSearch is better, however the order of growth is the same. O(n) 73 | 74 | func badLinearSearch(array: [Int], element: Int) -> Bool { 75 | var found = false 76 | for i in 0...array.count - 1 { 77 | if array[i] == element { 78 | found = true 79 | } 80 | } 81 | return found 82 | } 83 | 84 | 85 | 86 | func goodLinearSearch(array: [Int], element: Int) -> Bool { 87 | for i in array { 88 | if i == element { 89 | return true 90 | } 91 | } 92 | return false 93 | } 94 | 95 | 96 | 97 | // What is the Big O of the following funciton? 98 | // n((n*1) + (n*n)) 99 | 100 | // n((n*1) + (n*n)) starting point 101 | // n(n + n^2) step 2 102 | // n^2 + n^3 final reduction 103 | 104 | 105 | // Simplifying Big O 106 | 107 | // O(n/2) == O(n) 108 | 109 | 110 | func printHalfOfArray(array: [Int]) { 111 | for value in array where value < array.count/2 { 112 | print(value) 113 | } 114 | } 115 | 116 | 117 | 118 | // How far can we simplify? 119 | 120 | var posts: [Int] = [1,2,3,4,5,6,7,8,9,10] 121 | var comments: [Int] = [1,2,3,4,5,6] 122 | 123 | // O(pc) 124 | 125 | 126 | for post in posts { 127 | for comment in comments { 128 | print("\(post)\(comment)") 129 | } 130 | } 131 | 132 | 133 | // O(p + c) 134 | 135 | 136 | for post in posts { 137 | print("\(post)") 138 | } 139 | for comment in comments { 140 | print("\(comment)") 141 | } 142 | 143 | 144 | 145 | //Examples 146 | 147 | func multiplyAllNumbersThrough(number: Int) { 148 | for i in 0.. { 9 | public var leftChild: BSTNode? 10 | public var value: T 11 | public var rightChild: BSTNode? 12 | 13 | public init(value: T, leftChild: BSTNode? = nil, rightChild: BSTNode? = nil){ 14 | self.value = value 15 | self.leftChild = leftChild 16 | self.rightChild = rightChild 17 | } 18 | } 19 | 20 | extension BSTNode: CustomStringConvertible { 21 | 22 | public var description: String { 23 | return diagram(for: self) 24 | } 25 | 26 | private func diagram(for node: BSTNode?, 27 | _ top: String = "", 28 | _ root: String = "", 29 | _ bottom: String = "") -> String { 30 | guard let node = node else { 31 | return root + "nil\n" 32 | } 33 | if node.leftChild == nil && node.rightChild == nil { 34 | return root + "\(node.value)\n" 35 | } 36 | return diagram(for: node.rightChild, top + " ", top + "┌──", top + "│ ") 37 | + root + "\(node.value)\n" 38 | + diagram(for: node.leftChild, bottom + "│ ", bottom + "└──", bottom + " ") 39 | } 40 | } 41 | 42 | public class BinarySearchTree { 43 | public private(set) var root: BSTNode? 44 | public init() {} 45 | 46 | public func insert(_ value: T){ 47 | guard let root = root else { 48 | let newNode = BSTNode(value: value) 49 | self.root = newNode 50 | return 51 | } 52 | self.insert(from: root, value: value) 53 | } 54 | 55 | private func insert(from node: BSTNode, value: T) { 56 | if value >= node.value { 57 | if let right = node.rightChild { 58 | insert(from: right, value: value) 59 | }else { 60 | let newNode = BSTNode(value: value) 61 | node.rightChild = newNode 62 | } 63 | }else { 64 | if let left = node.leftChild { 65 | insert(from: left, value: value) 66 | }else{ 67 | let newNode = BSTNode(value: value) 68 | node.leftChild = newNode 69 | } 70 | } 71 | } 72 | 73 | 74 | 75 | public func contains(value: T) -> Bool { 76 | guard let root = root else { return false } 77 | return search(for: value, from: root) 78 | } 79 | 80 | private func search(for value: T, from node: BSTNode) -> Bool { 81 | if value >= node.value { 82 | if let right = node.rightChild { 83 | return search(for: value, from: right) 84 | }else { 85 | return false 86 | } 87 | }else { 88 | if let left = node.leftChild { 89 | return search(for: value, from: left) 90 | }else { 91 | return false 92 | } 93 | } 94 | } 95 | } 96 | 97 | extension BinarySearchTree: CustomStringConvertible { 98 | public var description: String { 99 | return root?.description ?? "Empty Tree" 100 | } 101 | } 102 | 103 | let binarySearchTree = BinarySearchTree() 104 | 105 | for i in [17,32,45,2,4,43,12,11,4,16,23,7,3,98,20]{ 106 | binarySearchTree.insert(i) 107 | } 108 | print(binarySearchTree.description) 109 | //print(binarySearchTree.root?.value) 110 | //print(binarySearchTree.root?.rightChild?.value) 111 | //print(binarySearchTree.root?.leftChild?.value) 112 | -------------------------------------------------------------------------------- /DataStructures/DataStructures.playground/Pages/BinarySearchTree.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | import Foundation 2 | 3 | public struct BinarySearchTree { 4 | public private(set) var root: BinaryNode? 5 | public init() {} 6 | } 7 | 8 | extension BinarySearchTree: CustomStringConvertible { 9 | public var description: String { 10 | guard let root = root else { return "empty tree" } 11 | return String(describing: root) 12 | } 13 | } 14 | 15 | extension BinarySearchTree { 16 | 17 | public mutating func insert(_ value: Element) { 18 | root = insert(from: root, value: value) 19 | } 20 | 21 | private func insert(from node: BinaryNode?, value: Element) -> BinaryNode { 22 | guard let node = node else { 23 | return BinaryNode(value: value) 24 | } 25 | if value < node.value { 26 | node.leftChild = insert(from: node.leftChild, value: value) 27 | } else { 28 | node.rightChild = insert(from: node.rightChild, value: value) 29 | } 30 | return node 31 | } 32 | } 33 | 34 | extension BinarySearchTree { 35 | 36 | public func contains(_ value: Element) -> Bool { 37 | var current = root 38 | while let node = current { 39 | if node.value == value { 40 | return true 41 | } 42 | if value < node.value { 43 | current = node.leftChild 44 | } else { 45 | current = node.rightChild 46 | } 47 | } 48 | return false 49 | } 50 | } 51 | 52 | private extension BinaryNode { 53 | 54 | var min: BinaryNode { 55 | return leftChild?.min ?? self 56 | } 57 | } 58 | 59 | extension BinarySearchTree { 60 | 61 | public mutating func remove(_ value: Element) { 62 | root = remove(node: root, value: value) 63 | } 64 | 65 | private func remove(node: BinaryNode?, value: Element) -> BinaryNode? { 66 | guard let node = node else { 67 | return nil 68 | } 69 | if value == node.value { 70 | if node.leftChild == nil && node.rightChild == nil { 71 | return nil 72 | } 73 | if node.leftChild == nil { 74 | return node.rightChild 75 | } 76 | if node.rightChild == nil { 77 | return node.leftChild 78 | } 79 | node.value = node.rightChild!.min.value 80 | node.rightChild = remove(node: node.rightChild, value: node.value) 81 | } else if value < node.value { 82 | node.leftChild = remove(node: node.leftChild, value: value) 83 | } else { 84 | node.rightChild = remove(node: node.rightChild, value: value) 85 | } 86 | return node 87 | } 88 | } 89 | 90 | // MARK: - Example 91 | var exampleTree: BinarySearchTree { 92 | var bst = BinarySearchTree() 93 | bst.insert(3) 94 | bst.insert(1) 95 | bst.insert(4) 96 | bst.insert(0) 97 | bst.insert(2) 98 | bst.insert(5) 99 | return bst 100 | } 101 | 102 | print(exampleTree) 103 | if exampleTree.contains(5) { 104 | print("Found 5!") 105 | } else { 106 | print("Couldn't find 5") 107 | } 108 | 109 | var tree = exampleTree 110 | print("Tree before removal:") 111 | print(tree) 112 | tree.remove(3) 113 | print("Tree after removing root:") 114 | print(tree) 115 | -------------------------------------------------------------------------------- /DataStructures/Week 3 - Data Structures.playground/Pages/Advanced Binary Search Tree.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | import Foundation 2 | 3 | public struct BinarySearchTree { 4 | public private(set) var root: BinaryNode? 5 | public init() {} 6 | } 7 | 8 | extension BinarySearchTree: CustomStringConvertible { 9 | public var description: String { 10 | guard let root = root else { return "empty tree" } 11 | return String(describing: root) 12 | } 13 | } 14 | 15 | extension BinarySearchTree { 16 | 17 | public mutating func insert(_ value: Element) { 18 | root = insert(from: root, value: value) 19 | } 20 | 21 | private func insert(from node: BinaryNode?, value: Element) -> BinaryNode { 22 | guard let node = node else { 23 | return BinaryNode(value: value) 24 | } 25 | if value < node.value { 26 | node.leftChild = insert(from: node.leftChild, value: value) 27 | } else { 28 | node.rightChild = insert(from: node.rightChild, value: value) 29 | } 30 | return node 31 | } 32 | } 33 | 34 | extension BinarySearchTree { 35 | 36 | public func contains(_ value: Element) -> Bool { 37 | var current = root 38 | while let node = current { 39 | if node.value == value { 40 | return true 41 | } 42 | if value < node.value { 43 | current = node.leftChild 44 | } else { 45 | current = node.rightChild 46 | } 47 | } 48 | return false 49 | } 50 | } 51 | 52 | private extension BinaryNode { 53 | 54 | var min: BinaryNode { 55 | return leftChild?.min ?? self 56 | } 57 | } 58 | 59 | extension BinarySearchTree { 60 | 61 | public mutating func remove(_ value: Element) { 62 | root = remove(node: root, value: value) 63 | } 64 | 65 | private func remove(node: BinaryNode?, value: Element) -> BinaryNode? { 66 | guard let node = node else { 67 | return nil 68 | } 69 | if value == node.value { 70 | if node.leftChild == nil && node.rightChild == nil { 71 | return nil 72 | } 73 | if node.leftChild == nil { 74 | return node.rightChild 75 | } 76 | if node.rightChild == nil { 77 | return node.leftChild 78 | } 79 | node.value = node.rightChild!.min.value 80 | node.rightChild = remove(node: node.rightChild, value: node.value) 81 | } else if value < node.value { 82 | node.leftChild = remove(node: node.leftChild, value: value) 83 | } else { 84 | node.rightChild = remove(node: node.rightChild, value: value) 85 | } 86 | return node 87 | } 88 | } 89 | 90 | // MARK: - Example 91 | var exampleTree: BinarySearchTree { 92 | var bst = BinarySearchTree() 93 | bst.insert(3) 94 | bst.insert(1) 95 | bst.insert(4) 96 | bst.insert(0) 97 | bst.insert(2) 98 | bst.insert(5) 99 | return bst 100 | } 101 | 102 | print(exampleTree) 103 | if exampleTree.contains(5) { 104 | print("Found 5!") 105 | } else { 106 | print("Couldn't find 5") 107 | } 108 | 109 | var tree = exampleTree 110 | print("Tree before removal:") 111 | print(tree) 112 | tree.remove(3) 113 | print("Tree after removing root:") 114 | print(tree) 115 | -------------------------------------------------------------------------------- /DataStructures/Week 2 - Data Structures.playground/Pages/Day 2 - Queue, Priority Queue, Stack.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Week 2 - Day 2 - Arrays and Linked Lists 2 | 3 | 4 | // Queue 5 | // Properties: 6 | // First In - First Out: FIFO 7 | // This is a line of objects 8 | 9 | // Operations in a Queue 10 | // - enqueue() - add to the back of the line 11 | // - dequeue() - remove from the front of the line 12 | // - peek() 13 | 14 | public struct Queue { 15 | 16 | fileprivate var array = [T]() 17 | 18 | public var isEmpty: Bool { 19 | return array.isEmpty 20 | } 21 | 22 | public mutating func enqueueu(_ element: T) { 23 | array.append(element) 24 | } 25 | 26 | public mutating func dequeue() -> T? { 27 | if isEmpty { 28 | return nil 29 | } else { 30 | return array.removeFirst() 31 | } 32 | } 33 | 34 | public mutating func peek() -> T? { 35 | return array.first 36 | } 37 | } 38 | 39 | 40 | 41 | 42 | // Stack 43 | // Properties: 44 | // Last In - First Out: LIFO 45 | // This is a stack of objects 46 | 47 | // Operations in a Stack 48 | // - push() - add an element to the top of the stack 49 | // - pop() - remove and return the top element on the stack 50 | // - top() - returns the top element without removing it. 51 | 52 | //Simple Stack 53 | public struct SimpleStack { 54 | 55 | fileprivate var array = [T]() 56 | 57 | public var isEmpty: Bool { 58 | return array.isEmpty 59 | } 60 | 61 | public mutating func push(_ element: T) { 62 | array.append(element) 63 | } 64 | 65 | public mutating func pop() -> T? { 66 | if isEmpty { 67 | return nil 68 | } else { 69 | return array.removeLast() 70 | } 71 | } 72 | 73 | public mutating func top() -> T? { 74 | return array.last 75 | } 76 | } 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | //Dressed up Stack 85 | 86 | public struct Stack { 87 | private var storage: [Element] = [] 88 | public init() {} 89 | } 90 | 91 | extension Stack: CustomStringConvertible { 92 | public var description: String { 93 | let topDivider = "----top----\n" 94 | let bottomDivider = "\n-----------" 95 | 96 | let stackElements = storage 97 | .map { "\($0)" } 98 | .reversed() 99 | .joined(separator: "\n") 100 | 101 | return topDivider + stackElements + bottomDivider 102 | } 103 | // Initialization 104 | public init(_ elements: [Element]) { 105 | storage = elements 106 | } 107 | 108 | // CRUD 109 | public mutating func push(_ element: Element) { 110 | storage.append(element) 111 | } 112 | 113 | @discardableResult 114 | public mutating func pop() -> Element? { 115 | return storage.popLast() 116 | } 117 | 118 | public func peek() -> Element? { 119 | return storage.last 120 | } 121 | 122 | public var isEmpty: Bool { 123 | return peek() == nil 124 | } 125 | } 126 | 127 | extension Stack: ExpressibleByArrayLiteral { // Makes it so you can initialize a stack like you would an array 128 | public init(arrayLiteral elements: Element...) { 129 | storage = elements 130 | } 131 | } 132 | 133 | // MARK: - Example 134 | var stack: Stack = [1.0, 2.0, 3.0, 4.0] 135 | print(stack, "Before pop") 136 | stack.pop() 137 | print(stack, "After pop") 138 | -------------------------------------------------------------------------------- /DataStructures/DataStructures.playground/Pages/BasicBinarySearchTree (Teach this in Class).xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | import Foundation 2 | 3 | //MARK: - VIDEO LINKS 4 | //Conceptual Overview of a Basic Binary Search Tree: https://vimeo.com/320114007 5 | //Live Walkthrough of this Implementation: https://vimeo.com/devmountain/review/320111190/a55f511fa3 6 | 7 | public class BSTNode { 8 | public var leftChild: BSTNode? 9 | public var value: T 10 | public var rightChild: BSTNode? 11 | 12 | public init(value: T, leftChild: BSTNode? = nil, rightChild: BSTNode? = nil){ 13 | self.value = value 14 | self.leftChild = leftChild 15 | self.rightChild = rightChild 16 | } 17 | } 18 | 19 | extension BSTNode: CustomStringConvertible { 20 | 21 | public var description: String { 22 | return diagram(for: self) 23 | } 24 | 25 | private func diagram(for node: BSTNode?, 26 | _ top: String = "", 27 | _ root: String = "", 28 | _ bottom: String = "") -> String { 29 | guard let node = node else { 30 | return root + "nil\n" 31 | } 32 | if node.leftChild == nil && node.rightChild == nil { 33 | return root + "\(node.value)\n" 34 | } 35 | return diagram(for: node.rightChild, top + " ", top + "┌──", top + "│ ") 36 | + root + "\(node.value)\n" 37 | + diagram(for: node.leftChild, bottom + "│ ", bottom + "└──", bottom + " ") 38 | } 39 | } 40 | 41 | public class BinarySearchTree { 42 | public private(set) var root: BSTNode? 43 | public init() {} 44 | 45 | public func insert(_ value: T){ 46 | guard let root = root else { 47 | let newNode = BSTNode(value: value) 48 | self.root = newNode 49 | return 50 | } 51 | self.insert(from: root, value: value) 52 | } 53 | 54 | private func insert(from node: BSTNode, value: T) { 55 | if value >= node.value { 56 | if let right = node.rightChild { 57 | insert(from: right, value: value) 58 | }else { 59 | let newNode = BSTNode(value: value) 60 | node.rightChild = newNode 61 | } 62 | }else { 63 | if let left = node.leftChild { 64 | insert(from: left, value: value) 65 | }else{ 66 | let newNode = BSTNode(value: value) 67 | node.leftChild = newNode 68 | } 69 | } 70 | } 71 | 72 | 73 | 74 | public func contains(value: T) -> Bool { 75 | guard let root = root else { return false } 76 | return search(for: value, from: root) 77 | } 78 | 79 | private func search(for value: T, from node: BSTNode) -> Bool { 80 | if value >= node.value { 81 | if let right = node.rightChild { 82 | return search(for: value, from: right) 83 | }else { 84 | return false 85 | } 86 | }else { 87 | if let left = node.leftChild { 88 | return search(for: value, from: left) 89 | }else { 90 | return false 91 | } 92 | } 93 | } 94 | } 95 | 96 | extension BinarySearchTree: CustomStringConvertible { 97 | public var description: String { 98 | return root?.description ?? "Empty Tree" 99 | } 100 | } 101 | 102 | let binarySearchTree = BinarySearchTree() 103 | 104 | for i in [17,32,45,2,4,43,12,11,4,16,23,7,3,98,20]{ 105 | binarySearchTree.insert(i) 106 | } 107 | print(binarySearchTree.description) 108 | //print(binarySearchTree.root?.value) 109 | //print(binarySearchTree.root?.rightChild?.value) 110 | //print(binarySearchTree.root?.leftChild?.value) 111 | -------------------------------------------------------------------------------- /DataStructures/DataStructures.playground/Pages/Heaps.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | //: [Previous](@previous) 2 | import UIKit 3 | 4 | //MARK: - VIDEO LINKS 5 | //Conceptual Overview and live walkthrough of this implementation: https://vimeo.com/304967758 6 | 7 | 8 | class MinHeap{ 9 | //MARK: - Helpers 10 | 11 | private var theGoods: [T] = [] 12 | 13 | private func getLeftChildIndex(for parentIndex: Int) -> Int{ 14 | return 2 * parentIndex + 1 15 | } 16 | 17 | private func getRightChildIndex(for parentIndex: Int) -> Int{ 18 | return 2 * parentIndex + 2 19 | } 20 | 21 | private func getParentIndex(for childIndex: Int) -> Int{ 22 | return ((childIndex - 1)/2) 23 | } 24 | 25 | private func leftChild(for index: Int) -> T?{ 26 | let leftIndex = getLeftChildIndex(for: index) 27 | guard leftIndex < theGoods.count else { return nil } 28 | return theGoods[leftIndex] 29 | } 30 | 31 | private func rightChild(for index: Int) -> T?{ 32 | let rightIndex = getRightChildIndex(for: index) 33 | guard rightIndex < theGoods.count else { return nil } 34 | return theGoods[rightIndex] 35 | } 36 | 37 | private func parent(for index: Int) -> T{ 38 | return theGoods[getParentIndex(for: index)] 39 | } 40 | 41 | private func heapifyDown(from index: Int){ 42 | if let leftChild = leftChild(for: index){ 43 | var switchIndex: Int! 44 | if let rightChild = rightChild(for: index){ 45 | switchIndex = leftChild < rightChild ? getLeftChildIndex(for: index) : getRightChildIndex(for: index) 46 | }else { 47 | switchIndex = getLeftChildIndex(for: index) 48 | } 49 | heapifyDown(from: switchIndex) 50 | } 51 | } 52 | 53 | private func heapifyUp(from index: Int){ 54 | if parent(for: index) > theGoods[index]{ 55 | let parentIndex = getParentIndex(for: index) 56 | theGoods.swapAt(index, parentIndex) 57 | heapifyUp(from: parentIndex) 58 | } 59 | } 60 | 61 | private func printLevel(_ level: Int, totalItemCount: Int){ 62 | let numberOfElements = Int(pow(Double(level), 2)) 63 | let startingIndex = totalItemCount 64 | for i in startingIndex...startingIndex + numberOfElements{ 65 | guard i < theGoods.count - 1 else { return } 66 | print(theGoods[i], terminator: " ") 67 | } 68 | print("\n") 69 | printLevel(level+1, totalItemCount: totalItemCount + numberOfElements) 70 | } 71 | 72 | //MARK: - Public Data Structure Methods 73 | 74 | public func peek() -> T? { 75 | return theGoods.first 76 | } 77 | 78 | public func poll() -> T? { 79 | guard !theGoods.isEmpty else { return nil} 80 | let item = theGoods.first 81 | theGoods[0] = theGoods.remove(at: theGoods.count - 1) 82 | heapifyDown(from: 0) 83 | return item 84 | } 85 | 86 | public func add(aGood: T){ 87 | theGoods.append(aGood) 88 | heapifyUp(from: theGoods.count - 1) 89 | } 90 | 91 | public func printFormattedHeap(){ 92 | printLevel(0, totalItemCount: 0) 93 | } 94 | } 95 | 96 | let myHeap = MinHeap() 97 | myHeap.add(aGood: 2) 98 | let numbers = [2,4,5,7,8,12,1,4,54,7,65] 99 | let moreNumbers = [90,87,45,34,23,12,65,7,8,2,3,4,5,6,7,87] 100 | numbers.forEach{ myHeap.add(aGood: $0) } 101 | moreNumbers.forEach{ myHeap.add(aGood: $0) } 102 | myHeap.printFormattedHeap() 103 | 104 | -------------------------------------------------------------------------------- /DesignPatterns/DecoratorPattern.playground/Contents.swift: -------------------------------------------------------------------------------- 1 | import UIKit 2 | 3 | protocol Pizza: CustomStringConvertible { 4 | func getCost() -> Double 5 | func getDescription() -> String 6 | } 7 | 8 | // Base Class 9 | class PlainPizza: Pizza { 10 | func getCost() -> Double { 11 | return 4.0 12 | } 13 | 14 | func getDescription() -> String { 15 | return "Thin Dough" 16 | } 17 | 18 | var description: String { 19 | return "🍕 \(getDescription)\n💸 \(getCost())\n" 20 | } 21 | } 22 | 23 | 24 | // Decorator 25 | class ToppingsDecorator: Pizza { 26 | var description: String { 27 | return "🍕\(getDescription())\n💸 $\(getCost())\n" 28 | } 29 | 30 | private let decoratedPizza: Pizza 31 | 32 | required init(decoratedPizza: Pizza) { 33 | self.decoratedPizza = decoratedPizza 34 | } 35 | 36 | func getCost() -> Double { 37 | return decoratedPizza.getCost() 38 | } 39 | 40 | func getDescription() -> String { 41 | return decoratedPizza.getDescription() 42 | } 43 | 44 | } 45 | 46 | 47 | class Mozzarella: ToppingsDecorator { 48 | required init(decoratedPizza: Pizza) { 49 | super.init(decoratedPizza: decoratedPizza) 50 | } 51 | 52 | override func getCost() -> Double { 53 | return super.getCost() + 1.0 54 | } 55 | 56 | override func getDescription() -> String { 57 | return super.getDescription() + ", " + "Mozzarella" 58 | } 59 | } 60 | 61 | class TomatoSauce: ToppingsDecorator { 62 | override func getCost() -> Double { 63 | return super.getCost() + 0.50 64 | } 65 | 66 | override func getDescription() -> String { 67 | return super.getDescription() + ", " + "Tomato Sauce" 68 | } 69 | 70 | } 71 | 72 | // MARK: - EXAMPLE 73 | var myPizza: Pizza = PlainPizza() 74 | myPizza = TomatoSauce(decoratedPizza: Mozzarella(decoratedPizza: myPizza)) 75 | print(myPizza) 76 | 77 | var veganPizza: Pizza = PlainPizza() 78 | veganPizza = TomatoSauce(decoratedPizza: myPizza) 79 | print(veganPizza) 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | 92 | 93 | 94 | 95 | 96 | 97 | 98 | 99 | 100 | 101 | 102 | 103 | 104 | 105 | 106 | 107 | 108 | 109 | 110 | 111 | 112 | 113 | 114 | 115 | 116 | 117 | 118 | 119 | 120 | 121 | 122 | 123 | 124 | 125 | 126 | // Core Component 127 | protocol Character { 128 | func getHealth() -> Int 129 | } 130 | 131 | // Concrete Components 132 | struct Orc: Character { 133 | func getHealth() -> Int { 134 | return 10 135 | } 136 | } 137 | 138 | struct Elf: Character { 139 | func getHealth() -> Int { 140 | return 5 141 | } 142 | } 143 | 144 | // Decorator 145 | protocol CharacterType: Character { 146 | var base: Character { get } 147 | } 148 | 149 | // Concrete Decorators 150 | struct Warlord: CharacterType { 151 | 152 | let base: Character 153 | 154 | func getHealth() -> Int { 155 | return 50 + base.getHealth() 156 | } 157 | 158 | // New responsibility 159 | func battleCry() { 160 | print("RAWR") 161 | } 162 | } 163 | 164 | struct Epic: CharacterType { 165 | 166 | let base: Character 167 | 168 | func getHealth() -> Int { 169 | return 30 + base.getHealth() 170 | } 171 | } 172 | 173 | let orc = Orc() 174 | let orcWarlord = Warlord(base: orc) 175 | let epicOrcWarlord = Epic(base: orcWarlord) 176 | let doubleEpicOrcWarlord = Epic(base: epicOrcWarlord) 177 | let elf = Elf() 178 | let elfWarlord = Warlord(base: elf) 179 | print(elf.getHealth()) 180 | 181 | -------------------------------------------------------------------------------- /DesignPatterns/Week 5 - Design Patterns.playground/Pages/Day 4 - Abstract Factory Pattern.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Week 5 - Day 4 - Abstract Factory Pattern 2 | 3 | //VIDEO WALKTHROUGH: - https://vimeo.com/308815485 4 | 5 | // 1. The Abstract Factory Pattern 6 | // 2. The Problem - You have multiple versions of _________ that you need to create. 7 | 8 | // Porsche, Volkswagen, Audi 9 | 10 | protocol Car { 11 | func drive() 12 | } 13 | 14 | protocol AbstractSports: Car { 15 | 16 | } 17 | 18 | protocol AbstractSedan: Car { 19 | 20 | } 21 | 22 | class AudiSports: AbstractSports { 23 | func drive() { 24 | print("You're driving an Audi Sports Car") 25 | } 26 | } 27 | 28 | class AudiSedan: AbstractSedan { 29 | func drive() { 30 | print("You're driving an Audi Sedan") 31 | } 32 | } 33 | 34 | class VolkswagenSports: AbstractSports { 35 | func drive() { 36 | print("You're driving an Volkswagen Sports Car") 37 | } 38 | } 39 | 40 | class VolkswagenSedan: AbstractSedan { 41 | func drive() { 42 | print("You're driving an Volkswagen Sedan") 43 | } 44 | } 45 | 46 | class PorscheSports: AbstractSports { 47 | func drive() { 48 | print("You're driving an Porsche Sports Car") 49 | } 50 | } 51 | 52 | class PorscheSedan: AbstractSedan { 53 | func drive() { 54 | print("You're driving an Porsche Sedan") 55 | } 56 | } 57 | 58 | // Porsche, Volkswagen, Audi 59 | 60 | protocol AbstractCarFactory { 61 | func buildSport() -> AbstractSports 62 | func buildSedan() -> AbstractSedan 63 | } 64 | 65 | class AudiFactory: AbstractCarFactory { 66 | func buildSport() -> AbstractSports { 67 | return AudiSports() 68 | } 69 | func buildSedan() -> AbstractSedan { 70 | return AudiSedan() 71 | } 72 | } 73 | 74 | class VolkswagenFactory: AbstractCarFactory { 75 | func buildSport() -> AbstractSports { 76 | return VolkswagenSports() 77 | } 78 | func buildSedan() -> AbstractSedan { 79 | return VolkswagenSedan() 80 | } 81 | } 82 | 83 | class PorscheFactory: AbstractCarFactory { 84 | func buildSport() -> AbstractSports { 85 | return PorscheSports() 86 | } 87 | func buildSedan() -> AbstractSedan { 88 | return PorscheSedan() 89 | } 90 | } 91 | 92 | 93 | 94 | 95 | 96 | 97 | 98 | var carFactory: AbstractCarFactory = PorscheFactory() 99 | let sedan = carFactory.buildSedan() 100 | let sports = carFactory.buildSport() 101 | sedan.drive() 102 | sports.drive() 103 | carFactory = AudiFactory() 104 | let newSedan = carFactory.buildSedan() 105 | newSedan.drive() 106 | 107 | 108 | //class SuperCarFactory { 109 | // func buildSport() -> AbstractSports { 110 | // return AbstractSports() 111 | // } 112 | // func buildSedan() -> AbstractSedan { 113 | // return AbstractSedan() 114 | // } 115 | //} 116 | // 117 | //class AudiFactory: SuperCarFactory { 118 | // override func buildSport() -> AbstractSports { 119 | // return AudiSports() 120 | // } 121 | // func buildSedan() -> AbstractSedan { 122 | // return AudiSedan() 123 | // } 124 | //} 125 | // 126 | //class VolkswagenFactory: SuperCarFactory { 127 | // func buildSport() -> AbstractSports { 128 | // return VolkswagenSports() 129 | // } 130 | // func buildSedan() -> AbstractSedan { 131 | // return VolkswagenSedan() 132 | // } 133 | //} 134 | // 135 | //class PorscheFactory: SuperCarFactory { 136 | // func buildSport() -> AbstractSports { 137 | // return PorscheSports() 138 | // } 139 | // func buildSedan() -> AbstractSedan { 140 | // return PorscheSedan() 141 | // } 142 | //} 143 | -------------------------------------------------------------------------------- /DataStructures/Week 3 - Data Structures.playground/Pages/Day 2 - Heap, Trie.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Week 3 - Day 2 - Heap, Trie 2 | 3 | 4 | 5 | import Foundation 6 | // What is a Heap? 7 | // It's a tree where the root node is either the smallest or the largest element in the tree. 8 | 9 | // What is percolating? 10 | 11 | // When do you percolate up or down? 12 | // How efficient is a Heap? 13 | 14 | class MinHeap{ 15 | //MARK: - Helpers 16 | 17 | private var theGoods: [T] = [] 18 | 19 | private func getLeftChildIndex(for parentIndex: Int) -> Int{ 20 | return 2 * parentIndex + 1 21 | } 22 | 23 | private func getRightChildIndex(for parentIndex: Int) -> Int{ 24 | return 2 * parentIndex + 2 25 | } 26 | 27 | private func getParentIndex(for childIndex: Int) -> Int{ 28 | return ((childIndex - 1)/2) 29 | } 30 | 31 | private func leftChild(for index: Int) -> T?{ 32 | let leftIndex = getLeftChildIndex(for: index) 33 | guard leftIndex < theGoods.count else { return nil } 34 | return theGoods[leftIndex] 35 | } 36 | 37 | private func rightChild(for index: Int) -> T?{ 38 | let rightIndex = getRightChildIndex(for: index) 39 | guard rightIndex < theGoods.count else { return nil } 40 | return theGoods[rightIndex] 41 | } 42 | 43 | private func parent(for index: Int) -> T{ 44 | return theGoods[getParentIndex(for: index)] 45 | } 46 | 47 | private func heapifyDown(from index: Int){ 48 | if let leftChild = leftChild(for: index){ 49 | var switchIndex: Int! 50 | if let rightChild = rightChild(for: index){ 51 | switchIndex = leftChild < rightChild ? getLeftChildIndex(for: index) : getRightChildIndex(for: index) 52 | }else { 53 | switchIndex = getLeftChildIndex(for: index) 54 | } 55 | theGoods.swapAt(index, switchIndex) 56 | heapifyDown(from: switchIndex) 57 | } 58 | } 59 | 60 | private func heapifyUp(from index: Int){ 61 | if parent(for: index) > theGoods[index]{ 62 | let parentIndex = getParentIndex(for: index) 63 | theGoods.swapAt(index, parentIndex) 64 | heapifyUp(from: parentIndex) 65 | } 66 | } 67 | 68 | private func printLevel(_ level: Int, totalItemCount: Int, numberOfElements: Int){ 69 | let startingIndex = totalItemCount 70 | let endIndex = startingIndex + numberOfElements 71 | for i in startingIndex.. T? { 82 | return theGoods.first 83 | } 84 | 85 | public func poll() -> T? { 86 | guard !theGoods.isEmpty else { return nil} 87 | let item = theGoods.first 88 | theGoods[0] = theGoods.remove(at: theGoods.count - 1) 89 | heapifyDown(from: 0) 90 | return item 91 | } 92 | 93 | public func add(aGood: T){ 94 | theGoods.append(aGood) 95 | heapifyUp(from: theGoods.count - 1) 96 | } 97 | 98 | public func printFormattedHeap(){ 99 | // print(theGoods[0]) 100 | printLevel(1, totalItemCount: 0, numberOfElements: 1) 101 | } 102 | } 103 | 104 | let myHeap = MinHeap() 105 | let numbers = [2,4,5,7,8,12,1,4,54,7,65] 106 | let moreNumbers = [90,87,45,34,23,12,65,7,8,2,3,4,5,6,7,87] 107 | numbers.forEach{ myHeap.add(aGood: $0) } 108 | moreNumbers.forEach{ myHeap.add(aGood: $0) } 109 | 110 | //myHeap.printFormattedHeap() 111 | myHeap.printFormattedHeap() 112 | 113 | // What is a Trie? 114 | // What is a Trie used for? 115 | 116 | //Please take a look at the "Tries" full XCode project in this repository for an implemenation 117 | 118 | // How efficient is looking up in a Trie? 119 | // How would you implement a Trie? 120 | -------------------------------------------------------------------------------- /DataStructures/Week 2 - Data Structures.playground/Pages/Day 1 - Arrays and Linked Lists.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Week 2 - Day 1 - Arrays and Linked Lists 2 | 3 | 4 | // Array 5 | 6 | // Properties 7 | // - Store an ORDERED list of items. 8 | // - Access the elements in the array in constant time. 9 | // - Amortization - Appending on the end is still constant time. 10 | 11 | 12 | 13 | // Linked List 14 | 15 | // Properties 16 | // - Stored an ORDERED list of items. 17 | // - But the location o 18 | 19 | let array: [Int] = [12, 45, 2, 21] 20 | 21 | for i in array { 22 | if i == 12 { 23 | print("found \(i)") 24 | } 25 | } 26 | 27 | public final class LinkedList { 28 | 29 | public class LinkedListNode { 30 | var value: T 31 | var next: LinkedListNode? 32 | 33 | public init(_ value: T) { 34 | self.value = value 35 | } 36 | } 37 | 38 | public typealias Node = LinkedListNode 39 | 40 | private var head: Node? 41 | private var tail: Node? 42 | var count: Int = 0 43 | 44 | public var isEmpty: Bool { 45 | return head == nil 46 | } 47 | 48 | public func append(_ value: T) { 49 | let newNode = Node(value) 50 | append(newNode) 51 | } 52 | 53 | public func append(_ node: Node) { 54 | let newNode = node 55 | if count == 0 { 56 | head = newNode 57 | tail = newNode 58 | } else { 59 | tail?.next = newNode 60 | tail = newNode 61 | } 62 | count += 1 63 | } 64 | 65 | public subscript(index: Int) -> T? { 66 | let node = self.node(at: index) 67 | return node?.value 68 | } 69 | 70 | public func node(at index: Int) -> Node? { 71 | assert(head != nil, "List is empty") 72 | assert(index >= 0, "index must be greater than 0") 73 | 74 | if index == 0 { 75 | return head! 76 | } else { 77 | var node = head!.next 78 | for _ in 1.. Int? { 90 | var index = 0 91 | var currNode = head 92 | while currNode !== head { 93 | index += 1 94 | if let next = currNode?.next { 95 | currNode = next 96 | } else { 97 | return nil 98 | } 99 | } 100 | return index 101 | } 102 | 103 | // Your assignment is to add the funcitonality to the insert and remove functions. 104 | public func insert(_ value: T, at index: Int) { 105 | let newNode = Node.init(value) 106 | insert(newNode, at: index) 107 | } 108 | 109 | public func insert(_ newNode: Node, at index: Int) { 110 | if index == 0 { 111 | newNode.next = head 112 | head = newNode 113 | } else if let prev = node(at: index - 1) { 114 | let next = prev.next 115 | newNode.next = next 116 | prev.next = newNode 117 | } 118 | } 119 | 120 | @discardableResult public func remove(node: Node) -> T? { 121 | guard let index = self.index(for: node) else { 122 | return nil 123 | } 124 | let prev = self.node(at: index - 1) 125 | let next = node.next 126 | 127 | if let prev = prev { 128 | prev.next = next 129 | } else { 130 | head = next 131 | } 132 | node.next = nil 133 | return node.value 134 | } 135 | 136 | } 137 | 138 | 139 | var practiceList = LinkedList() 140 | practiceList.append("Sally") 141 | practiceList[0] 142 | -------------------------------------------------------------------------------- /InterviewQuestions/Week 4 - Technical Interviews.playground/Pages/Day 4 - Interview Questions 4.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Week 4 - Day 4 - Technical Interviews 2 | 3 | 4 | // Stack Min - How would you design a stack which in addition to push and pop, has a function min() which 5 | // returns the minimum element? push(), pop() and min() should all operate in O(1) time. 6 | 7 | import DataStructure 8 | 9 | public class MinStack { 10 | private var mainStack: [T] 11 | private var minStack: [T] 12 | 13 | public init() { 14 | mainStack = .init() 15 | minStack = .init() 16 | } 17 | 18 | public func peek() -> T? { 19 | return mainStack.last 20 | } 21 | 22 | public func min() -> T? { 23 | return minStack.last 24 | } 25 | 26 | public func push(_ value: T) { 27 | mainStack.append(value) 28 | 29 | if !minStack.isEmpty && value > min()! { return } 30 | minStack.append(value) 31 | } 32 | 33 | public func pop() -> T? { 34 | guard !mainStack.isEmpty else { return nil } 35 | 36 | let lastValue = mainStack.removeLast() 37 | if lastValue == min() { 38 | minStack.removeLast() 39 | } 40 | return lastValue 41 | } 42 | } 43 | 44 | 45 | // Practice Questions and create the approach. 46 | 47 | // 1. String Compression - Write a function to perform basic string compression using the counts of reppeated 48 | // characters. For example, the string aabcccccaaa would become a2b1c5a3. If the compressed version of the 49 | // string is not smaller than the original string your method should return the original string. 50 | 51 | // 2. Check Balanced - Implement a function to check if a binary tree is balanced. For the purposes of this 52 | // question, a balanced tree is defined to be a tree such that the heights of the two subtrees of any node 53 | // never differ by more than one. 54 | 55 | // 3. Three in One - Describe how you could use a single array to implement three stacks. 56 | 57 | // 4. Rotate Matrix - Given an image represented by an NxN matrix, write a method to rotate the image by 90 degrees. 58 | // How would you do this in place? 59 | 60 | // 5. An animal shelter, which holds only dogs and cats operates on a strictly "first in, first out" basis. 61 | // People must adopt either the "oldest"(based on arrival time) of all the animals at the shelter, or they 62 | // can select whether they would prefer a dor or a cat (and will recieve the oldest animal of that type). 63 | // They cannot select which specific animal they would like. Create the data structures to maintain this 64 | // system and implement operations such as enqueue(), dequeueAny(), dequeueDog(), and dequeueCat(). 65 | // You may only use a LinkedList data structure. 66 | 67 | // 6. Remove Dups - Write code to remove duplicates from an unsorted linked list. 68 | 69 | // 7. Is Unique - Implement an algorithm to determine if a string has all unique characters. 70 | 71 | // 8. URLify - Write a funciton to replace all spaces in a string with "%20". How could you add additional 72 | // percent encodings? 73 | 74 | // 9. Route Between Nodes - Given a directed graph, design an algorithm to find out whether there is a route 75 | // between two nodes. 76 | 77 | // 10. Check Permutation - Given two strings, write a method to decide if one is a permutation of the other. 78 | 79 | // 11. Delete middle node - Implement an algorithm that deletes a node in the middle of a singly linked list, 80 | // given only access to that node. 81 | 82 | // 12. Return kth to Last - Implement an algorithm to find the kth to last element of a singly linked list. 83 | // How would you do this if you didn't have access to the size from the start? 84 | 85 | // 13. Minimal Tree - Given a sorted (increasing order) array with unique integer elements, write an algorithm 86 | // to create a binary search tree with minimal height. 87 | 88 | // 14. Validate BST - Implement a function to check if a binary tree is a binary seach tree. 89 | -------------------------------------------------------------------------------- /DataStructures/DataStructures.playground/Pages/LinkedList.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | import Foundation 2 | 3 | //MARK: - VIDEO LINKS 4 | //Conceptual Overview of a Linked List: https://vimeo.com/devmountain/review/320108637/f6ff990457 5 | //Live Walkthrough of implementation: https://vimeo.com/devmountain/review/320109169/c5e762c66f 6 | 7 | public class Node { 8 | public var value: Value 9 | public var next: Node? 10 | 11 | public init(value: Value, next: Node? = nil) { 12 | self.value = value 13 | self.next = next 14 | } 15 | } 16 | 17 | extension Node: CustomStringConvertible { 18 | public var description: String { 19 | guard let next = next else { 20 | return "\(value)" 21 | } 22 | return "\(value) -> " + String(describing: next) + " " 23 | } 24 | } 25 | 26 | public struct LinkedList { 27 | 28 | public var head: Node? 29 | public var tail: Node? 30 | 31 | public init() {} 32 | 33 | public var isEmpty: Bool { 34 | return head == nil 35 | } 36 | 37 | } 38 | 39 | extension LinkedList: CustomStringConvertible { 40 | public var description: String { 41 | guard let head = head else { 42 | return "Empty List" 43 | } 44 | return String(describing: head) 45 | } 46 | } 47 | 48 | 49 | // MARK: - Push, Append, Insert(after:) 50 | extension LinkedList { 51 | 52 | /// Pushes the value to the front of the list 53 | public mutating func push(_ value: Value) { 54 | head = Node(value: value, next: head) 55 | if tail == nil { 56 | tail = head 57 | } 58 | } 59 | 60 | /// Append the value to the tail of the list 61 | public mutating func append(_ value: Value) { 62 | // 1 63 | guard !isEmpty else { 64 | push(value) 65 | return 66 | } 67 | 68 | // 2 69 | tail!.next = Node(value: value) 70 | 71 | // 3 72 | tail = tail!.next 73 | } 74 | 75 | public func node(at index: Int) -> Node? { 76 | // 1 77 | var currentNode = head 78 | var currentIndex = 0 79 | 80 | // 2 81 | while currentNode != nil && currentIndex < index { 82 | currentNode = currentNode!.next 83 | currentIndex += 1 84 | } 85 | 86 | return currentNode 87 | } 88 | 89 | @discardableResult 90 | public mutating func insert(_ value: Value, 91 | after node: Node) -> Node { 92 | guard tail !== node else { 93 | append(value) 94 | return tail! 95 | } 96 | 97 | node.next = Node(value: value, next: node.next) 98 | return node.next! 99 | } 100 | 101 | @discardableResult 102 | public mutating func pop() -> Value? { 103 | defer { 104 | head = head?.next 105 | if isEmpty { 106 | tail = nil 107 | } 108 | } 109 | 110 | return head?.value 111 | } 112 | 113 | @discardableResult 114 | public mutating func removeLast() -> Value? { 115 | // 1 116 | guard let head = head else { 117 | return nil 118 | } 119 | // 2 120 | guard head.next != nil else { 121 | return pop() 122 | } 123 | // 3 124 | var prev = head 125 | var current = head 126 | 127 | while let next = current.next { 128 | prev = current 129 | current = next 130 | } 131 | // 4 132 | prev.next = nil 133 | tail = prev 134 | return current.value 135 | } 136 | } 137 | 138 | // MARK: - Example 139 | var list = LinkedList() 140 | list.push(3) 141 | list.push(2) 142 | list.push(1) 143 | 144 | print("Before popping list: \(list)") 145 | let poppedValue = list.pop() 146 | print("After popping list: \(list)") 147 | print("Popped value: " + String(describing: poppedValue)) 148 | 149 | -------------------------------------------------------------------------------- /DataStructures/Tries/Tries/Base.lproj/Main.storyboard: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # DevMountain CS 2 | 3 | ## What's the point? 4 | 5 | Computer Science is the basis for everything you've learned at DevMountain. There are two main purposes to this additional series of classes. The first purpose is to make sure you are the most prepared and able job candidates that you can be. Knowing these principles will help you perform betting in challenging interviews and will help you be more confident in all potential job oportunities. If you don't get a job, then it will be much harder to put into practice everything that you've learned here at DevMountain. The second purpose of this course is to make sure when you do get your dream job that you will be as well prepared as possible to make well designed and efficient code. The better you understand these concepts the more clearly you will be able to think about your program in general and over time writing well designed code will become natural and instinctive. By well designed code we mean that the code is easily reusable, testable and maintainable. 6 | 7 | 8 | # Learning Objectives 9 | 10 | ### Week 1 - Big O Notation 11 | 12 | * __Monday__ - Define what Big O is, Recognize O(n), O(1), O(n²) 13 | * __Tuesday__ - Define O(log n), O(2^n). Describe real life examples of O(n), O(1), O(n²) 14 | * __Wednesday__ - Apply Big O to previous stretch problems. Describe real like examples of O(log n), O(2^n) 15 | * __Thursday__ - Distinguish which Big O's are the fastest / most efficient. Distinguish between time and space complexity 16 | 17 | ### Week 2 - Data Structures Part 1 18 | 19 | * __Monday__ - Describe why data structures are useful in improving Big O. Distinguish between Array and Linked-List 20 | * __Tuesday__ - Create a Queue and a Stack using an Array or Linked-List. Be able to analyze Big O of each 21 | * __Wednesday__ - Compare and contrast Arrays vs Dictionaries. Describe 2 things you can do to avoid collisions 22 | * __Thursday__ - Define what a Tree is, difference types of Trees. Be able to recognize different typs of trees 23 | 24 | ### Week 3 - Data Structures Part 2 25 | 26 | * __Monday__ - Operate on a Binary Search Tree. Explain why a balance Binary Search Tree is desirable. Be able to analyze the Big O of a Binary Search Tree 27 | * __Tuesday__ - Define and explain when a heap is used and when a trie is used 28 | * __Wednesday__ - Describe what a Set is, and be able to operate on a Set 29 | * __Thursday__ - Define a Graph. Recognize a problem where Graphs may be needed 30 | 31 | ### Week 4 - Interview Questions 32 | 33 | * __Monday__ - Be able to list the steps for solving a technical question 34 | * __Tuesday__ - Explain what B.U.D. Optimization is, solve a technical question using the B.U.D. technique 35 | * __Wednesday__ - Explain what the D.I.Y. technique is, solve a technical question using the D.I.Y. technique. Do the same for Simplify and Generalize 36 | * __Thursday__ - Explain what the Base Case and Build technique is, solve a technical question using the Base Case and Build technique. Do the same with DataStructure Brainstorm 37 | 38 | ### Week 5 - Design Patterns Part 1 39 | 40 | * __Monday__ - Describe what problem Strategy Pattern solves, and how exactly it solves that problem 41 | * __Tuesday__ - Describe what problem Oberserver/Decorator pattern solves, and how exactly it solves that problem 42 | * __Wednesday__ - Describe what problem Factory Method solves, and how exactly it solves that problem 43 | * __Thursday__ - Describe what problem Abstract Factory Method solves, and how exactly it solves that problem. Be able to describe the difference between Factory Method and Abstract Factory Method 44 | 45 | ### Week 6 - Design Patterns Part 2 + Review 46 | 47 | * __Monday__ - Describe what problem Facade solves, and how exactly it solves that problem 48 | * __Tuesday__ - Describe what problem Proxy solves, and how exactly it solves that problem. Be able to describe the difference between Proxy and Facade Methods 49 | * __Wednesday__ - Describe the four steps of Object Oriented Design. be able to design a Deck of Cards data structure 50 | * __Thursday__ - Be ready to teach any given topic we've gone over 51 | . 52 | . 53 | . 54 | . 55 | . 56 | . 57 | . 58 | . 59 | . 60 | . 61 | . 62 | . 63 | . 64 | . 65 | . 66 | . 67 | . 68 | . 69 | . 70 | . 71 | . 72 | . 73 | . 74 | . 75 | . 76 | . 77 | . 78 | . 79 | . 80 | . 81 | . 82 | . 83 | . 84 | . 85 | . 86 | . 87 | . 88 | . 89 | . 90 | . 91 | . 92 | . 93 | . 94 | . 95 | . 96 | . 97 | . 98 | #### Week 1 - Big O 99 | 1. Day 1 - Simple definition. What is big O - O(1) & O(n) & O(n^2) - O(ab) - What is Big O? Why is it important? How do you simplify Big O? 100 | • https://www.youtube.com/watch?v=v4cd1O4zkGw <— Big O overview 101 | https://www.youtube.com/watch?v=MyeV2_tGqvw 102 | • https://www.youtube.com/watch?v=OMInLBKYAWg <— Linear Time 103 | • https://www.youtube.com/watch?v=1Md4Uo8LtHI <— Constant Time 104 | • https://www.youtube.com/watch?v=mIjuDg8ky4U <— Quadratic Time 105 | • https://www.youtube.com/watch?v=gHzZZYJENpo <— O(N)O(1) in Swift Brian Voong 106 | 2. Day 2 - O(log n) & O(2^n) - What is the difference between FRANK 107 | • https://www.youtube.com/watch?v=Hatl0qrT0bI <— Logarithmic Time 108 | • https://www.youtube.com/watch?v=Hatl0qrT0bI <— Exponential Time 109 | 3. Day 3 - O(n!) / O(sqrt(n)) / and other odd ones 110 | 4. Day 4 - Time vs. Space/ Practice 111 | • https://www.youtube.com/watch?v=bNjMFtHLioA <— Time vs. Space 112 | 113 | #### Week 2 - Data Structures Part 1 114 | 1. Day 1 - Arrays/Linked List 115 | • https://www.youtube.com/watch?v=_jQhALI4ujg <— Linked Lists 116 | • https://www.youtube.com/watch?v=jiHuPbUGlBE <— Short video on Linked Lists and Arrays 117 | 2. Day 2 - Queue/Priority Queue/Stack 118 | • https://www.youtube.com/watch?v=wjI1WNcIntg <— Queue / Stack 119 | 3. Day 3 - Dictionaries/ HashMap -> The two main ways of dealing with collisions // Chaining and linear Probing 120 | • https://www.youtube.com/watch?v=wjI1WNcIntg <— Hash/Hash Map/Collisions 121 | 4. Day 4 - Trees/Binary Trees -> Definitions, uses examples etc etc 122 | • https://www.youtube.com/watch?v=oSWTXtMglKE<— B.S.T. 123 | 124 | #### Week 3 - Data Structures Part 2 125 | 1. Day 5 - Binary Search Trees -> Definitions, uses examples etc etc 126 | • https://www.youtube.com/watch?v=oSWTXtMglKE<— B.S.T. 127 | 2. Day 6 - Heap/Trie -> Two different use cases for a tree - mention how heap is a great example of priority queue. 128 | 3. Day 7 - Set/Set Theory -> Set theory (Unions, ) 129 | 4. Day 8 - Graphs 130 | 131 | #### Week 4 - Practice Interview Questions 132 | 1. Day 1 - 133 | 2. Day 2 - 134 | 3. Day 3 - 135 | 4. Day 4 - 136 | 137 | #### Week 5 - Design Patterns 138 | 1. Day 1 - Strategy Pattern 139 | • https://www.youtube.com/watch?v=v9ejT8FO-7I 140 | 2. Day 2 - Observer Pattern/Decorator Pattern 141 | • https://www.youtube.com/watch?v=_BpmfnqjgzQ <— Observer Pattern 142 | • https://www.youtube.com/watch?v=GCraGHx6gso <— Decorator Pattern 143 | 3. Day 3 - Factory Method 144 | • https://www.youtube.com/watch?v=EcFVTgRHJLM 145 | 4. Day 4 - Abstract Factory 146 | • https://www.youtube.com/watch?v=v-GiuMmsXj4 147 | 148 | #### Week 6 - Design Patterns/ Design Practice 149 | 1. Day 1 - Facade 150 | • https://www.youtube.com/watch?v=K4FkHVO5iac 151 | 2. Day 2 - Proxy 152 | • https://www.youtube.com/watch?v=NwaabHqPHeM 153 | 3. Day 3 - Practice Design Interview Questions 154 | • https://courses.cs.washington.edu/courses/cse403/09sp/lectures/lecture07-uml.pdf <— This is an awesome slide show teaching UML 155 | 4. Day 4 - Review and Practice
 156 | 157 | -------------------------------------------------------------------------------- /DataStructures/Tries/Tries/ViewController.swift: -------------------------------------------------------------------------------- 1 | // 2 | // ViewController.swift 3 | // Tries 4 | // 5 | // Created by DevMountain on 10/23/18. 6 | // Copyright © 2018 trevorAdcock. All rights reserved. 7 | // 8 | 9 | import UIKit 10 | 11 | class ViewController: UIViewController { 12 | var autocompleter = Trie() 13 | var searchTerm: [String] = [] 14 | var saveSearchText: String = "" 15 | 16 | @IBOutlet weak var tableView: UITableView! 17 | @IBOutlet weak var autoCompleteSearchBar: UISearchBar! 18 | 19 | override func viewDidLoad() { 20 | super.viewDidLoad() 21 | autoCompleteSearchBar.delegate = self 22 | autocompleter.add(item: ["B","L","U","E"]) 23 | autocompleter.add(item: ["B","R","E", "A", "K"]) 24 | autocompleter.add(item: ["B","L","A","M","E"]) 25 | autocompleter.add(item: ["B","L","A","C","K"]) 26 | autocompleter.printAllNodes() 27 | // Do any additional setup after loading the view, typically from a nib. 28 | } 29 | } 30 | 31 | extension ViewController: UISearchBarDelegate{ 32 | 33 | 34 | 35 | func searchBar(_ searchBar: UISearchBar, textDidChange searchText: String) { 36 | var node: TrieNode! 37 | if searchText.count < saveSearchText.count{ 38 | node = autocompleter.currentNode.parent 39 | }else{ 40 | let searchString = String(searchText.last ?? "Z") 41 | let searchNode = TrieNode(value: searchString) 42 | node = autocompleter.findChild(from: autocompleter.currentNode, searchNode: searchNode) 43 | } 44 | saveSearchText = searchText 45 | autocompleter.moveCurrentTo(node: node) 46 | } 47 | } 48 | 49 | import Foundation 50 | 51 | public protocol Queue { 52 | associatedtype Element 53 | mutating func enqueue(_ element: Element) -> Bool 54 | mutating func dequeue() -> Element? 55 | var isEmpty: Bool { get } 56 | var peek: Element? { get } 57 | } 58 | 59 | public struct QueueArray: Queue { 60 | 61 | private var array: [T] = [] 62 | public init() {} 63 | 64 | public var isEmpty: Bool { 65 | return array.isEmpty 66 | } 67 | 68 | public var peek: T? { 69 | return array.first 70 | } 71 | 72 | @discardableResult 73 | public mutating func enqueue(_ element: T) -> Bool { 74 | array.append(element) 75 | return true 76 | } 77 | 78 | @discardableResult 79 | public mutating func dequeue() -> T? { 80 | return isEmpty ? nil : array.removeFirst() 81 | } 82 | 83 | } 84 | 85 | extension QueueArray: CustomStringConvertible { 86 | public var description: String { 87 | return String(describing: array) 88 | } 89 | } 90 | 91 | 92 | class TrieNode { 93 | 94 | var value: T? 95 | var children: [TrieNode] = [] 96 | var searched: Bool = false 97 | var parent: TrieNode? 98 | 99 | func forEachDepthFirst(visit: (TrieNode) -> Void){ 100 | visit(self) 101 | print("ForEachDepthFirst Currently at \(self.value)") 102 | self.children.forEach{ 103 | $0.forEachDepthFirst(visit: visit) 104 | } 105 | } 106 | 107 | init(value: T?){ 108 | self.value = value 109 | } 110 | } 111 | 112 | class Trie{ 113 | 114 | var rootNode: TrieNode = TrieNode(value: nil) 115 | var currentNode: TrieNode 116 | private var nodeQueue = QueueArray>() 117 | 118 | init(){ 119 | currentNode = rootNode 120 | } 121 | public func printAllNodes(){ 122 | rootNode.forEachDepthFirst { (node) in 123 | print(node.value ?? "Root Node") 124 | } 125 | } 126 | 127 | @discardableResult 128 | public func moveCurrentTo(node: TrieNode) -> TrieNode?{ 129 | if let childNode = findChild(from: currentNode, searchNode: node){ 130 | currentNode = childNode 131 | print(self.showCurrentPossiblities()) 132 | return childNode 133 | }else{ 134 | currentNode = node 135 | print(self.showCurrentPossiblities()) 136 | return nil 137 | } 138 | } 139 | 140 | var allValues: [[NodeValue]] = [] 141 | var values: [NodeValue] = [] 142 | var firstRecursion: Bool = true 143 | 144 | func goDeepOnNode(node: TrieNode){ 145 | if let value = node.value{ 146 | values.append(value) 147 | if let nextNode = findUnsearchedChildren(of: node){ 148 | firstRecursion = false 149 | goDeepOnNode(node: nextNode) 150 | } 151 | }else{ 152 | let valuesCopy = values.map{ $0 } 153 | allValues.append(valuesCopy) 154 | values = [] 155 | } 156 | } 157 | 158 | func findUnsearchedChildren(of node: TrieNode) -> TrieNode?{ 159 | for child in node.children{ 160 | if child.searched == false{ 161 | child.searched = true 162 | return child 163 | } 164 | } 165 | return nil 166 | } 167 | 168 | 169 | private func getPossibilities(for node: TrieNode) -> [[NodeValue]]{ 170 | var bigArray = [[NodeValue]]() 171 | var valuesArray: [NodeValue] = [] 172 | node.forEachDepthFirst { (node) in 173 | 174 | if node.value == nil{ 175 | guard node !== rootNode else { return } 176 | var hasParent = true 177 | var workingNode: TrieNode? = node 178 | 179 | while hasParent == true{ 180 | print("Has Parent is \(hasParent)") 181 | if let parentValue = workingNode?.parent?.value{ 182 | print("parent has a value of \(parentValue)") 183 | valuesArray.append(parentValue) 184 | workingNode = workingNode?.parent 185 | print("😯 Working Node moving up the tree. working node is now \(workingNode?.value)") 186 | }else{ 187 | let arrayCopy = Array(valuesArray.reversed()) 188 | print("copying values array: \(valuesArray) new array is \(arrayCopy)") 189 | bigArray.append(arrayCopy) 190 | print("appended. big array is now \(bigArray)") 191 | valuesArray = [] 192 | hasParent = false 193 | } 194 | } 195 | } 196 | } 197 | return bigArray 198 | } 199 | 200 | private func diveDeeper(from node: TrieNode, for searchNode: TrieNode){ 201 | print("Looking for \(searchNode.value) in children of \(node.value). the parent node has children \(node.children.map{ $0.value }))") 202 | if let child = findChild(from: node, searchNode: searchNode){ 203 | nodeQueue.dequeue() 204 | print("Child Found. Diving Deeper into NodeQueue. Next Node is \(nodeQueue.peek?.value)") 205 | guard let nextNode = nodeQueue.peek else {return} 206 | diveDeeper(from: child, for: nextNode) 207 | }else{ 208 | // guard let parentNode = nodeQueue.peek else {return} 209 | print("No Child Found. Contructing branch from \(nodeQueue.description)") 210 | createBranchFromCurrentNodeQueue() 211 | print("appending \(String(describing: searchNode.value)) with children \(searchNode.children.compactMap{ $0.value })) to parent node\(node.value)") 212 | node.children.append(searchNode) 213 | searchNode.parent = node 214 | } 215 | } 216 | 217 | public func add(item: [NodeValue]){ 218 | nodeQueue.enqueue(rootNode) 219 | item.forEach{ nodeQueue.enqueue(TrieNode(value: $0))} 220 | guard let firstNode = nodeQueue.dequeue(), 221 | let nextNode = nodeQueue.peek else {return} 222 | diveDeeper(from: firstNode, for: nextNode) 223 | } 224 | 225 | private func createBranchFromCurrentNodeQueue(){ 226 | print(nodeQueue.peek?.value ?? "Z") 227 | if let node = nodeQueue.dequeue(){ 228 | 229 | print(node.value) 230 | if let nextNode = nodeQueue.peek{ 231 | node.children.append(nextNode) 232 | nextNode.parent = node 233 | print("appending \(nextNode.value) to \(node.value)") 234 | createBranchFromCurrentNodeQueue() 235 | }else{ 236 | print("appending nil node to the end of \(node.value))") 237 | let terminator = TrieNode(value: nil) 238 | node.children.append(terminator) 239 | terminator.parent = node 240 | } 241 | } 242 | } 243 | 244 | public func showCurrentPossiblities() -> [[NodeValue]]{ 245 | return getPossibilities(for: currentNode) 246 | } 247 | 248 | func findChild(from parent: TrieNode, searchNode: TrieNode) -> TrieNode?{ 249 | for child in parent.children{ 250 | if child.value == searchNode.value{ 251 | return child 252 | } 253 | } 254 | return nil 255 | } 256 | } 257 | 258 | -------------------------------------------------------------------------------- /DataStructures/Week 2 - Data Structures.playground/Pages/Day 4 - Trees, Binary Trees.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Week 2 - Day 4 - Trees, Binary Trees 2 | 3 | // Trees 4 | 5 | // Definition 6 | 7 | // Trees must have 8 | // 1. A tree must have one root node which has zero or more child nodes. 9 | // 2. Every child node must have zero or more child nodes. 10 | 11 | // Trees cannot have 12 | // 1. Cycles 13 | 14 | // Trees may have 15 | // 1. Any type of value stored in the nodes. 16 | // 2. Can have any order in the node values. 17 | // 3. Any number of child nodes. 18 | // 4. Children nodes may or may not have links back to their parents. 19 | 20 | // What is the height of a tree? 21 | // What is a depth of a node? 22 | 23 | 24 | import Foundation 25 | 26 | //General Purpose Tree 27 | 28 | public class TreeNode { 29 | 30 | public var value: T 31 | public var children: [TreeNode] = [] 32 | 33 | public init(_ value: T) { 34 | self.value = value 35 | } 36 | 37 | public func add(_ child: TreeNode) { 38 | children.append(child) 39 | } 40 | } 41 | 42 | extension TreeNode { 43 | public func forEachDepthFirst(visit: (TreeNode) -> Void) { 44 | visit(self) 45 | children.forEach { 46 | $0.forEachDepthFirst(visit: visit) 47 | } 48 | } 49 | } 50 | 51 | extension TreeNode { 52 | public func forEachLevelOrder(visit: (TreeNode) -> Void) { 53 | visit(self) 54 | var queue = Queue() 55 | children.forEach { queue.enqueue($0) } 56 | while let node = queue.dequeue() { 57 | visit(node) 58 | node.children.forEach { queue.enqueue($0) } 59 | } 60 | } 61 | } 62 | 63 | extension TreeNode where T: Equatable { 64 | public func search(_ value: T) -> TreeNode? { 65 | var result: TreeNode? 66 | 67 | forEachDepthFirst { node in 68 | if node.value == value { 69 | result = node 70 | } 71 | } 72 | return result 73 | } 74 | } 75 | 76 | 77 | // MARK: - Example 78 | func makeBeverageTree() -> TreeNode { 79 | let tree = TreeNode("Beverages") 80 | 81 | let hot = TreeNode("hot") 82 | let cold = TreeNode("cold") 83 | 84 | let tea = TreeNode("tea") 85 | let coffee = TreeNode("coffee") 86 | let chocolate = TreeNode("cocoa") 87 | 88 | let blackTea = TreeNode("black") 89 | let greenTea = TreeNode("green") 90 | let chaiTea = TreeNode("chai") 91 | 92 | let soda = TreeNode("soda") 93 | let milk = TreeNode("milk") 94 | 95 | let gingerAle = TreeNode("ginger ale") 96 | let bitterLemon = TreeNode("bitter lemon") 97 | 98 | tree.add(hot) 99 | tree.add(cold) 100 | 101 | hot.add(tea) 102 | hot.add(coffee) 103 | hot.add(chocolate) 104 | 105 | cold.add(soda) 106 | cold.add(milk) 107 | 108 | tea.add(blackTea) 109 | tea.add(greenTea) 110 | tea.add(chaiTea) 111 | 112 | soda.add(gingerAle) 113 | soda.add(bitterLemon) 114 | 115 | return tree 116 | } 117 | 118 | let tree = makeBeverageTree() 119 | 120 | // Depth First 121 | tree.forEachDepthFirst { print($0.value) } 122 | 123 | // Level Order 124 | tree.forEachLevelOrder { print($0.value) } 125 | 126 | 127 | // Search 128 | if let searchResult1 = tree.search("ginger ale") { 129 | print("Found node: \(searchResult1.value)") 130 | } 131 | 132 | if let searchResult2 = tree.search("WKD Blue") { 133 | print(searchResult2.value) 134 | } else { 135 | print("Couldn't find WKD Blue") 136 | } 137 | 138 | // Types of Trees 139 | 140 | // 1. Binary Trees 141 | // Rules - Can have 0-2 children. 142 | 143 | // 2. Binary Search Tree 144 | // Rules - The left hand side must be less than the parent. 145 | // - The Right hand side must be more than the parent. 146 | 147 | // When is a tree Degenerate? 148 | // When is a tree Balanced? 149 | // When is a tree Complete? 150 | // When is a tree Full? 151 | // When is a tree Perfect? 152 | 153 | import Foundation 154 | 155 | public class BinaryNode { 156 | 157 | public var value: Element 158 | public var leftChild: BinaryNode? 159 | public var rightChild: BinaryNode? 160 | 161 | public init(value: Element) { 162 | self.value = value 163 | } 164 | } 165 | 166 | extension BinaryNode: CustomStringConvertible { 167 | 168 | public var description: String { 169 | return diagram(for: self) 170 | } 171 | 172 | private func diagram(for node: BinaryNode?, 173 | _ top: String = "", 174 | _ root: String = "", 175 | _ bottom: String = "") -> String { 176 | guard let node = node else { 177 | return root + "nil\n" 178 | } 179 | if node.leftChild == nil && node.rightChild == nil { 180 | return root + "\(node.value)\n" 181 | } 182 | return diagram(for: node.rightChild, top + " ", top + "┌──", top + "│ ") 183 | + root + "\(node.value)\n" 184 | + diagram(for: node.leftChild, bottom + "│ ", bottom + "└──", bottom + " ") 185 | } 186 | } 187 | 188 | extension BinaryNode { 189 | 190 | public func traverseInOrder(visit: (Element) -> Void) { 191 | leftChild?.traverseInOrder(visit: visit) 192 | visit(value) 193 | rightChild?.traverseInOrder(visit: visit) 194 | } 195 | 196 | public func traversePreOrder(visit: (Element) -> Void) { 197 | visit(value) 198 | leftChild?.traversePreOrder(visit: visit) 199 | rightChild?.traversePreOrder(visit: visit) 200 | } 201 | 202 | public func traversePostOrder(visit: (Element) -> Void) { 203 | leftChild?.traversePostOrder(visit: visit) 204 | rightChild?.traversePostOrder(visit: visit) 205 | visit(value) 206 | } 207 | } 208 | 209 | 210 | public struct BinarySearchTree { 211 | 212 | public private(set) var root: BinaryNode? 213 | public init() {} 214 | } 215 | 216 | extension BinarySearchTree: CustomStringConvertible { 217 | 218 | public var description: String { 219 | guard let root = root else { return "empty tree" } 220 | return String(describing: root) 221 | } 222 | } 223 | 224 | extension BinarySearchTree { 225 | 226 | public mutating func insert(_ value: Element) { 227 | root = insert(from: root, value: value) 228 | } 229 | 230 | private func insert(from node: BinaryNode?, value: Element) -> BinaryNode { 231 | guard let node = node else { 232 | return BinaryNode(value: value) 233 | } 234 | if value < node.value { 235 | node.leftChild = insert(from: node.leftChild, value: value) 236 | } else { 237 | node.rightChild = insert(from: node.rightChild, value: value) 238 | } 239 | return node 240 | } 241 | } 242 | 243 | extension BinarySearchTree { 244 | 245 | public func contains(_ value: Element) -> Bool { 246 | var current = root 247 | while let node = current { 248 | if node.value == value { 249 | return true 250 | } 251 | if value < node.value { 252 | current = node.leftChild 253 | } else { 254 | current = node.rightChild 255 | } 256 | } 257 | return false 258 | } 259 | } 260 | 261 | private extension BinaryNode { 262 | 263 | var min: BinaryNode { 264 | return leftChild?.min ?? self 265 | } 266 | } 267 | 268 | extension BinarySearchTree { 269 | 270 | public mutating func remove(_ value: Element) { 271 | root = remove(node: root, value: value) 272 | } 273 | 274 | private func remove(node: BinaryNode?, value: Element) -> BinaryNode? { 275 | guard let node = node else { 276 | return nil 277 | } 278 | if value == node.value { 279 | if node.leftChild == nil && node.rightChild == nil { 280 | return nil 281 | } 282 | if node.leftChild == nil { 283 | return node.rightChild 284 | } 285 | if node.rightChild == nil { 286 | return node.leftChild 287 | } 288 | node.value = node.rightChild!.min.value 289 | node.rightChild = remove(node: node.rightChild, value: node.value) 290 | } else if value < node.value { 291 | node.leftChild = remove(node: node.leftChild, value: value) 292 | } else { 293 | node.rightChild = remove(node: node.rightChild, value: value) 294 | } 295 | return node 296 | } 297 | } 298 | 299 | // MARK: - Example 300 | var exampleTree: BinarySearchTree { 301 | var bst = BinarySearchTree() 302 | bst.insert(3) 303 | bst.insert(1) 304 | bst.insert(4) 305 | bst.insert(0) 306 | bst.insert(2) 307 | bst.insert(5) 308 | return bst 309 | } 310 | 311 | // When is a tree Degenerate? 312 | // A tree where each node has only zero or one children. 313 | 314 | // When is a tree Balanced? 315 | // When the node count of the left side of the tree and the right side of the tree are roughly equal. 316 | 317 | // When is a tree Complete? 318 | // A tree is complete when all nodes are inserted as far left as possible and only when the current layer is full do they go to the new layer. 319 | 320 | // When is a tree Full? 321 | // A full tree is where all nodes either have zero or the max number of children possible. (For a Binary tree that's two) 322 | 323 | // When is a tree Perfect? 324 | // A perfect tree is where all leaf nodes have the same level, (or only differ by 1) (a complete tree is a type of perfect tree) 325 | 326 | 327 | 328 | // Can a BST have duplicate nodes? 329 | // Yes you have to change the way that the BST is organized though and it might add complexity to the tree. 330 | // (i.e. Linked list of duplicated at each node, or a left: <= while right: > rule.) 331 | exampleTree.description 332 | 333 | 334 | // Assignment 335 | // Make a Degenerate Tree 336 | BinarySearchTree.node(.empty, "0", BinaryNode.node(.empty, "1", BinaryTree.node(.empty, "2", BinaryTree.node(.empty, "3", .empty)))) 337 | // Make a Perfect Tree 338 | BinarySearchTree.node(BinaryTree.node(.empty, "2", .empty), "1", BinaryTree.node(.empty, "2", .empty)) 339 | // Make a Binary Seach Tree 340 | BinarySearchTree.node(BinaryTree.node(.empty, "0", .empty), "1", BinaryTree.node(.empty, "2", .empty)) 341 | 342 | exampleTree.contains(3) 343 | -------------------------------------------------------------------------------- /DataStructures/Tries/Tries.xcodeproj/project.pbxproj: -------------------------------------------------------------------------------- 1 | // !$*UTF8*$! 2 | { 3 | archiveVersion = 1; 4 | classes = { 5 | }; 6 | objectVersion = 50; 7 | objects = { 8 | 9 | /* Begin PBXBuildFile section */ 10 | F7A1B36B217FD70700C31CD2 /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = F7A1B36A217FD70700C31CD2 /* AppDelegate.swift */; }; 11 | F7A1B36D217FD70700C31CD2 /* ViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = F7A1B36C217FD70700C31CD2 /* ViewController.swift */; }; 12 | F7A1B370217FD70700C31CD2 /* Main.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = F7A1B36E217FD70700C31CD2 /* Main.storyboard */; }; 13 | F7A1B372217FD70900C31CD2 /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = F7A1B371217FD70900C31CD2 /* Assets.xcassets */; }; 14 | F7A1B375217FD70900C31CD2 /* LaunchScreen.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = F7A1B373217FD70900C31CD2 /* LaunchScreen.storyboard */; }; 15 | /* End PBXBuildFile section */ 16 | 17 | /* Begin PBXFileReference section */ 18 | F7A1B367217FD70700C31CD2 /* Tries.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = Tries.app; sourceTree = BUILT_PRODUCTS_DIR; }; 19 | F7A1B36A217FD70700C31CD2 /* AppDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = ""; }; 20 | F7A1B36C217FD70700C31CD2 /* ViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ViewController.swift; sourceTree = ""; }; 21 | F7A1B36F217FD70700C31CD2 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/Main.storyboard; sourceTree = ""; }; 22 | F7A1B371217FD70900C31CD2 /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = ""; }; 23 | F7A1B374217FD70900C31CD2 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/LaunchScreen.storyboard; sourceTree = ""; }; 24 | F7A1B376217FD70900C31CD2 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 25 | /* End PBXFileReference section */ 26 | 27 | /* Begin PBXFrameworksBuildPhase section */ 28 | F7A1B364217FD70700C31CD2 /* Frameworks */ = { 29 | isa = PBXFrameworksBuildPhase; 30 | buildActionMask = 2147483647; 31 | files = ( 32 | ); 33 | runOnlyForDeploymentPostprocessing = 0; 34 | }; 35 | /* End PBXFrameworksBuildPhase section */ 36 | 37 | /* Begin PBXGroup section */ 38 | F7A1B35E217FD70700C31CD2 = { 39 | isa = PBXGroup; 40 | children = ( 41 | F7A1B369217FD70700C31CD2 /* Tries */, 42 | F7A1B368217FD70700C31CD2 /* Products */, 43 | ); 44 | sourceTree = ""; 45 | }; 46 | F7A1B368217FD70700C31CD2 /* Products */ = { 47 | isa = PBXGroup; 48 | children = ( 49 | F7A1B367217FD70700C31CD2 /* Tries.app */, 50 | ); 51 | name = Products; 52 | sourceTree = ""; 53 | }; 54 | F7A1B369217FD70700C31CD2 /* Tries */ = { 55 | isa = PBXGroup; 56 | children = ( 57 | F7A1B36A217FD70700C31CD2 /* AppDelegate.swift */, 58 | F7A1B36C217FD70700C31CD2 /* ViewController.swift */, 59 | F7A1B36E217FD70700C31CD2 /* Main.storyboard */, 60 | F7A1B371217FD70900C31CD2 /* Assets.xcassets */, 61 | F7A1B373217FD70900C31CD2 /* LaunchScreen.storyboard */, 62 | F7A1B376217FD70900C31CD2 /* Info.plist */, 63 | ); 64 | path = Tries; 65 | sourceTree = ""; 66 | }; 67 | /* End PBXGroup section */ 68 | 69 | /* Begin PBXNativeTarget section */ 70 | F7A1B366217FD70700C31CD2 /* Tries */ = { 71 | isa = PBXNativeTarget; 72 | buildConfigurationList = F7A1B379217FD70900C31CD2 /* Build configuration list for PBXNativeTarget "Tries" */; 73 | buildPhases = ( 74 | F7A1B363217FD70700C31CD2 /* Sources */, 75 | F7A1B364217FD70700C31CD2 /* Frameworks */, 76 | F7A1B365217FD70700C31CD2 /* Resources */, 77 | ); 78 | buildRules = ( 79 | ); 80 | dependencies = ( 81 | ); 82 | name = Tries; 83 | productName = Tries; 84 | productReference = F7A1B367217FD70700C31CD2 /* Tries.app */; 85 | productType = "com.apple.product-type.application"; 86 | }; 87 | /* End PBXNativeTarget section */ 88 | 89 | /* Begin PBXProject section */ 90 | F7A1B35F217FD70700C31CD2 /* Project object */ = { 91 | isa = PBXProject; 92 | attributes = { 93 | LastSwiftUpdateCheck = 1000; 94 | LastUpgradeCheck = 1000; 95 | ORGANIZATIONNAME = trevorAdcock; 96 | TargetAttributes = { 97 | F7A1B366217FD70700C31CD2 = { 98 | CreatedOnToolsVersion = 10.0; 99 | }; 100 | }; 101 | }; 102 | buildConfigurationList = F7A1B362217FD70700C31CD2 /* Build configuration list for PBXProject "Tries" */; 103 | compatibilityVersion = "Xcode 9.3"; 104 | developmentRegion = en; 105 | hasScannedForEncodings = 0; 106 | knownRegions = ( 107 | en, 108 | Base, 109 | ); 110 | mainGroup = F7A1B35E217FD70700C31CD2; 111 | productRefGroup = F7A1B368217FD70700C31CD2 /* Products */; 112 | projectDirPath = ""; 113 | projectRoot = ""; 114 | targets = ( 115 | F7A1B366217FD70700C31CD2 /* Tries */, 116 | ); 117 | }; 118 | /* End PBXProject section */ 119 | 120 | /* Begin PBXResourcesBuildPhase section */ 121 | F7A1B365217FD70700C31CD2 /* Resources */ = { 122 | isa = PBXResourcesBuildPhase; 123 | buildActionMask = 2147483647; 124 | files = ( 125 | F7A1B375217FD70900C31CD2 /* LaunchScreen.storyboard in Resources */, 126 | F7A1B372217FD70900C31CD2 /* Assets.xcassets in Resources */, 127 | F7A1B370217FD70700C31CD2 /* Main.storyboard in Resources */, 128 | ); 129 | runOnlyForDeploymentPostprocessing = 0; 130 | }; 131 | /* End PBXResourcesBuildPhase section */ 132 | 133 | /* Begin PBXSourcesBuildPhase section */ 134 | F7A1B363217FD70700C31CD2 /* Sources */ = { 135 | isa = PBXSourcesBuildPhase; 136 | buildActionMask = 2147483647; 137 | files = ( 138 | F7A1B36D217FD70700C31CD2 /* ViewController.swift in Sources */, 139 | F7A1B36B217FD70700C31CD2 /* AppDelegate.swift in Sources */, 140 | ); 141 | runOnlyForDeploymentPostprocessing = 0; 142 | }; 143 | /* End PBXSourcesBuildPhase section */ 144 | 145 | /* Begin PBXVariantGroup section */ 146 | F7A1B36E217FD70700C31CD2 /* Main.storyboard */ = { 147 | isa = PBXVariantGroup; 148 | children = ( 149 | F7A1B36F217FD70700C31CD2 /* Base */, 150 | ); 151 | name = Main.storyboard; 152 | sourceTree = ""; 153 | }; 154 | F7A1B373217FD70900C31CD2 /* LaunchScreen.storyboard */ = { 155 | isa = PBXVariantGroup; 156 | children = ( 157 | F7A1B374217FD70900C31CD2 /* Base */, 158 | ); 159 | name = LaunchScreen.storyboard; 160 | sourceTree = ""; 161 | }; 162 | /* End PBXVariantGroup section */ 163 | 164 | /* Begin XCBuildConfiguration section */ 165 | F7A1B377217FD70900C31CD2 /* Debug */ = { 166 | isa = XCBuildConfiguration; 167 | buildSettings = { 168 | ALWAYS_SEARCH_USER_PATHS = NO; 169 | CLANG_ANALYZER_NONNULL = YES; 170 | CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; 171 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; 172 | CLANG_CXX_LIBRARY = "libc++"; 173 | CLANG_ENABLE_MODULES = YES; 174 | CLANG_ENABLE_OBJC_ARC = YES; 175 | CLANG_ENABLE_OBJC_WEAK = YES; 176 | CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; 177 | CLANG_WARN_BOOL_CONVERSION = YES; 178 | CLANG_WARN_COMMA = YES; 179 | CLANG_WARN_CONSTANT_CONVERSION = YES; 180 | CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; 181 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 182 | CLANG_WARN_DOCUMENTATION_COMMENTS = YES; 183 | CLANG_WARN_EMPTY_BODY = YES; 184 | CLANG_WARN_ENUM_CONVERSION = YES; 185 | CLANG_WARN_INFINITE_RECURSION = YES; 186 | CLANG_WARN_INT_CONVERSION = YES; 187 | CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; 188 | CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; 189 | CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; 190 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 191 | CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; 192 | CLANG_WARN_STRICT_PROTOTYPES = YES; 193 | CLANG_WARN_SUSPICIOUS_MOVE = YES; 194 | CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE; 195 | CLANG_WARN_UNREACHABLE_CODE = YES; 196 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 197 | CODE_SIGN_IDENTITY = "iPhone Developer"; 198 | COPY_PHASE_STRIP = NO; 199 | DEBUG_INFORMATION_FORMAT = dwarf; 200 | ENABLE_STRICT_OBJC_MSGSEND = YES; 201 | ENABLE_TESTABILITY = YES; 202 | GCC_C_LANGUAGE_STANDARD = gnu11; 203 | GCC_DYNAMIC_NO_PIC = NO; 204 | GCC_NO_COMMON_BLOCKS = YES; 205 | GCC_OPTIMIZATION_LEVEL = 0; 206 | GCC_PREPROCESSOR_DEFINITIONS = ( 207 | "DEBUG=1", 208 | "$(inherited)", 209 | ); 210 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 211 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 212 | GCC_WARN_UNDECLARED_SELECTOR = YES; 213 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 214 | GCC_WARN_UNUSED_FUNCTION = YES; 215 | GCC_WARN_UNUSED_VARIABLE = YES; 216 | IPHONEOS_DEPLOYMENT_TARGET = 12.0; 217 | MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE; 218 | MTL_FAST_MATH = YES; 219 | ONLY_ACTIVE_ARCH = YES; 220 | SDKROOT = iphoneos; 221 | SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG; 222 | SWIFT_OPTIMIZATION_LEVEL = "-Onone"; 223 | }; 224 | name = Debug; 225 | }; 226 | F7A1B378217FD70900C31CD2 /* Release */ = { 227 | isa = XCBuildConfiguration; 228 | buildSettings = { 229 | ALWAYS_SEARCH_USER_PATHS = NO; 230 | CLANG_ANALYZER_NONNULL = YES; 231 | CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE; 232 | CLANG_CXX_LANGUAGE_STANDARD = "gnu++14"; 233 | CLANG_CXX_LIBRARY = "libc++"; 234 | CLANG_ENABLE_MODULES = YES; 235 | CLANG_ENABLE_OBJC_ARC = YES; 236 | CLANG_ENABLE_OBJC_WEAK = YES; 237 | CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES; 238 | CLANG_WARN_BOOL_CONVERSION = YES; 239 | CLANG_WARN_COMMA = YES; 240 | CLANG_WARN_CONSTANT_CONVERSION = YES; 241 | CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; 242 | CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR; 243 | CLANG_WARN_DOCUMENTATION_COMMENTS = YES; 244 | CLANG_WARN_EMPTY_BODY = YES; 245 | CLANG_WARN_ENUM_CONVERSION = YES; 246 | CLANG_WARN_INFINITE_RECURSION = YES; 247 | CLANG_WARN_INT_CONVERSION = YES; 248 | CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES; 249 | CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; 250 | CLANG_WARN_OBJC_LITERAL_CONVERSION = YES; 251 | CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR; 252 | CLANG_WARN_RANGE_LOOP_ANALYSIS = YES; 253 | CLANG_WARN_STRICT_PROTOTYPES = YES; 254 | CLANG_WARN_SUSPICIOUS_MOVE = YES; 255 | CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE; 256 | CLANG_WARN_UNREACHABLE_CODE = YES; 257 | CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; 258 | CODE_SIGN_IDENTITY = "iPhone Developer"; 259 | COPY_PHASE_STRIP = NO; 260 | DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; 261 | ENABLE_NS_ASSERTIONS = NO; 262 | ENABLE_STRICT_OBJC_MSGSEND = YES; 263 | GCC_C_LANGUAGE_STANDARD = gnu11; 264 | GCC_NO_COMMON_BLOCKS = YES; 265 | GCC_WARN_64_TO_32_BIT_CONVERSION = YES; 266 | GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR; 267 | GCC_WARN_UNDECLARED_SELECTOR = YES; 268 | GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; 269 | GCC_WARN_UNUSED_FUNCTION = YES; 270 | GCC_WARN_UNUSED_VARIABLE = YES; 271 | IPHONEOS_DEPLOYMENT_TARGET = 12.0; 272 | MTL_ENABLE_DEBUG_INFO = NO; 273 | MTL_FAST_MATH = YES; 274 | SDKROOT = iphoneos; 275 | SWIFT_COMPILATION_MODE = wholemodule; 276 | SWIFT_OPTIMIZATION_LEVEL = "-O"; 277 | VALIDATE_PRODUCT = YES; 278 | }; 279 | name = Release; 280 | }; 281 | F7A1B37A217FD70900C31CD2 /* Debug */ = { 282 | isa = XCBuildConfiguration; 283 | buildSettings = { 284 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; 285 | CODE_SIGN_STYLE = Automatic; 286 | INFOPLIST_FILE = Tries/Info.plist; 287 | LD_RUNPATH_SEARCH_PATHS = ( 288 | "$(inherited)", 289 | "@executable_path/Frameworks", 290 | ); 291 | PRODUCT_BUNDLE_IDENTIFIER = com.trevoradcock.Tries; 292 | PRODUCT_NAME = "$(TARGET_NAME)"; 293 | SWIFT_VERSION = 4.2; 294 | TARGETED_DEVICE_FAMILY = "1,2"; 295 | }; 296 | name = Debug; 297 | }; 298 | F7A1B37B217FD70900C31CD2 /* Release */ = { 299 | isa = XCBuildConfiguration; 300 | buildSettings = { 301 | ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; 302 | CODE_SIGN_STYLE = Automatic; 303 | INFOPLIST_FILE = Tries/Info.plist; 304 | LD_RUNPATH_SEARCH_PATHS = ( 305 | "$(inherited)", 306 | "@executable_path/Frameworks", 307 | ); 308 | PRODUCT_BUNDLE_IDENTIFIER = com.trevoradcock.Tries; 309 | PRODUCT_NAME = "$(TARGET_NAME)"; 310 | SWIFT_VERSION = 4.2; 311 | TARGETED_DEVICE_FAMILY = "1,2"; 312 | }; 313 | name = Release; 314 | }; 315 | /* End XCBuildConfiguration section */ 316 | 317 | /* Begin XCConfigurationList section */ 318 | F7A1B362217FD70700C31CD2 /* Build configuration list for PBXProject "Tries" */ = { 319 | isa = XCConfigurationList; 320 | buildConfigurations = ( 321 | F7A1B377217FD70900C31CD2 /* Debug */, 322 | F7A1B378217FD70900C31CD2 /* Release */, 323 | ); 324 | defaultConfigurationIsVisible = 0; 325 | defaultConfigurationName = Release; 326 | }; 327 | F7A1B379217FD70900C31CD2 /* Build configuration list for PBXNativeTarget "Tries" */ = { 328 | isa = XCConfigurationList; 329 | buildConfigurations = ( 330 | F7A1B37A217FD70900C31CD2 /* Debug */, 331 | F7A1B37B217FD70900C31CD2 /* Release */, 332 | ); 333 | defaultConfigurationIsVisible = 0; 334 | defaultConfigurationName = Release; 335 | }; 336 | /* End XCConfigurationList section */ 337 | }; 338 | rootObject = F7A1B35F217FD70700C31CD2 /* Project object */; 339 | } 340 | -------------------------------------------------------------------------------- /DesignPatterns/Week 6 - Design Patterns.playground/Pages/Day 2 - Proxy Pattern.xcplaygroundpage/Contents.swift: -------------------------------------------------------------------------------- 1 | // Week 6 - Day 2 - Proxy Pattern 2 | 3 | //VIDEO WALKTHROUGH: - https://vimeo.com/308815767 4 | 5 | import Foundation 6 | 7 | // This is the interface that the concrete class and the proxy both implement. 8 | protocol IBookParser { 9 | func getWordCount() -> Int 10 | } 11 | 12 | // This is the concrete class that you want to add a proxy for. 13 | fileprivate class ConcreteBookParser: IBookParser { 14 | 15 | fileprivate var bookArray: [String] 16 | 17 | init(book: String) { 18 | let bookSequence = book.split(separator: " ") 19 | self.bookArray = bookSequence.compactMap{ String($0) } 20 | } 21 | 22 | fileprivate func getWordCount() -> Int { 23 | return bookArray.count 24 | } 25 | } 26 | 27 | // This is the proxy class which implements the interface and contains a concrete class. 28 | // The functions don't do the calculation they only run the proxy logic in the proxy functions then call the concrete class for the actual calculations. 29 | class LazyProxyBookParser: IBookParser { 30 | 31 | fileprivate var bookParser: ConcreteBookParser? 32 | var book: String 33 | 34 | init(book: String) { 35 | self.book = book 36 | } 37 | 38 | public func getWordCount() -> Int { 39 | if bookParser == nil { 40 | self.bookParser = ConcreteBookParser(book: book) 41 | } 42 | return self.bookParser!.getWordCount() 43 | } 44 | } 45 | 46 | let henryV = """ 47 | ACT I 48 | PROLOGUE 49 | Enter Chorus 50 | Chorus 51 | O for a Muse of fire, that would ascend 52 | The brightest heaven of invention, 53 | A kingdom for a stage, princes to act 54 | And monarchs to behold the swelling scene! 55 | Then should the warlike Harry, like himself, 56 | Assume the port of Mars; and at his heels, 57 | Leash'd in like hounds, should famine, sword and fire 58 | Crouch for employment. But pardon, and gentles all, 59 | The flat unraised spirits that have dared 60 | On this unworthy scaffold to bring forth 61 | So great an object: can this cockpit hold 62 | The vasty fields of France? or may we cram 63 | Within this wooden O the very casques 64 | That did affright the air at Agincourt? 65 | O, pardon! since a crooked figure may 66 | Attest in little place a million; 67 | And let us, ciphers to this great accompt, 68 | On your imaginary forces work. 69 | Suppose within the girdle of these walls 70 | Are now confined two mighty monarchies, 71 | Whose high upreared and abutting fronts 72 | The perilous narrow ocean parts asunder: 73 | Piece out our imperfections with your thoughts; 74 | Into a thousand parts divide on man, 75 | And make imaginary puissance; 76 | Think when we talk of horses, that you see them 77 | Printing their proud hoofs i' the receiving earth; 78 | For 'tis your thoughts that now must deck our kings, 79 | Carry them here and there; jumping o'er times, 80 | Turning the accomplishment of many years 81 | Into an hour-glass: for the which supply, 82 | Admit me Chorus to this history; 83 | Who prologue-like your humble patience pray, 84 | Gently to hear, kindly to judge, our play. 85 | Exit 86 | 87 | SCENE I. London. An ante-chamber in the KING'S palace. 88 | Enter the ARCHBISHOP OF CANTERBURY, and the BISHOP OF ELY 89 | CANTERBURY 90 | My lord, I'll tell you; that self bill is urged, 91 | Which in the eleventh year of the last king's reign 92 | Was like, and had indeed against us pass'd, 93 | But that the scambling and unquiet time 94 | Did push it out of farther question. 95 | ELY 96 | But how, my lord, shall we resist it now? 97 | CANTERBURY 98 | It must be thought on. If it pass against us, 99 | We lose the better half of our possession: 100 | For all the temporal lands which men devout 101 | By testament have given to the church 102 | Would they strip from us; being valued thus: 103 | As much as would maintain, to the king's honour, 104 | Full fifteen earls and fifteen hundred knights, 105 | Six thousand and two hundred good esquires; 106 | And, to relief of lazars and weak age, 107 | Of indigent faint souls past corporal toil. 108 | A hundred almshouses right well supplied; 109 | And to the coffers of the king beside, 110 | A thousand pounds by the year: thus runs the bill. 111 | ELY 112 | This would drink deep. 113 | CANTERBURY 114 | 'Twould drink the cup and all. 115 | ELY 116 | But what prevention? 117 | CANTERBURY 118 | The king is full of grace and fair regard. 119 | ELY 120 | And a true lover of the holy church. 121 | CANTERBURY 122 | The courses of his youth promised it not. 123 | The breath no sooner left his father's body, 124 | But that his wildness, mortified in him, 125 | Seem'd to die too; yea, at that very moment 126 | Consideration, like an angel, came 127 | And whipp'd the offending Adam out of him, 128 | Leaving his body as a paradise, 129 | To envelop and contain celestial spirits. 130 | Never was such a sudden scholar made; 131 | Never came reformation in a flood, 132 | With such a heady currance, scouring faults 133 | Nor never Hydra-headed wilfulness 134 | So soon did lose his seat and all at once 135 | As in this king. 136 | ELY 137 | We are blessed in the change. 138 | CANTERBURY 139 | Hear him but reason in divinity, 140 | And all-admiring with an inward wish 141 | You would desire the king were made a prelate: 142 | Hear him debate of commonwealth affairs, 143 | You would say it hath been all in all his study: 144 | List his discourse of war, and you shall hear 145 | A fearful battle render'd you in music: 146 | Turn him to any cause of policy, 147 | The Gordian knot of it he will unloose, 148 | Familiar as his garter: that, when he speaks, 149 | The air, a charter'd libertine, is still, 150 | And the mute wonder lurketh in men's ears, 151 | To steal his sweet and honey'd sentences; 152 | So that the art and practic part of life 153 | Must be the mistress to this theoric: 154 | Which is a wonder how his grace should glean it, 155 | Since his addiction was to courses vain, 156 | His companies unletter'd, rude and shallow, 157 | His hours fill'd up with riots, banquets, sports, 158 | And never noted in him any study, 159 | Any retirement, any sequestration 160 | From open haunts and popularity. 161 | ELY 162 | The strawberry grows underneath the nettle 163 | And wholesome berries thrive and ripen best 164 | Neighbour'd by fruit of baser quality: 165 | And so the prince obscured his contemplation 166 | Under the veil of wildness; which, no doubt, 167 | Grew like the summer grass, fastest by night, 168 | Unseen, yet crescive in his faculty. 169 | CANTERBURY 170 | It must be so; for miracles are ceased; 171 | And therefore we must needs admit the means 172 | How things are perfected. 173 | ELY 174 | But, my good lord, 175 | How now for mitigation of this bill 176 | Urged by the commons? Doth his majesty 177 | Incline to it, or no? 178 | CANTERBURY 179 | He seems indifferent, 180 | Or rather swaying more upon our part 181 | Than cherishing the exhibiters against us; 182 | For I have made an offer to his majesty, 183 | Upon our spiritual convocation 184 | And in regard of causes now in hand, 185 | Which I have open'd to his grace at large, 186 | As touching France, to give a greater sum 187 | Than ever at one time the clergy yet 188 | Did to his predecessors part withal. 189 | ELY 190 | How did this offer seem received, my lord? 191 | CANTERBURY 192 | With good acceptance of his majesty; 193 | Save that there was not time enough to hear, 194 | As I perceived his grace would fain have done, 195 | The severals and unhidden passages 196 | Of his true titles to some certain dukedoms 197 | And generally to the crown and seat of France 198 | Derived from Edward, his great-grandfather. 199 | ELY 200 | What was the impediment that broke this off? 201 | CANTERBURY 202 | The French ambassador upon that instant 203 | Craved audience; and the hour, I think, is come 204 | To give him hearing: is it four o'clock? 205 | ELY 206 | It is. 207 | CANTERBURY 208 | Then go we in, to know his embassy; 209 | Which I could with a ready guess declare, 210 | Before the Frenchman speak a word of it. 211 | ELY 212 | I'll wait upon you, and I long to hear it. 213 | Exeunt 214 | 215 | SCENE II. The same. The Presence chamber. 216 | Enter KING HENRY V, GLOUCESTER, BEDFORD, EXETER, WARWICK, WESTMORELAND, and Attendants 217 | KING HENRY V 218 | Where is my gracious Lord of Canterbury? 219 | EXETER 220 | Not here in presence. 221 | KING HENRY V 222 | Send for him, good uncle. 223 | WESTMORELAND 224 | Shall we call in the ambassador, my liege? 225 | KING HENRY V 226 | Not yet, my cousin: we would be resolved, 227 | Before we hear him, of some things of weight 228 | That task our thoughts, concerning us and France. 229 | Enter the ARCHBISHOP OF CANTERBURY, and the BISHOP of ELY 230 | 231 | CANTERBURY 232 | God and his angels guard your sacred throne 233 | And make you long become it! 234 | KING HENRY V 235 | Sure, we thank you. 236 | My learned lord, we pray you to proceed 237 | And justly and religiously unfold 238 | Why the law Salique that they have in France 239 | Or should, or should not, bar us in our claim: 240 | And God forbid, my dear and faithful lord, 241 | That you should fashion, wrest, or bow your reading, 242 | Or nicely charge your understanding soul 243 | With opening titles miscreate, whose right 244 | Suits not in native colours with the truth; 245 | For God doth know how many now in health 246 | Shall drop their blood in approbation 247 | Of what your reverence shall incite us to. 248 | Therefore take heed how you impawn our person, 249 | How you awake our sleeping sword of war: 250 | We charge you, in the name of God, take heed; 251 | For never two such kingdoms did contend 252 | Without much fall of blood; whose guiltless drops 253 | Are every one a woe, a sore complaint 254 | 'Gainst him whose wrong gives edge unto the swords 255 | That make such waste in brief mortality. 256 | Under this conjuration, speak, my lord; 257 | For we will hear, note and believe in heart 258 | That what you speak is in your conscience wash'd 259 | As pure as sin with baptism. 260 | CANTERBURY 261 | Then hear me, gracious sovereign, and you peers, 262 | That owe yourselves, your lives and services 263 | To this imperial throne. There is no bar 264 | To make against your highness' claim to France 265 | But this, which they produce from Pharamond, 266 | 'In terram Salicam mulieres ne succedant:' 267 | 'No woman shall succeed in Salique land:' 268 | Which Salique land the French unjustly gloze 269 | To be the realm of France, and Pharamond 270 | The founder of this law and female bar. 271 | Yet their own authors faithfully affirm 272 | That the land Salique is in Germany, 273 | Between the floods of Sala and of Elbe; 274 | Where Charles the Great, having subdued the Saxons, 275 | There left behind and settled certain French; 276 | Who, holding in disdain the German women 277 | For some dishonest manners of their life, 278 | Establish'd then this law; to wit, no female 279 | Should be inheritrix in Salique land: 280 | Which Salique, as I said, 'twixt Elbe and Sala, 281 | Is at this day in Germany call'd Meisen. 282 | Then doth it well appear that Salique law 283 | Was not devised for the realm of France: 284 | Nor did the French possess the Salique land 285 | Until four hundred one and twenty years 286 | After defunction of King Pharamond, 287 | Idly supposed the founder of this law; 288 | Who died within the year of our redemption 289 | Four hundred twenty-six; and Charles the Great 290 | Subdued the Saxons, and did seat the French 291 | Beyond the river Sala, in the year 292 | Eight hundred five. Besides, their writers say, 293 | King Pepin, which deposed Childeric, 294 | Did, as heir general, being descended 295 | Of Blithild, which was daughter to King Clothair, 296 | Make claim and title to the crown of France. 297 | Hugh Capet also, who usurped the crown 298 | Of Charles the duke of Lorraine, sole heir male 299 | Of the true line and stock of Charles the Great, 300 | To find his title with some shows of truth, 301 | 'Through, in pure truth, it was corrupt and naught, 302 | Convey'd himself as heir to the Lady Lingare, 303 | Daughter to Charlemain, who was the son 304 | To Lewis the emperor, and Lewis the son 305 | Of Charles the Great. Also King Lewis the Tenth, 306 | Who was sole heir to the usurper Capet, 307 | Could not keep quiet in his conscience, 308 | Wearing the crown of France, till satisfied 309 | That fair Queen Isabel, his grandmother, 310 | Was lineal of the Lady Ermengare, 311 | Daughter to Charles the foresaid duke of Lorraine: 312 | By the which marriage the line of Charles the Great 313 | Was re-united to the crown of France. 314 | So that, as clear as is the summer's sun. 315 | King Pepin's title and Hugh Capet's claim, 316 | King Lewis his satisfaction, all appear 317 | To hold in right and title of the female: 318 | So do the kings of France unto this day; 319 | Howbeit they would hold up this Salique law 320 | To bar your highness claiming from the female, 321 | And rather choose to hide them in a net 322 | Than amply to imbar their crooked titles 323 | Usurp'd from you and your progenitors. 324 | KING HENRY V 325 | May I with right and conscience make this claim? 326 | CANTERBURY 327 | The sin upon my head, dread sovereign! 328 | For in the book of Numbers is it writ, 329 | When the man dies, let the inheritance 330 | Descend unto the daughter. Gracious lord, 331 | Stand for your own; unwind your bloody flag; 332 | Look back into your mighty ancestors: 333 | Go, my dread lord, to your great-grandsire's tomb, 334 | From whom you claim; invoke his warlike spirit, 335 | And your great-uncle's, Edward the Black Prince, 336 | Who on the French ground play'd a tragedy, 337 | Making defeat on the full power of France, 338 | Whiles his most mighty father on a hill 339 | Stood smiling to behold his lion's whelp 340 | Forage in blood of French nobility. 341 | O noble English. that could entertain 342 | With half their forces the full Pride of France 343 | And let another half stand laughing by, 344 | All out of work and cold for action! 345 | ELY 346 | Awake remembrance of these valiant dead 347 | And with your puissant arm renew their feats: 348 | You are their heir; you sit upon their throne; 349 | The blood and courage that renowned them 350 | Runs in your veins; and my thrice-puissant liege 351 | Is in the very May-morn of his youth, 352 | Ripe for exploits and mighty enterprises. 353 | EXETER 354 | Your brother kings and monarchs of the earth 355 | Do all expect that you should rouse yourself, 356 | As did the former lions of your blood. 357 | WESTMORELAND 358 | They know your grace hath cause and means and might; 359 | So hath your highness; never king of England 360 | Had nobles richer and more loyal subjects, 361 | Whose hearts have left their bodies here in England 362 | And lie pavilion'd in the fields of France. 363 | CANTERBURY 364 | O, let their bodies follow, my dear liege, 365 | With blood and sword and fire to win your right; 366 | In aid whereof we of the spiritualty 367 | Will raise your highness such a mighty sum 368 | As never did the clergy at one time 369 | Bring in to any of your ancestors. 370 | KING HENRY V 371 | We must not only arm to invade the French, 372 | But lay down our proportions to defend 373 | Against the Scot, who will make road upon us 374 | With all advantages. 375 | CANTERBURY 376 | They of those marches, gracious sovereign, 377 | Shall be a wall sufficient to defend 378 | Our inland from the pilfering borderers. 379 | KING HENRY V 380 | We do not mean the coursing snatchers only, 381 | But fear the main intendment of the Scot, 382 | Who hath been still a giddy neighbour to us; 383 | For you shall read that my great-grandfather 384 | Never went with his forces into France 385 | But that the Scot on his unfurnish'd kingdom 386 | Came pouring, like the tide into a breach, 387 | With ample and brim fulness of his force, 388 | Galling the gleaned land with hot assays, 389 | Girding with grievous siege castles and towns; 390 | That England, being empty of defence, 391 | Hath shook and trembled at the ill neighbourhood. 392 | CANTERBURY 393 | She hath been then more fear'd than harm'd, my liege; 394 | For hear her but exampled by herself: 395 | When all her chivalry hath been in France 396 | And she a mourning widow of her nobles, 397 | She hath herself not only well defended 398 | But taken and impounded as a stray 399 | The King of Scots; whom she did send to France, 400 | To fill King Edward's fame with prisoner kings 401 | And make her chronicle as rich with praise 402 | As is the ooze and bottom of the sea 403 | With sunken wreck and sunless treasuries. 404 | WESTMORELAND 405 | But there's a saying very old and true, 406 | 'If that you will France win, 407 | Then with Scotland first begin:' 408 | For once the eagle England being in prey, 409 | To her unguarded nest the weasel Scot 410 | Comes sneaking and so sucks her princely eggs, 411 | Playing the mouse in absence of the cat, 412 | To tear and havoc more than she can eat. 413 | EXETER 414 | It follows then the cat must stay at home: 415 | Yet that is but a crush'd necessity, 416 | Since we have locks to safeguard necessaries, 417 | And pretty traps to catch the petty thieves. 418 | While that the armed hand doth fight abroad, 419 | The advised head defends itself at home; 420 | For government, though high and low and lower, 421 | Put into parts, doth keep in one consent, 422 | Congreeing in a full and natural close, 423 | Like music. 424 | CANTERBURY 425 | Therefore doth heaven divide 426 | The state of man in divers functions, 427 | Setting endeavour in continual motion; 428 | To which is fixed, as an aim or butt, 429 | Obedience: for so work the honey-bees, 430 | Creatures that by a rule in nature teach 431 | The act of order to a peopled kingdom. 432 | They have a king and officers of sorts; 433 | Where some, like magistrates, correct at home, 434 | Others, like merchants, venture trade abroad, 435 | Others, like soldiers, armed in their stings, 436 | Make boot upon the summer's velvet buds, 437 | Which pillage they with merry march bring home 438 | To the tent-royal of their emperor; 439 | Who, busied in his majesty, surveys 440 | The singing masons building roofs of gold, 441 | The civil citizens kneading up the honey, 442 | The poor mechanic porters crowding in 443 | Their heavy burdens at his narrow gate, 444 | The sad-eyed justice, with his surly hum, 445 | Delivering o'er to executors pale 446 | The lazy yawning drone. I this infer, 447 | That many things, having full reference 448 | To one consent, may work contrariously: 449 | As many arrows, loosed several ways, 450 | Come to one mark; as many ways meet in one town; 451 | As many fresh streams meet in one salt sea; 452 | As many lines close in the dial's centre; 453 | So may a thousand actions, once afoot. 454 | End in one purpose, and be all well borne 455 | Without defeat. Therefore to France, my liege. 456 | Divide your happy England into four; 457 | Whereof take you one quarter into France, 458 | And you withal shall make all Gallia shake. 459 | If we, with thrice such powers left at home, 460 | Cannot defend our own doors from the dog, 461 | Let us be worried and our nation lose 462 | The name of hardiness and policy. 463 | KING HENRY V 464 | Call in the messengers sent from the Dauphin. 465 | Exeunt some Attendants 466 | 467 | Now are we well resolved; and, by God's help, 468 | And yours, the noble sinews of our power, 469 | France being ours, we'll bend it to our awe, 470 | Or break it all to pieces: or there we'll sit, 471 | Ruling in large and ample empery 472 | O'er France and all her almost kingly dukedoms, 473 | Or lay these bones in an unworthy urn, 474 | Tombless, with no remembrance over them: 475 | Either our history shall with full mouth 476 | Speak freely of our acts, or else our grave, 477 | Like Turkish mute, shall have a tongueless mouth, 478 | Not worshipp'd with a waxen epitaph. 479 | Enter Ambassadors of France 480 | 481 | Now are we well prepared to know the pleasure 482 | Of our fair cousin Dauphin; for we hear 483 | Your greeting is from him, not from the king. 484 | First Ambassador 485 | May't please your majesty to give us leave 486 | Freely to render what we have in charge; 487 | Or shall we sparingly show you far off 488 | The Dauphin's meaning and our embassy? 489 | KING HENRY V 490 | We are no tyrant, but a Christian king; 491 | Unto whose grace our passion is as subject 492 | As are our wretches fetter'd in our prisons: 493 | Therefore with frank and with uncurbed plainness 494 | Tell us the Dauphin's mind. 495 | First Ambassador 496 | Thus, then, in few. 497 | Your highness, lately sending into France, 498 | Did claim some certain dukedoms, in the right 499 | Of your great predecessor, King Edward the Third. 500 | In answer of which claim, the prince our master 501 | Says that you savour too much of your youth, 502 | And bids you be advised there's nought in France 503 | That can be with a nimble galliard won; 504 | You cannot revel into dukedoms there. 505 | He therefore sends you, meeter for your spirit, 506 | This tun of treasure; and, in lieu of this, 507 | Desires you let the dukedoms that you claim 508 | Hear no more of you. This the Dauphin speaks. 509 | KING HENRY V 510 | What treasure, uncle? 511 | EXETER 512 | Tennis-balls, my liege. 513 | KING HENRY V 514 | We are glad the Dauphin is so pleasant with us; 515 | His present and your pains we thank you for: 516 | When we have march'd our rackets to these balls, 517 | We will, in France, by God's grace, play a set 518 | Shall strike his father's crown into the hazard. 519 | Tell him he hath made a match with such a wrangler 520 | That all the courts of France will be disturb'd 521 | With chaces. And we understand him well, 522 | How he comes o'er us with our wilder days, 523 | Not measuring what use we made of them. 524 | We never valued this poor seat of England; 525 | And therefore, living hence, did give ourself 526 | To barbarous licence; as 'tis ever common 527 | That men are merriest when they are from home. 528 | But tell the Dauphin I will keep my state, 529 | Be like a king and show my sail of greatness 530 | When I do rouse me in my throne of France: 531 | For that I have laid by my majesty 532 | And plodded like a man for working-days, 533 | But I will rise there with so full a glory 534 | That I will dazzle all the eyes of France, 535 | Yea, strike the Dauphin blind to look on us. 536 | And tell the pleasant prince this mock of his 537 | Hath turn'd his balls to gun-stones; and his soul 538 | Shall stand sore charged for the wasteful vengeance 539 | That shall fly with them: for many a thousand widows 540 | Shall this his mock mock out of their dear husbands; 541 | Mock mothers from their sons, mock castles down; 542 | And some are yet ungotten and unborn 543 | That shall have cause to curse the Dauphin's scorn. 544 | But this lies all within the will of God, 545 | To whom I do appeal; and in whose name 546 | Tell you the Dauphin I am coming on, 547 | To venge me as I may and to put forth 548 | My rightful hand in a well-hallow'd cause. 549 | So get you hence in peace; and tell the Dauphin 550 | His jest will savour but of shallow wit, 551 | When thousands weep more than did laugh at it. 552 | Convey them with safe conduct. Fare you well. 553 | Exeunt Ambassadors 554 | 555 | EXETER 556 | This was a merry message. 557 | KING HENRY V 558 | We hope to make the sender blush at it. 559 | Therefore, my lords, omit no happy hour 560 | That may give furtherance to our expedition; 561 | For we have now no thought in us but France, 562 | Save those to God, that run before our business. 563 | Therefore let our proportions for these wars 564 | Be soon collected and all things thought upon 565 | That may with reasonable swiftness add 566 | More feathers to our wings; for, God before, 567 | We'll chide this Dauphin at his father's door. 568 | Therefore let every man now task his thought, 569 | That this fair action may on foot be brought. 570 | Exeunt. Flourish 571 | """ 572 | 573 | 574 | let bookProxy = LazyProxyBookParser(book: henryV) 575 | bookProxy.getWordCount() 576 | bookProxy.getWordCount() 577 | --------------------------------------------------------------------------------