我想使用cats-effect的IO monad读取一个文件列表,如下所示:
def readFile(file: File): IO[Either[CouldNotReadFromFileError, String]] = ???
// lists all the files I want to read
// returns an Either b/c this might encounter i/o problems
def findFiles(): IO[Either[Throwable, Array[File]]] = ???
// reads all files and saves their content in an Array[String]
// ignores files it could not read or find
def readFiles(): IO[Array[String]] = for {
filesE <- listFiles
files = filesE match {
case Left(err) =>
log.error("An error happened while reading files: " + err.getMessage)
List[File]()
case Right(fs) => fs.toList.map(readFile)
}
// files has type: List[IO[Either[CouldNotReadFromFileError, String]]]
// to continue here I'd like to have a: IO[List[Either[CouldNotReadFromFileError, String]]]
???
} yield ???现在,为了在for-yield结构中继续我的计算,我想将我的List[IO[Either[CouldNotReadFromFileError, String]]]转换为IO[List[Either[CouldNotReadFromFileError, String]]]。我知道我可能可以用cat's traverse做这样的事情,但不知道具体怎么做。任何帮助都是非常感谢的。
发布于 2019-02-13 22:13:32
sequence足以满足您的需求:
import java.io.File
import cats.effect.IO
import cats.implicits._
final class CouldNotReadFromFileError extends RuntimeException("message")
object TestTest {
def readFile(file: File): IO[Either[CouldNotReadFromFileError, String]] = ???
def findFiles: IO[Either[Throwable, Array[File]]] =
???
// reads all files and saves their content in an Array[String]
// ignores files it could not read or find
def readFiles(): IO[Array[String]] =
for {
filesE <- findFiles
files = filesE match {
case Left(err) =>
List.empty
case Right(fs) =>
fs.toList.map(readFile)
}
// The type ascription below is just for demonstration purposes.
// You don't need to keep it there.
a <- files.sequence: IO[List[Either[CouldNotReadFromFileError, String]]]
} yield {
???
}
}https://stackoverflow.com/questions/54671857
复制相似问题