Java Flow API 的实践(三):Stream 的实现
概述
前段时间在使用 Android 的 LiveData 时感受到,如果仅仅实现观察者模式,在进行响应式编程时,处理数据流还是有诸多不便,直接使用 Flow API 也会遇到这个问题,所以本篇就实现一个简易的 Stream 类(仅实现filter、map、reduce、flatMap和forEach)来处理这类问题。(注意,本篇的代码处于实验性阶段,旨在提供一种思路,仅用于学习)
实现效果如下:
Flow.Publisher<Integer> publisher = Flows.from(1, 2, 3, 4, 5, 6, 7, 8, 9, 10);
Stream.from(publisher)
.forEach(integer -> System.out.println("ExampleUnitTest.forEach 1=>" + integer))
.filter(integer -> integer % 2 == 0)
.forEach(integer -> System.out.println("ExampleUnitTest.forEach 2=>" + integer))
.map(integer -> integer + 10)
.reduce(0, (integer, integer2) -> integer + integer2)
.flatMap(integer -> {
char[] chars = String.valueOf(integer).toCharArray();
Character[] buf = new Character[chars.length];
for (int i = 0; i < chars.length; i++) {
buf[i] = chars[i];
}
return Stream.from(Flows.fromArray(buf));
})
.subscribe(new Flow.Subscriber<Character>() {
@Override
public void onSubscribe(Flow.Subscription subscription) {
System.out.println("ExampleUnitTest.onSubscribe =>");
}
@Override
public void onNext(Character item) {
System.out.println("ExampleUnitTest.onNext =>" + item);
}
@Override
public void onError(Throwable throwable) {
System.out.println("ExampleUnitTest.onError =>" + throwable);
}
@Override
public void onComplete() {
System.out.println("ExampleUnitTest.onComplete =>");
}
});
Stream 类的实现
public class Stream<T, R> implements Flow.Processor<T, R> {
public static <T> Stream<T, T> from(Flow.Publisher<T> publisher) {
return new Stream<>(publisher);
}
protected final Flow.Publisher<T> publisher;
protected Flow.Subscriber subscriber;
private Stream(Flow.Publisher<T> publisher) {
this.publisher = Objects.requireNonNull(publisher);
}
@Override
public void subscribe(Flow.Subscriber<? super R> subscriber) {
this.subscriber = subscriber;
this.publisher.subscribe(this);
}
@Override
public void onSubscribe(Flow.Subscription subscription) {
subscriber.onSubscribe(subscription);
}
@Override
public void onNext(T item) {
subscriber.onNext(item);
}
@Override
public void onError(Throwable throwable) {
subscriber.onError(throwable);
}
@Override
public void onComplete() {
subscriber.onComplete();
}
public <K> Stream<?, K> map(Function<R, K> mapper) {
Objects.requireNonNull(mapper);
return new Stream<R, K>(this) {
@Override
public void onNext(R item) {
subscriber.onNext(mapper.apply(item));
}
};
}
public Stream<?, R> filter(Predicate<R> predicate) {
Objects.requireNonNull(predicate);
return new Stream<R, R>(this) {
@Override
public void onNext(R item) {
if (predicate.test(item)) {
super.onNext(item);
}
}
};
}
public <K> Stream<?, K> reduce(K seed, BiFunction<K, R, K> reducer) { //注意这里的 BiFunction 接口需要从JDK里复制一份出来,或者自己定义一个即可
Objects.requireNonNull(reducer);
return new Stream<R, K>(this) {
private K reduceSeed = Objects.requireNonNull(seed);
@Override
public void onNext(R item) {
reduceSeed = reducer.apply(reduceSeed, item);
}
@Override
public void onComplete() {
subscriber.onNext(reduceSeed);
super.onComplete();
}
};
}
public Stream<?, R> forEach(Consumer<R> consumer) {
Objects.requireNonNull(consumer);
return map((R r) -> {
consumer.accept(r);
return r;
});
}
public <K> Stream<?, K> flatMap(Function<R, Stream<?, K>> mapper) {
return new Stream<R, K>(this) {
@Override
public void onNext(R item) {
Stream<?, K> stream = mapper.apply(item);
stream.subscribe(new Flow.Subscriber<K>() {
@Override
public void onSubscribe(Flow.Subscription subscription) {
}
@Override
public void onNext(K item) {
subscriber.onNext(item);
}
@Override
public void onError(Throwable throwable) {
subscriber.onError(throwable);
}
@Override
public void onComplete() {
}
});
}
};
}
}