funkcionális Swift: lezárások { }

forrás: Pexels

a bezárások a funkcionalitás önálló blokkjai, amelyeket át lehet adni és használni a kódban.

— Apple

a bezárások rögzíthetnek és tárolhatnak hivatkozásokat bármilyen állandóra és változóra abból a kontextusból, amelyben meghatározták őket, amelyet bezárásnak nevezünk. A bezárást úgy tekinthetjük, mint egy függvényt, amelynek nincs saját neve, és bármilyen értéket rögzít a környezetéből. A függvények és bezárások első osztályú objektumok a Swift – ben: tárolhatja őket, átadhatja őket argumentumként a függvényeknek, és úgy kezelheti őket, mint bármely más értéket vagy objektumot. A lezárások átadása befejezéskezelőként sok API-ban általános minta. A standard Swift könyvtár bezárásokat használ többnyire eseménykezeléshez és visszahívásokhoz.

a függvények önálló kóddarabok, amelyek egy adott feladatot hajtanak végre. A függvénynek nevet ad, amely azonosítja, hogy mit csinál, és ezt a nevet arra használja, hogy “hívja” a függvényt, hogy szükség esetén elvégezze a feladatát. A func kulcsszóval definiál egy függvényt. A függvények számos paraméterhez, variadikus paraméterekhez nem vezethetnek, és nem vagy több paramétert adhatnak vissza.

Function take 2 params and return 1 param

Function type

a Function type a paraméter típusokból és a függvény visszatérési típusából áll. A fenti példában a függvény típusa:(Int, Int) -> Int

ez így olvasható: “olyan függvény, amelynek két paramétere van, mindkettő Int típusú, és amely Inttípusú értéket ad vissza.”A funkció típusa paraméterként vagy visszatérési típusként állítható be.

Függvénytípusok bármely ilyen változóhoz rendelhetők:

var mathFunction: (Int, Int) -> Int = add

a funkciók a bezárások speciális esetei. A lezárások a három forma egyikét öltik:

  • globális függvények: van nevük, és nem tudnak értéket rögzíteni.
  • beágyazott függvények: van nevük, és értékeket rögzíthetnek a bezáró függvényükből.
  • bezárási kifejezések: nincs nevük, és értékeket rögzíthetnek a környezetükből.

Záró Kifejezés:

Swift záródokumentum

záródokumentum létrehozható úgy, hogy a visszatérési típus után egy függvénytípust helyezünk a göndör zárójelbe és a in kulcsszót.

a

zárási argumentumok hivatkozhatnak egy pozícióra, azaz. , , , és így tovább.

A gyorsírási Nevek megadása után nincs szükség lezárási argumentumok megadására, és a

kulcsszóban a bezárásból származó Implicit visszatérések:

az egy kifejezésű lezárások implicit módon visszaadhatják egyetlen kifejezésük eredményét a return kulcsszó elhagyásával a deklarációjukból.

többsoros kifejezés lezárása esetén a return kulcsszó nem hagyható ki.

Záró Lezárás:

ha a függvény utolsó argumentumaként át kell adni egy lezárási kifejezést egy függvénynek, és a lezárási kifejezés túl hosszú, akkor írható záró lezárásként. A záró lezárás a függvényhívás zárójelei () után íródik, annak ellenére, hogy ez még mindig a függvény argumentuma. Ha a záró Bezárás szintaxist használja, akkor nem írja meg a Bezárás argumentumcímkéjét a függvényhívás részeként.

lezárás mint érv a módszerhíváshoz

záró zárás (pl. lezárás a módszer zárójelei után)

ha a bezárás a módszer utolsó paramétere, akkor a swift lehetővé teszi, hogy így írjon 🖕

záró zárási példa a reduce használatával()

a záró zárási szintaxis használata szépen beágyazza a zárás funkcionalitását közvetlenül a zárás által támogatott funkció után, anélkül, hogy a teljes zárást be kellene tekerni a reduce(_:) módszer külső zárójelébe.

értékek rögzítése:

a lezárás konstansokat és változókat rögzíthet abból a környezetből, amelyben meg van határozva. A lezárás ezután hivatkozhat és módosíthatja ezen állandók és változók értékeit a testén belül, még akkor is, ha az eredeti hatókör, amely meghatározta az állandókat és változókat, már nem létezik.

a Swift-ben a Bezárás legegyszerűbb formája, amely képes rögzíteni az értékeket, egy beágyazott függvény, amelyet egy másik függvény törzsébe írnak. A beágyazott függvény rögzítheti a külső függvény argumentumait, és rögzítheti a külső függvényben definiált konstansokat és változókat is.

példa a Swift dokumentumban

ez a makeIncrementerfüggvény egy argumentumot fogad el, azaz Int bemenetként, és függvénytípust ad vissza, azaz () -> Int. Ez azt jelenti, hogy függvényt ad vissza, nem pedig egyszerű értéket. A visszaadott függvénynek nincsenek paraméterei, és minden híváskor Int értéket ad vissza.

itt amount argumentum, runningTotal változóként deklarálva és 0-val inicializálva. Beágyazott függvény incrementer rögzíti amount és runningTotal a környező kontextusban.

lássuk makeIncrementer működés közben:

