reoxidant / practice-swift

Practice on writing code the swift language in apps, tests or something else
GNU General Public License v3.0
2 stars 1 forks source link

Protocols Documentation - finished section, miss - Initializer Requirements, Adopting a Protocol Using a Synthesized Implementation, Class-Only Protocols, Protocol Extensions #387

Closed reoxidant closed 2 years ago

reoxidant commented 3 years ago

Protocol Syntax - finish, was spent 1h

Red Section, Reading 3, Project 3.

//Topic - Protocol Syntax

//in example create a new Protocol

protocol SomeProtocol{

}

//in example create a expanded class for current protocol

class SomeClass:SomeProtocol{

}

//in example create class and his parent class and do inherince the parent class first and later inherince protocols 

class SuperSomeClass{

}

class ChildSomeClass:SuperSomeClass, SomeProtocol{

}
reoxidant commented 3 years ago

Property Requirements - finish, was spent 2h

Red Section, Reading 3, Project 3.

//Topic - Property Requirements

//in example create in Protocol stored property with can to get and set his value

protocol SomeProtocol{
    var propMustBeSettable:Int {get set}
    var propDoesNotBeNeedSettable: Int {get}
}

//in example define a required property in protocol use static key word

protocol AnotherProtocol{
    static var someTypeProperty: Int {get set}
}

//in example the protocol with one required property

protocol Human{
    var name: String{get}
}

//in example create struct with apply Protocol and define name as requirement property

struct Person:Human{
    var name:String
}

let person = Person(name:"Vitaliy")

print(person.name)

//in example create class with apply Protocol and define property fullName as counting property

class AnotherPerson:Human{
    var name:String
    var secondName:String
    var fullName:String{
        return "\(name) \(secondName)"
    }

    init(name:String, secondName:String){
        self.name = name
        self.secondName = secondName
    }
}

let secPerson = AnotherPerson(name:"Mary", secondName:"Sokolova")

print("The AnotherPerson fullname is \(secPerson.fullName)")
reoxidant commented 3 years ago

Method Requirements - finish, was spent 15 min

Red Section, Reading 3, Project 3.

//Topic - Method Requirements

//in example protoloc can be install func that return a Double value 

protocol SomeProtocol{
    static func someTypeMethod()
}

protocol RandomNumber{
    func random() -> Double
}

class GeneratorRandomNumber:RandomNumber{
    func random() -> Double{
        return Double.random(in: 0.0...1.0)
    }
}

let generator = GeneratorRandomNumber()

print("get a new double value \(generator.random()) fromn generator")

print("and another double value \(generator.random())")
reoxidant commented 3 years ago

not that topic in swift 1.0

Mutating Method Requirements - finish, was spent 30 min

Red Section, Reading 3, Project 3.

//Topic - Mutating Method Requirements

//in example realease protocol witch change state toggle methods by enum on calling self and any value for him

protocol Togglable{
    func toggle()
}

enum OnOffSwitch{
    case off, on
    func toggle(){
        switch self{
            case .off:
                self = .on
            case .on:
                self = .off
        }
    }
}

var lightSwitch = OnOffSwitch.off
lightSwitch.toggle()

enum HumanSex{
    case man, girl
    func toggle(){
        switch self{
            case .man:
                self = .girl
            case .girl:
                self = .man
        }
    }
}

var changeSex = HumanSex.man
changeSex.toggle()
reoxidant commented 3 years ago

not that topic in swift 1.0

//Topic - Initializer Requirements

reoxidant commented 3 years ago

Protocols as Types - finish, was spent 30 min

Red Section, Reading 3, Project 3.

//
// Created by vshapovalov on 15.02.2021.
//

import Foundation

//Topic - Protocols as Types

//in example protocol use it in that case as Type

//define protocols

protocol RandomNumber{
    func random() -> Double
}

class RandomNumberGenerator:RandomNumber{
    func random() -> Double{
        return Double.random(in: 0.0...1.0)
    }
}

/*
in example define
a Dice class which use type RandomNumberGenerator
for getting a random double value with range 0.0 to 0.1

just use construction generator.random() for calling a type of Protocols
*/

class Dice{
    let sides:Int
    let generator: RandomNumberGenerator

