考虑以下代码:
void tryToOpenSafe() {
getCorrectSafeCombination().subscribe(combination -> System.out.println("Correct combination is " + combination));
}
Maybe<Integer> getCorrectSafeCombination() {
return getPossibleCombinations()
.toObservable()
.flatMapIterable(combinations -> combinations)
.flatMap(combination -> tryToOpenSafeWithCombination(combination).toObservable()
.map(isCorrect -> new CombinationCheckResult(combination, isCorrect)))
.filter(result -> result.isCorrect)
.map(result -> result.combination)
.firstElement();
}
Single<List<Integer>> getPossibleCombinations() {
final List<Integer> combinations = Arrays.asList(123, 456, 789, 321);
return Single.just(combinations);
}
// this is expensive
final Single<Boolean> tryToOpenSafeWithCombination(int combination) {
System.out.println("Trying to open safe with " + combination);
final boolean isCorrectCombination = combination == 789;
return Single.just(isCorrectCombination);
}
我收到了一份我想打开的保险箱的可能“组合”(整数)列表。当然只有一种组合是正确的。
使用我当前的方法,getCorrectSafeCombination()
将提供它找到的第一个正确组合;但它仍然会尝试所有组合。
虽然这是有效的:一旦找到正确的组合,就无需尝试其他组合。
Rx 如何做到这一点?
最佳答案
发生这种情况是因为 flatMap
用于并发处理可观察对象,而您需要顺序处理。要解决这个问题,您只需将 flatMap
更改为 concatMap
以确保在您的 getCorrectSafeCombination
方法中观察值的顺序流动:
Maybe<Integer> getCorrectSafeCombination() {
return getPossibleCombinations()
.toObservable()
.flatMapIterable(combinations -> combinations)
//this one
.concatMap(combination -> tryToOpenSafeWithCombination(combination).toObservable()
.map(isCorrect -> new CombinationCheckResult(combination, isCorrect)))
.filter(result -> result.isCorrect)
.map(result -> result.combination)
.firstElement();
}
关于java - 对列表中的每一个,进行操作直到满足条件,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52294250/