Megjegyzés: Optimalizálásként a Swift ehelyett rögzíthet és tárolhat egy érték másolatát, ha az érték nem mutálódik egy bezárással, és ha az érték nem mutálódik a Bezárás létrehozása után.

a Swift kezeli az összes olyan memóriakezelést is, amely a változók megsemmisítésével jár, amikor már nincs rájuk szükség.

ahhoz, hogy megszabaduljon a hosszú lezárás kifejezés függvény argumentum használhatja typealias.

nem menekülő lezárások:

a lezárási paraméterek alapértelmezés szerint a Swift 3 előtt szöktek el. A lezárás nem kerülné el a függvénytestet, ha a bezárási paraméterek nem szökő

a Swift 3-ban meg lett fordítva. Amikor egy bezárást ad át függvény argumentumként, a Bezárás végrehajtásra kerül a függvény törzsével, és visszaadja a fordítót. Ahogy a végrehajtás véget ér, az átadott lezárás kiesik a hatókörből, és nincs többé a memóriában.

a legkevesebb, amit tudnod kell

a bezárási paraméterek alapértelmezés szerint nem menekülnek, ha el akarsz menekülni a Bezárás végrehajtásától, akkor a @escaping parancsot kell használnod a bezárási paraméterekkel.

a nem szökő záróelem életciklusa:
1. Adja át a bezárást függvény argumentumként a függvényhívás során.
2. Végezzen néhány munkát a funkcióban, majd hajtsa végre a bezárást.
3. Függvény visszatér.

a jobb memóriakezelésnek és optimalizálásnak köszönhetően a Swift az összes bezárást alapértelmezés szerint nem szökésre változtatta. CaptureList.swift egy példa a szökésmentes lezárásra.

megjegyzés: a @ non-Escape annotáció csak a

menekülési zárások függvénytípusaira vonatkozik:

azt mondják, hogy egy lezárás elkerüli a függvényt, amikor a lezárást argumentumként adják át a függvénynek, de a függvény visszatérése után hívják meg. A lezárás @escaping jelölése azt jelenti, hogy kifejezetten a self – re kell hivatkoznia a lezáráson belül.

a @menekülési lezárás életciklusa:
1. Adja át a bezárást függvény argumentumként a függvényhívás során.
2. Végezzen további munkát a funkcióban.
3. Funkció végre a lezárás aszinkron vagy tárolt.
4. Függvény visszatér.

lássuk, hol zárások alapértelmezés szerint menekülő:

  • a függvénytípus változói implicit módon menekülnek
  • a typealiases implicit módon menekülnek
  • az opcionális lezárások implicit módon menekülnek

gyakori hiba:

nem menekülő lezárás hozzárendelése a menekülő lezáráshoz. Vannak 2 ennek kijavításának módjai:

  • jelölje meg a lezárást menekülésként
  • vagy tartsa meg az alapértelmezett @noescape viselkedést a lezárás opcionális

Autoklasszik:

a Swift @autoclosure attribútuma lehetővé teszi egy argumentum meghatározását, amely automatikusan bezáródik. Nem vesz fel semmilyen érvet, és amikor meghívják, visszaadja a benne lévő kifejezés értékét. Ez a szintaktikai kényelem lehetővé teszi, hogy kihagyja a függvény paramétere körüli zárójeleket azáltal, hogy explicit lezárás helyett normál kifejezést ír.

például a assert(condition:message:file:line:) függvény autoklózt vesz fel condition és messageparamétereihez; condition paraméterét csak hibakeresési buildekben, message paraméterét pedig csak akkor értékeli ki, ha conditionfalse.

func assert(_ expression: @autoclosure () -> Bool,
_ message: @autoclosure () -> String) {}

a @autoclosure használata a @escaping attribútum szintaxisával:

@autoclosure @escaping () -> Bool

zárások vs blokkok:

“a Swift lezárások és az Objective-C blokkok kompatibilisek, így a Swift lezárásokat átadhatja az Objective-C módszereknek, amelyek blokkokat várnak el. A Swift lezárások és függvények azonos típusúak, így akár egy Swift függvény nevét is átadhatja. A bezárások hasonló rögzítési szemantikával rendelkeznek, mint a blokkok, de egy kulcsfontosságú módon különböznek egymástól: a változók változékonyak, nem pedig másolhatók. Más szavakkal, a _ _ blokk viselkedése az Objective-C-ben a változók alapértelmezett viselkedése a Swift-ben.”

bezárások vs küldöttek:

a megoldás a problémától függ. Sőt, az Apple a visszahívási mintára helyezi a hangsúlyt. UIAlertAction példa erre.

https://medium.com/@abhimuralidharan/functional-swift-all-about-closures-310bc8af31dd

https://medium.com/@kumarpramod017/what-do-mean-escaping-and-nonescaping-closures-in-swift-d404d721f39d

https://oleb.net/blog/2016/10/optional-non-escaping-closures/

https://swiftunboxed.com/lang/closures-escaping-noescape-swift3/

https://medium.com/@johnsundell/using-autoclosure-when-designing-swift-apis-67fe20a8b2e

Vélemény, hozzászólás?

Az e-mail-címet nem tesszük közzé.

Previous post Gondolatok a ló pajta Melegítőkről-Blackburn Architects, P. C.: Blackburn Architects, P. C.
Next post jótállás