    init(sides:Int, generator: RandomNumberGenerator){
        self.sides = sides
        self.generator = generator
    }

    func roll() -> Int{
        return Int(generator.random() * Double(sides)) + 1
    }
}

let dice6 = Dice(sides: 6, generator: RandomNumberGenerator())

for _ in 1...5{
    print("The throw of game cube equal: \(dice6.roll())")
}
reoxidant commented 3 years ago

not that topic in swift 1.0

Delegation - finish, was spent 4h

Red Section, Reading 3, Project 3.

//Topic - Delegation

//in example protocol use it in that case as Type

//define protocols

protocol RandomNumber{
    func random() -> Double
}

class RandomNumberGenerator:RandomNumber{
    func random() -> Double{
        return Double.random(in: 0.0...1.0)
    }
}

/*
in example define
a Dice class which use type RandomNumberGenerator
for getting a random double value with range 0.0 to 0.1

just use construction generator.random() for calling a type of Protocols
*/

class Dice{
    let sides:Int
    let generator: RandomNumberGenerator

    init(sides:Int, generator: RandomNumberGenerator){
        self.sides = sides
        self.generator = generator
    }

    func roll() -> Int{
        return Int(generator.random() * Double(sides)) + 1
    }
}

let dice6 = Dice(sides: 6, generator: RandomNumberGenerator())

for _ in 1...5{
    print("The throw of game cube equal: \(dice6.roll())")
}

//in example define a protocol DiceGame it's define a core object game

protocol DiceGame {
    var dice: Dice { get }
    func play()
}

//in example define a protocol which manage a game

protocol DiceGameDelegate: AnyObject {
    func gameDidStart (_ game: DiceGame)
    func game(_ game: DiceGame, didStartNewTurnWithDiceRoll diceRoll:Int)
    func gameDidEnd(_ game: DiceGame)
}

//

class SnakesAndLadders: DiceGame{
    let finalSquare = 25
    //define a object dice
    let dice = Dice(sides: 6, generator: RandomNumberGenerator())
    var square = 0
    var board: [Int]

    //init board
    init(){
        board = Array(repeating: 0, count: finalSquare + 1)
        board[03] = +08; board[06] = +11; board[09] = +09; board[10] = +02
        board[14] = -10; board[19] = -11; board[22] = -02; board[24] = -08
    }

    //fix cycle delegate variable, optional for using
    weak var delegate: DiceGameDelegate?
    //a method play that's a main logic move by square
    func play() {
        square = 0
        delegate?.gameDidStart(self)
        gameLoop: while square != finalSquare {
            let diceRoll = dice.roll()
            delegate?.game(self, didStartNewTurnWithDiceRoll: diceRoll)
            switch square + diceRoll {
            case finalSquare:
                break gameLoop
            case let newSquare where newSquare > finalSquare:
                continue gameLoop
            default:
                square += diceRoll
                square += board[square]
            }
        }
        delegate?.gameDidEnd(self)
    }
}

//in example create tracker for dice game which track by protocol all state each game

class DiceGameTracker: DiceGameDelegate{
    //initialize variable which will be change by ending steps
    var numberOfTurns = 0
    func gameDidStart(_ game:DiceGame){
        //reset variable value to null
        numberOfTurns = 0
        if game is SnakesAndLadders{
            print("Start the new game")
        }
        //describe how many sides has a bone
        print("The played game of bone has a \(game.dice.sides) sides")
    }
    func game(_ game: DiceGame, didStartNewTurnWithDiceRoll diceRoll:Int)
    {
        //increase value of number turns
        numberOfTurns += 1
        print("Takeout \(diceRoll)")
    }
    func gameDidEnd(_ game:DiceGame){
        //print to console that the game is finish and how many complete steps will be
        print("A long game \(numberOfTurns) of steps")
    }
}

//decide to create a new

protocol RandomNumber{
    func randomAge() -> Double
}

protocol Human{
    var human: Man {get}
    func actionOnHuman()
}

protocol HumanCreatorDelegate: AnyObject{
    func startToCreate(_ human:Human)
    func defineAgeAHuman(_ human:Human,creatingAgeUseMethod defineAge:Int)
    func finishCreating(_ human:Human)
}

