Kotlin 难以同时使用arrow、Option和RxJava

Kotlin 难以同时使用arrow、Option和RxJava,kotlin,functional-programming,reactive-programming,rx-java2,arrow-kt,Kotlin,Functional Programming,Reactive Programming,Rx Java2,Arrow Kt,我很难找到一个很好的方法来协调使用RxJava和箭头kt或者和选项类型。我有两种方法,既返回代码>单< P>,如果我是你,我会考虑简化你的返回类型,而不使用 >在单< /代码>中,因为单< /代码>已经可以发出错误。因此,最终,您只能使用选项,并处理RxJava链中的错误,而不是在或上进行平面映射。比如: class Foo(val qux: Option<Qux>) class Bar class Qux class ApiError fun loadFoo(): Single

我很难找到一个很好的方法来协调使用RxJava和箭头kt
或者
选项
类型。我有两种方法,既返回代码>单< P>,如果我是你,我会考虑简化你的返回类型,而不使用<代码> <代码> >在<代码>单< /代码>中,因为<代码>单< /代码>已经可以发出错误。因此,最终,您只能使用
选项
,并处理RxJava链中的错误,而不是在
上进行平面映射。比如:

class Foo(val qux: Option<Qux>)
class Bar
class Qux
class ApiError

fun loadFoo(): Single<Option<Foo>> {
  // in case of an error, this will return Single.error(ApiError(...)) if ApiError extends Throwable
  // otherwise make it extend it or just wrap it into something which is a Throwable   
}

fun loadBar(qux: Qux): Single<Option<Bar>> {
  // same as above
}


fun loadBarFromFooOption(maybeFoo: Option<Foo>): Single<Option<Bar>> {
    return maybeFoo.flatMap { foo -> foo.qux }
        .map { qux -> loadBar(qux) }
        .getOrElse { Single.just(Option.empty()) }
}

fun doStuffToGetBar(): Single<Option<Bar>> {
    return loadFoo().flatMap { fooOption -> loadBarFromFooOption(fooOption) }
}

// somewhere else
doStuffToGetBar().subscribe({ barOption -> /* ... */ }, { error -> /* ... */ })
class-Foo(val-qux:Option)
分类栏
类群
类错误
fun loadFoo():单个{
//在发生错误的情况下,如果APIRROR扩展了Throwable,则将返回Single.error(APIRROR(…))
//否则,让它扩展它或只是把它包装成一个可以扔掉的东西
}
趣味加载条(qux:qux):单人{
//同上
}
趣味LoadBarFromFoooOption(maybeFoo:Option):单个{
返回maybeFoo.flatMap{foo->foo.qux}
.map{qux->loadBar(qux)}
.getOrElse{Single.just(Option.empty())}
}
fun doStuffToGetBar():单个{
返回loadFoo().flatMap{fooooption->loadBarFromFooOption(fooooption)}
}
//其他地方
doStuffToGetBar().subscribe({barOption->/*…*/},{error->/*…*/})

是的,这是一个关于单身汉已经能够发出错误的好观点。我认为我们的目标是使用其中一个。Left来清楚地定义所有预期的错误情况。然后,当我们订阅Observable时,如果不实现错误处理程序,它将使任何异常/意外错误崩溃。
fun loadBarFromMaybeFoo(maybeFoo: Option<Foo>): Single<Either<ApiError, Option<Bar>>> {
    return maybeFoo.flatMap { foo -> foo.qux }
        .map { qux -> loadBar(qux) }
        .getOrElse { Single.just(Either.Right(Option.empty())) }
}

fun doStuffToGetBar(): Single<Either<ApiError, Option<Bar>>> {
    return loadFoo()
        .flatMap { maybeFooOrError ->
            maybeFooOrError.fold(
                { error -> Single.just(Either.Left(error)) },
                { maybeFoo -> loadBarFromMaybeFoo(maybeFoo) }
            )
        }
}
fun doStuffToGetBar(): Single<Either<ApiError, Option<Bar>>> {
    return SingleK.monadDefer().bindingCatch {
        val maybeFooOrError: Either<ApiError, Option<Foo>> = loadFoo().k().bind()

        val maybeQuxOrError: Either<ApiError, Option<Qux>> = maybeFooOrError.map { maybeFoo ->
            maybeFoo.flatMap { it.qux }
        }

        // return type is Either<ApiError, Option<Either<ApiError, Option<Bar>>>>
        // desired return type is Either<ApiError, Option<Bar>>
        maybeQuxOrError.map { maybeQux ->
            maybeQux.map { qux ->
                loadBar(qux).k().bind() // this part doesn't seem good
            }
        }
    }.value()
}
class Foo(val qux: Option<Qux>)
class Bar
class Qux
class ApiError

fun loadFoo(): Single<Option<Foo>> {
  // in case of an error, this will return Single.error(ApiError(...)) if ApiError extends Throwable
  // otherwise make it extend it or just wrap it into something which is a Throwable   
}

fun loadBar(qux: Qux): Single<Option<Bar>> {
  // same as above
}


fun loadBarFromFooOption(maybeFoo: Option<Foo>): Single<Option<Bar>> {
    return maybeFoo.flatMap { foo -> foo.qux }
        .map { qux -> loadBar(qux) }
        .getOrElse { Single.just(Option.empty()) }
}

fun doStuffToGetBar(): Single<Option<Bar>> {
    return loadFoo().flatMap { fooOption -> loadBarFromFooOption(fooOption) }
}

// somewhere else
doStuffToGetBar().subscribe({ barOption -> /* ... */ }, { error -> /* ... */ })