Publisher umwandeln mit Operatoren - wurzelsand/swift-memos GitHub Wiki
collect()
map()
flatMap()
tryMap()
scan()
-
Just
-Publisher if case let
throws
Schicke aus einer Schleife die Zahlen von 0 bis 9 über ein PassthroughSubject
an ein Sink und gebe sie als Array aus.
import Combine
var subscriptions = Set<AnyCancellable>()
let subject = PassthroughSubject<Int, Never>()
subject
.collect()
.sink(receiveCompletion: { print("completion:", $0)}, receiveValue: { print("value:", $0)})
.store(in: &subscriptions)
for i in 0..<10 {
subject.send(i)
}
subject.send(completion: .finished)
Ausgabe:
value: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
completion: finished
Program ended with exit code: 0
- Mit
collect(3)
würden immer nur maximal 3 Werte zwischengespeichert und dementsprechend mehrere Arrays aus maximal 3 Werten verschickt.
Gegeben sei ein Publisher von Strings:
["hello", "world"].publisher
Wandel den gegebenen Publisher in einen Publisher um, der alle Buchstaben in Großbuchstaben umwandelt.
var subscriptions = Set<AnyCancellable>()
func uppercased(of string: String) -> String {
string.uppercased()
}
["hello", "world"].publisher
.map(uppercased(of:))
.sink {
print("value:", $0)
}
.store(in: &subscriptions)
}
Ausgabe:
value: HELLO
value: WORLD
Gegeben sei ein Publisher von Strings:
["hello", "world"].publisher
Wandel den gegebenen Publisher in mehrere Publisher um, die Buchstaben in Großbuchstaben umwandeln.
var subscriptions = Set<AnyCancellable>()
func uppercased(of string: String) -> AnyPublisher<String, Never> {
Just(string.uppercased())
.eraseToAnyPublisher()
}
["hello", "world"].publisher
.flatMap(maxPublishers: .unlimited, uppercased(of:))
.sink {
print("value:", $0)
}
.store(in: &subscriptions)
}
Ausgabe:
value: HELLO
value: WORLD
map
erzeugt einen Publisher der die einzelnen Elemente des Datenstroms umwandelt. flatMap
erzeugt aus den einzelnen Elementen des Datenstroms mehrere Publisher.
Wir erweitern String um eine Methode isCapitalized
die einen StringError
auslösen kann:
enum StringError: Error {
case empty
}
extension String {
func isCapitalized() throws -> Bool {
guard let first = first else { throw StringError.empty }
return first.isUppercase
}
}
Ein Just
-Publisher für Strings soll von einem Sink abonniert werden, der ausgibt, ob der String groß geschrieben wurde. Wenn ein StringError
ausgelöst wurde, soll er im Completion-Block angezeigt werden.
enum StringError: Error {
case empty
}
extension String {
func isCapitalized() throws -> Bool {
guard let first = first else { throw StringError.empty }
return first.isUppercase
}
}
var subscriptions = Set<AnyCancellable>()
Just("")
.tryMap {
try $0.isCapitalized()
}
.sink(receiveCompletion: { completion in
if case let .failure(error) = completion {
if case StringError.empty = error {
print("String is empty")
}
}
}, receiveValue: { print("capitalized:", $0) })
.store(in: &subscriptions)
Ausgabe:
String is empty
Gegeben sei ein Publisher:
["H", "e", "l", "l", "o"].publisher
Ausgegeben werden soll:
H
He
Hel
Hell
Hello
var subscriptions = Set<AnyCancellable>()
["H", "e", "l", "l", "o"].publisher
.scan("") { stored, new in // .scan("", +)
return stored + new
}
.sink {
print($0)
}
.store(in: &subscriptions)