class RandomNumberGenerator : RandomNumber{
    func randomAge()->Double{
        return Double.random(in: 0.0...1.0)
    }
}

class Man{
    let generator: RandomNumberGenerator
    let name:String

    init(name:String, generator:RandomNumberGenerator){
        self.name = name
        self.generator = generator
    }

    func defineAge()->Int{
        return Int(generator.randomAge() * Double(100)) + 1
    }
}

class WorkHumanCreator:Human{
    var human = Man(name:"Masha", generator:RandomNumberGenerator())

    weak var delegate:HumanCreatorDelegate?

    func actionOnHuman(){
        let age = human.defineAge()
        delegate?.startToCreate(self)
        delegate?.defineAgeAHuman(self, creatingAgeUseMethod: age)
        delegate?.finishCreating(self)
    }
}

class TrackerHumanCreator:HumanCreatorDelegate{
    var mainStep = 0
    func startToCreate(_ human:Human){
        mainStep += 1

        if human is WorkHumanCreator{
            print("Create a new human")
        }

        print("The man is created with name \(human.human.name)")
    }
    func defineAgeAHuman(_ human:Human,creatingAgeUseMethod defineAge:Int){
        mainStep += 1

        print("Assign a new age \(defineAge)")
    }
    func finishCreating(_ human:Human){
        mainStep += 1

        print("End creating a man with \(mainStep) count step")
    }
}

var tracker = TrackerHumanCreator()
var man = WorkHumanCreator()
man.delegate = tracker
man.actionOnHuman()
reoxidant commented 3 years ago

Adding Protocol Conformance with an Extension - finish, was spent 2h

Red Section, Reading 3, Project 3.

//Topic - Adding Protocol Conformance with an Extension

//in example create protocol that show text which expand more any class that subscribe with him

protocol findNameOfBook  {
    var bookName: String { get }
}

protocol findNameOfFood{
    var foodName: String { get }
}

class Book{
    var name:String

    init(name:String){
        self.name = name
    }
}

class Food{
    var describe:String

    init(name:String){
        self.describe = name
    }
}

extension Book: findNameOfBook{
    var bookName: String{
        return "The name is book - \(self.name)"
    }
}

extension Food: findNameOfFood{
    var foodName: String{
        return "The name is food - \(self.describe)"
    }
}

let book = Book(name:"Black")

print(book.bookName)

let apple = Food(name:"Apple")
let banana = Food(name:"Banana")

print(apple.foodName)

//Subtopic - Conditionally Conforming to a Protocol

//in example we can expend the instance of Array add variable bookName and evaluating this value by protocol expect

extension Array: findNameOfFood where Element: findNameOfFood {
    var foodName: String {
        let name = self.map { $0.foodName }
        return "[" + name.joined(separator: ", ") + "]"
    }
}

let myStuff = [banana, apple]
print("The array protocols of findNameOfFood contains: \(myStuff.foodName)")

//Subtopic - Declaring Protocol Adoption with an Extension

//in example define a new class Hamster and adding to him a new protocol that not apply later when class has been initialize

protocol FindName {
    var description: String { get }
}

struct Cat{
    var name: String
    var description: String{
        return "The name of cat is \(name)"
    }
}

//now expend the cat object use FindName protocol

extension Cat: FindName {}

let cat = Cat(name:"Pushok")

//create a new instance class Cat and direct a protocol FindName

var newCat: FindName = cat
print(newCat.description)
//The name of cat is Pushok
reoxidant commented 3 years ago

not that topic in swift 1.0

//Topic - Adopting a Protocol Using a Synthesized Implementation

reoxidant commented 3 years ago

Collections of Protocol Types - finish, was spent 30 min

Red Section, Reading 3, Project 3.

//Topic - Collections of Protocol Types

//in example we can use protocols as types for array or dictionary

protocol DescribeObject{
    func describe()->String
}

class Human:DescribeObject{

    var name:String
    var age:Int
    var city:String
    var love:String

    init(name:String,age:Int,city:String,love:String){
        self.name = name
        self.age = age
        self.city = city
        self.love = love
    }

    func describe()->String{
        return "My name is \(name), i am \(age) old years, i live in \(city), i love \(love)"
    }
}

//create 4 humans class

