Pour ceux qui découvrent Swift et veulent se faire une idée de Combine. Voici un code simple.
Le but est de comprendre cela aujourd'hui! Tu n'as pas besoin de savoir. J'expliquerai plus tard. Ceux qui comprennent n'ont pas à le lire.
import Combine
let a = CurrentValueSubject<Int, Never>(3)
let b = Just(1)
let publisher = b.combineLatest(a).map{b,a in a + b}
publisher.sink{ added in
print(added)
}
a.send(10)
Je ne pense pas que cela ait vraiment de sens, mais qu'est-ce qui est susceptible d'être affiché dans la sortie standard (impression)?
La réponse est
4
11
Deux lignes s'affichent. Le premier «4» est «3 + 1» Le 11 suivant est "10 + 1".
Combiner l'importation
import Combine
Vous pouvez le faire avec. Disponible sur ** iOS 13 ** et supérieur.
Vous pouvez facilement l'essayer sur Playground.
Éditeur et abonné sont les termes dont il faut se souvenir pour le moment dans Combine.
Nom | Lecture japonaise | que faites-vous |
---|---|---|
Publisher | Éditeur | Publier des données |
Subscriber | Abonné | Abonnez-vous aux données |
Vous n'avez pas à le comprendre, alors mémorisez 2 mots pour le moment! Publisher, Subscriber
Just est (probablement) l'éditeur le plus simple.
Allons voir la définition pour le moment. (Extrait)
@available(macOS 10.15, iOS 13.0, tvOS 13.0, watchOS 6.0, *)
public struct Just<Output> : Publisher {
// ... (réduction)
}
Pour le moment, c'est un Publisher qui hérite du Publisher. Il semble être vrai qu'il ne peut être utilisé qu'avec iOS 13.0 ou supérieur.
Ce qui est écrit dans cette juste explication est
A publisher that emits an output to each subscriber just once, and then finishes.
De cette phrase, vous pouvez voir que:
N'oubliez pas que c'est un éditeur qui génère une valeur.
Avec l'exemple de code
publisher.sink{ added in
print(added)
}
Il y avait.
En regardant l'explication de ce [puits](https://developer.apple.com/documentation/combine/publisher/sink(receivevalue :)),
Attaches a subscriber with closure-based behavior to a publisher that never fails.
La signification est inconnue, mais il semble que cela attachera un abonné, alors utilisons-le.
Que se passe-t-il si vous appelez think avec Just plus tôt?
Just(1).sink { r in
print(r)
}
Cela affichera «1».
Il semble que l'éditeur (Just) ne sort 1 qu'une seule fois, et en le plongeant, il est entré dans r, donc «1» est affiché.
Essayons également CurrentValueSubject <Int, Never> (3)
, dont nous n'avons pas encore discuté.
CurrentValueSubject<Int, Never>(3).sink { r in
print(r)
}
Cela affichera «3»!
Quelle est la différence avec Just ...
Qu'est-ce que CurrentValueSubject? Regardons la définition.
@available(macOS 10.15, iOS 13.0, tvOS 13.0, watchOS 6.0, *)
final public class CurrentValueSubject<Output, Failure> : Subject
Ce type semble être ** Sujet **. Ce n'était pas un éditeur! En outre, c'est la même chose que «Just»: il ne peut être utilisé que sur iOS 13.0 ou supérieur.
A subject that wraps a single value and publishes a new element whenever the value changes.
N'est-ce pas seulement l'éditeur qui peut publier? J'irai aussi voir la définition de Sujet.
public protocol Subject : AnyObject, Publisher
Apparemment, l'objet semble être un ** type d'éditeur **.
Comparé à Just
Just | Une sortiepourtant(just)Sortie une foisPublisher |
CurrentValueSubject | Enveloppez une valeur pour obtenir une nouvelle valeur lorsque la valeur changePublishFaireSubject |
La différence avec Just est que lorsque la valeur change, il publie la nouvelle valeur! Essayons.
import Combine
let a = CurrentValueSubject<Int, Never>(3)
a.sink{ added in
print(added)
}
a.value = 100
a.value = 10000
a.send(9999)
Qu'est-ce qui est susceptible d'être produit? La réponse est
3
100
10000
9999
Il imprime chaque fois qu'une .value est modifiée. De plus, a.send () semble être capable d'exprimer le changement de valeur.
La plupart du premier exemple a été expliqué.
import Combine
let a = CurrentValueSubject<Int, Never>(3)
let b = Just(1)
let publisher = b.combineLatest(a).map{b,a in a + b}
publisher.sink{ added in
print(added)
}
a.send(10)
Après cela, si vous savez let publisher = b.combineLatest (a) .map {b, a dans a + b}
, il semble que vous puissiez comprendre la signification du code d'une manière ou d'une autre.
combineLatest
Tout d'abord, prêtons attention à b.combineLatest (a)
.
Qu'est-ce que ça veut dire?
let a = CurrentValueSubject<Int, Never>(3)
let b = Just(1)
Donc, a et b sont des éditeurs.
Jetons un coup d'œil à la description de combineLatest.
Subscribes to an additional publisher and publishes a tuple upon receiving output from either publisher.
Ce type semble être à la fois Abonnez-vous et Publiez.
Essayez de le déplacer.
import Combine
let a = CurrentValueSubject<Int, Never>(3)
let b = Just(1)
let publisher = b.combineLatest(a).sink{r in
print(r)
}
Que va-t-il se passer avec ça?
La bonne réponse est
(1, 3)
En parlant de cela, combineLatest a dit plus tôt qu'il retournerait un tuple.
Changeons la valeur de a. Ajoutez 3 lignes de code.
import Combine
let a = CurrentValueSubject<Int, Never>(3)
let b = Just(1)
let publisher = b.combineLatest(a).sink{r in
print(r)
}
a.value = 4
a.value = 5
a.send(6)
Que se passe-t-il?
La bonne réponse est
(1, 3)
(1, 4)
(1, 5)
(1, 6)
La valeur de b reste inchangée et est imprimée en modifiant la valeur de a.
Avez-vous vu le mouvement?
En regardant la définition,
public func combineLatest<P>(_ other: P) -> Publishers.CombineLatest<Self, P> where P : Publisher, Self.Failure == P.Failure
C'est long et peu clair, mais il renvoie Publishers.CombineLatest <Self, P>
.
Publishers.CombineLatest
public struct CombineLatest<A, B> : Publisher
C'est ** Publisher **.
Ainsi, «b.combineLatest (a)» est une fonction qui fait de deux éditeurs un éditeur.
map
la carte est
Transforms all elements from the upstream publisher with a provided closure.
Il semble que tout sera transformé.
En regardant la définition
public func map<T>(_ transform: @escaping (Self.Output) -> T) -> Publishers.Map<Self, T>
Après tout, cela renvoie toujours Publisher!
L'exemple donné précédemment dans combineLatest
.
import Combine
let a = CurrentValueSubject<Int, Never>(3)
let b = Just(1)
let publisher = b.combineLatest(a).sink{r in
print(r)
}
a.value = 4
a.value = 5
a.send(6)
Le résultat est,
(1, 3)
(1, 4)
(1, 5)
(1, 6)
C'était.
Essayez d'ajouter une carte après combineLatest dans ce code.
import Combine
let a = CurrentValueSubject<Int, Never>(3)
let b = Just(1)
let publisher = b.combineLatest(a)
.map{(b,a) in a+b}
.sink{r in print(r)}
a.value = 4
a.value = 5
a.send(6)
Qu'est-ce qui est susceptible de revenir?
La bonne réponse est
4
5
6
7
c'est
(1, 3)
(1, 4)
(1, 5)
(1, 6)
Vous pouvez voir que chacun de ces résultats ajoute deux valeurs.
J'ai changé .map {(b, a) dans a + b}
en .map {(b, a) dans a}
.
Quelle sera la sortie?
import Combine
let a = CurrentValueSubject<Int, Never>(3)
let b = Just(1)
let publisher = b.combineLatest(a)
.map{(b,a) in a}
.sink{r in print(r)}
a.value = 4
a.value = 5
a.send(6)
La bonne réponse est
3
4
5
6
Pour utiliser Combine | iOS 13.Au-dessus de 0import Combine |
Ce qui est juste | Sortir la valeur une seule foisPublisher |
Qu'est-ce que l'évier | Abonnez-vous à la sortie de valeur par Publisher(Subscribe)Peut être traité |
CurrentValueSubject | La valeur peut être modifiée et la valeur modifiée est sortie.Publisher(Subject) |
Comment changer la valeur de CurrentValueSubject? | CurrentValueSubject.Attribuer à value ou CurrentValueSubject.send(value)Entrez une valeur dans |
Qu'est-ce que combineLatest | Fait de deux éditeurs un éditeur et renvoie la valeur sous forme de taple. |
Qu'est-ce que la carte | Transformez toutes les valeurs de l'éditeur |
Avez-vous compris le comportement du code en dessous de l'objectif?
import Combine
let a = CurrentValueSubject<Int, Never>(3)
let b = Just(1)
let publisher = b.combineLatest(a).map{b,a in a + b}
publisher.sink{ added in
print(added)
}
a.send(10)