我正在尝试使用VAVR的Try的惯用方法是什么。
我正在查看的用例必须执行以下步骤:
-获取鞋子列表(调用可能引发检查异常)
-清洁每双鞋子(调用可能引发检查异常)
-恢复每只鞋子(调用可能引发检查异常)
-返回清洁/恢复的鞋子列表
这是我的示例玩具代码,其中processRequest方法购买n双鞋,清洗并恢复它们;打印错误(如果有):
// definitions
ShoeStore java.util.List<Shoe> buy(int numberOfPairs) throws OutOfStockException;
ShoeCleaningService Shoe clean(Shoe dirtyShoe) throws OutOfShoePolishException;
ShoeRestoreService Shoe restore(Shoe oldShoe) throws OutOfSparePartsException;
class EnterpriseShoeService {
// constructor
...
public List<Shoe> processRequest(int numberOfPairs) {
Try<List<Shoe>> shoes = Try.of(() -> shoeStore.buy(numberOfPairs));
Try<List<Try<Shoe>>> cleanedAndRestoredShoes = shoes.map(xs -> xs.stream().map(shoe ->
Try.success(shoe)
.andThenTry(shoeCleaningService::clean)
.andThenTry(shoeRestoreService::restore))
.collect(Collectors.toList()));
List<Shoe> result = cleanedAndRestoredShoes
.getOrElseGet(err -> {
System.out.println(err.getMessage());
return Collections.emptyList();
})
.stream()
.map(shoeTry -> shoeTry.onFailure(err -> System.out.println(err.getMessage())))
.filter(Try::isSuccess)
.map(Try::get)
.collect(Collectors.toList());
return result;
}
}
我的问题是:如何简化这种逻辑?有没有可以消除的方法调用?可读性会提高吗?
答案 0 :(得分:1)
我不知道一切是否都按预期进行,因为未提及任何要求,但这应该可以使您了解分解的力量。
import io.vavr.collection.List;
import io.vavr.control.Try;
public class TryListComposition {
ShoeStore store;
ShoeCleaningService cleaningService;
ShoeRestoreService restoreService;
public java.util.List<Shoe> processRequest(int numberOfPairs) {
return processShoesRequest(numberOfPairs).getOrElse(List.empty()).toJavaList();
}
public Try<List<Shoe>> processShoesRequest(int numberOfPairs) {
return this.buy(numberOfPairs)
.map(shoes -> shoes
.map(this::cleanAndRestore)
.flatMap(x -> x)
);
}
public Try<Shoe> cleanAndRestore(Shoe shoe) {
return clean(shoe).flatMap(this::restore);
}
Try<List<Shoe>> buy(int numberOfPairs) {
return Try.of(() ->
List.ofAll(store.buy(numberOfPairs).stream());
}
Try<Shoe> clean(Shoe dirtyShoe) {
return Try.of(() -> cleaningService.clean(dirtyShoe));
}
Try<Shoe> restore(Shoe oldShoe) {
return Try.of(() -> restoreService.restore(oldShoe));
}
}
class Shoe {
}
interface ShoeStore {
java.util.List<Shoe> buy(int numberOfPairs) throws
OutOfStockException;
}
interface ShoeCleaningService {
Shoe clean(Shoe dirtyShoe) throws OutOfShoePolishException;
}
interface ShoeRestoreService {
Shoe restore(Shoe oldShoe) throws OutOfSparePartsException;
}
class OutOfStockException extends Exception {
}
class OutOfShoePolishException extends Exception {
}
class OutOfSparePartsException extends Exception {
}