var masha = Human(name:"Mary", age:24, city:"Noginsk", love:"drink coffee")
var ivan = Human(name:"Ivan", age:20, city:"Kolontaevo", love:"drink vodka")
var luba = Human(name:"Luba", age:45, city:"Kolontaevo", love:"her husband")
var ruslan = Human(name:"Ruslan", age:50, city:"Kolontaevo", love:"many eaten food")

var humansDescription:[DescribeObject] = [masha, ivan, luba, ruslan]

//enumerate all items of protocols and print a call his description method

for humanDesc in humansDescription{
    print(humanDesc.describe())
}
reoxidant commented 3 years ago

Protocol Inheritance - finish, was spent 1h 30 min

Red Section, Reading 3, Project 3.

//Topic Protocol Inheritance

//in example we can to inheritance on and more protocols syntax the same as classes and expend another protocols

protocol SomeProtocol{}

protocol AnotherProtocol{}

protocol InheritingProtocol: SomeProtocol, AnotherProtocol{
    //define protocols
}

protocol DescribeObject{
    func describe()->String
}

//in example we can to inheritance protocol from protocol and expand it

protocol PrettyTextRepresentable: DescribeObject {
    var prettyTextualDescription: String { get }
}

class Human: DescribeObject{
    var name:String
    var age:Int
    var city:String
    var love:String

    init(name:String,age:Int,city:String,love:String){
        self.name = name
        self.age = age
        self.city = city
        self.love = love
    }

    func describe()->String{
        return "My name is \(name), i am \(age) old years, i live in \(city), i love \(love)"
    }
}

//create extension for class Human where use protocol PrettyTextRepresentable and add realization of protocol

extension Human: PrettyTextRepresentable {
    var prettyTextualDescription:String{
        return "My name is \(name), i am \(age) old years, i live in \(city), i love \(love), i am pretty, yeah!!!"
    }
}

//create 4 humans class

var masha = Human(name:"Mary", age:24, city:"Noginsk", love:"drink coffee")
var ivan = Human(name:"Ivan", age:20, city:"Kolontaevo", love:"drink vodka")
var luba = Human(name:"Luba", age:45, city:"Kolontaevo", love:"her husband")
var ruslan = Human(name:"Ruslan", age:50, city:"Kolontaevo", love:"many eaten food")

var humansDescription:[PrettyTextRepresentable] = [masha, ivan, luba, ruslan]

//enumerate all items of protocols and print a call his description method

for humanDesc in humansDescription{
    //call new extension stored value from human class
    print(humanDesc.prettyTextualDescription)
}
reoxidant commented 3 years ago

not that topic in swift 1.0

//Topic - Class-Only Protocols

reoxidant commented 3 years ago

Protocol Composition - finish, was spent 1h 30 min

Red Section, Reading 3, Project 3.

//Topic Protocol Composition

//in example create composition as one big protocol which required realization from the class

protocol Named{
    var name: String { get }
}

protocol Aged{
    var age: Int { get }
}

struct Person: Named, Aged{
    var name: String
    var age: Int
}

//call the function where params expect a instance of class which used two protocols Named and Aged

func wishHappyBirthday(to celebration: Named & Aged){
    print("Happy Birthday, \(celebration.name) new you are age is \(celebration.age)!")
}
let birthdayPerson = Person(name: "Sasha", age: 21)
wishHappyBirthday(to: birthdayPerson)

// in example create Location class and merge with protocol Named create composition Location and Named together

class Location {
    var latitude: Double
    var longitude: Double
    init(latitude: Double, longitude: Double){
        self.latitude = latitude
        self.longitude = longitude
    }
}

// create class City which use two protocols

class City: Location, Named {
    var name: String
    init(name: String, latitude: Double, longitude: Double){
        self.name = name
        super.init(latitude: latitude, longitude: longitude)
    }
}

//call the function where params expect a instance of class which used two protocols Location and Named

func beginConcert(in location: Location & Named){
    print("Hello, \(location.name)")
}

let seattle = City(name: "Seattle", latitude: 47.6, longitude: -122.3)
beginConcert(in: seattle)

//create custom class use the same composition technology

class WeatherDescription{
    var tempValue: Int
    var duration: String
    init(tempValue:Int, duration:String){
        self.tempValue = tempValue
        self.duration = duration
    }
}

