2016-02-27 2 views
1

Имеет ли эта функция (или, возможно, некоторое монадическое обобщение) это имя?Имеет ли «естественная» функция от Seq [Option [T]] до опции [Seq [T]] имя?

def foo[T](in: Seq[Option[T]]): Option[Seq[T]] = { 
    val res = in.flatten.seq 
    if (res.length == in.length) Some(res) else None 
} 

Есть ли более элегантная реализация?

+2

Это обычно называется «последовательность» (посмотреть на Future.sequence, например) https://www.haskell.org/hoogle/?hoogle=sequence Прочитайте это для информации о реализации scalaz: HTTP: //eed3si9n.com/learning-scalaz-day12 –

+0

См. также мой ответ [здесь] (http://stackoverflow.com/a/12358892/334519). –

ответ

3

Как уже отмечались в комментариях, функция от Seq[M[A]] до M[Seq[A]] (где M монада) обычно называют sequence.

Определение Haskell его является:

Оценивайте каждое действие в последовательности слева направо, и собрать результаты.

Там нет общего реализация его в лестницу стандартной библиотеки, но вы можете увидеть пример для Future типа здесь: https://github.com/scala/scala/blob/v2.10.3/src/library/scala/concurrent/Future.scala#L487-L491

Вы можете найти общие реализаций sequence в библиотеках, таких как cats или scalaz.

Одно замечание состоит в том, что sequence является конкретным случаем более общей операции, обычно называемой traverse.

Haskell определяет, как traverse

Карта каждый элемент структуры к действию, оценивать эти действия слева направо, и игнорировать результаты.

Теперь, учитывая определение, sequence может быть реализован в терминах traverse, просто используя функцию тождества (x => x) в качестве операции карты traverse.

Если вы посмотрите на реализации, упомянутые выше, вы обнаружите, что все они используют это обобщение, и все они используют traverse для реализации sequence.

Смежные вопросы