Closed reoxidant closed 2 years ago
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)")
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())")
not that topic in swift 1.0
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()
not that topic in swift 1.0
//Topic - Initializer Requirements
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())")
}
not that topic in swift 1.0
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()
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
not that topic in swift 1.0
//Topic - Adopting a Protocol Using a Synthesized Implementation
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())
}
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)
}
not that topic in swift 1.0
//Topic - Class-Only Protocols
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)
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")
}
}
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
not that topic in swift 1.0
//Topic - Protocol Extensions
Protocol Syntax - finish, was spent 1h
Red Section, Reading 3, Project 3.