class Weather: WeatherDescription, Named{
    var name:String
    init(duration:String, tempValue:Int, name:String){
        self.name = name
        super.init(tempValue:tempValue, duration:duration)
    }
}

func describeWeather(in weather: WeatherDescription & Named ){
    print("It's a \(weather.name) duration more \(weather.duration) and have temperature value \(weather.tempValue)")
}

let winter = Weather(duration:"2 months", tempValue: -25, name:"Winter")
describeWeather(in: winter)
reoxidant commented 3 years ago

Checking for Protocol Conformance - finish, was spent 1h

Red Section, Reading 3, Project 3.

//Topic - Checking for Protocol Conformance

//in example create a protocol HasArea with stored prop area

protocol HasArea {
    var area: Double { get }
}

//create a two classes which equal requirement of protocol

class Circle: HasArea {
    let pi = 3.1415927
    var radius: Double
    //realization area variable of protocol use pi and radius value
    var area: Double { return pi * radius * radius}
    init(radius: Double) {self.radius = radius}
}

class Country: HasArea {
    //realization area variable of protocol just so
    var area: Double
    init (area: Double) {self.area = area}
}

class Animal {
    var legs: Int
    init(legs: Int) {self.legs = legs}
}

//all classes don't have a general class, but all from them can be stored in one array type of AnyObject

let objects: [AnyObject] = [
    //radius
    Circle(radius: 2.0),
    //area zone country
    Country(area: 243_610),
    //count legs
    Animal(legs:4)
]

//we can enumerate each value of array and provide all element to HasArea protocol

for object in objects{
    //use optional binding to unwrap result to objectWithArea variable result will be only area because it's protocol value and contains in all objects
    if let objectWithArea = object as? HasArea {
        print("Square equal \(objectWithArea.area)")
    } else {
        print("Has not a square")
    }
}
reoxidant commented 3 years ago

Optional Protocol Requirements - finish, was spent 2h

Red Section, Reading 3, Project 3.

//Topic - Optional Protocol Requirements

//in example create protocol, use optional value so define needed definition

//use @objc keyname for class not for structs and enumerations

//when u use a optional value for var or func them type automatic will be optional for example (Int) -> String will be ((int) -> String)?

//define class CounterDataSource

@objc protocol CounterDataSource{
    @objc optional func increment(forCount count: Int) -> Int
    @objc optional var fixedIncrement: Int { get }
}

//use CounterDataSource for chosen an equal value increment

//class Counter stored current value in variable count, func increment evaluate value count, call optional variable dataSource and use subfunction increment so return value and summing current count value each on self

class Counter{
    var count = 0
    var dataSource: CounterDataSource?
    func increment(){
        //can be throw down on increment, return optional value, unwrap to amount constant
        if let amount = dataSource?.increment?(forCount: count){
            count += amount
        } else if let amount = dataSource?.fixedIncrement {
            count += amount
        }
    }
}

//create class that realization protocol CounterDataSource
class ThreeSource: NSObject, CounterDataSource{
    //func increment optional we can may not to direct here
    let fixedIncrement = 3
}

//init class Counter and install CounterDataSource in variable dataSource
var counter = Counter()
counter.dataSource = ThreeSource()
for _ in 1...4{
    //count well be 0 therefore calling a fixedIncrement 4 times
    counter.increment()
    print(counter.count)
}

//3
//6
//9
//12

//in example create TowardsZeroSource class, which allow counting in more or small value of count

class TowardsZeroSource: NSObject, CounterDataSource {
//realize an optional protocol CounterDataSource func increment, if return 0, the counting not
    func increment(forCount count: Int) -> Int {
        //check count variable which will be returned only if u have positive variable
        if count == 0 {
            return 0
        } else if count < 0 {
            //count = -4
            //count = amount += 1
            return 1
        } else {
            return -1
        }
    }
}

//u can
var counterTZS = Counter()
counterTZS.count = -4
counterTZS.dataSource = TowardsZeroSource()

for _ in 1...5 {
    counter.increment()
    print(counter.count)
}

// -3
// -2
// -1
// 0
//now counter is zero
reoxidant commented 3 years ago

not that topic in swift 1.0

//Topic - Protocol Extensions