1

免責事項:これは宿題の一部です。カスタムListオブジェクトのflatMapを実装したいと思います。mapの実装に成功しましたが、flatMapに問題があります。マップから取得したリストのリストをフラット化する方法がわかりません。本当に地図を使うべきかどうかわかりません。

trait List[+A] {
  /** The first element */
  def head: A
  /** The rest of the elements */
  def tail: List[A]
  def flatMap[B](f: A => List[B]): List[B]
  def map[B](f: A => B): List[B]

  // Concatenate two lists
  def concat[B >: A](that: List[B]): List[B] = this match {
    case Empty => that
    case NonEmpty(head, tail) => NonEmpty(head, tail concat that)
  }
}

case object Empty extends List[Nothing] {
  def head = throw new UnsupportedOperationException("Empty.head")
  def tail = throw new UnsupportedOperationException("Empty.tail")
  def flatMap[B](f: Nothing => List[B]): List[B] = Empty
  def map[B](f: Nothing => B): List[B] = Empty

  override def toString = "Empty"
}

case class NonEmpty[A](head: A, tail: List[A]) extends List[A] {

  def map[B](f: A => B): List[B] = {

    NonEmpty(f(head), tail.map(f))

  }
def flatMap[B](f: A => List[B]): List[B] = {
    val a = this.map(f)
    for (x <- a; y <- x) yield y
  }
}
4

2 に答える 2

3

これは宿題なので、完全な解決策は提供したくありません。いくつかのヒントだけです。

  1. map実装する必要はありませんflatMap(実際には、逆の方が簡単です)。
  2. 必要なものはすべて揃っています ( aをflatMap返し、定義された関数を受け取りList[B]ます)Listconcat
  3. flatMap最初の実装Empty;-)
于 2012-12-29T14:33:50.333 に答える
2

長さ n のリストの flatMap を記述する必要があります。長さ n-1 のリストについて既に解決済みであると仮定して、解決してみてください。n => n-1 => ... => 1 => 0 であり、0 の場合は既に解決策があるため、これができれば問題は解決したことになります。

List は再帰型であるため、この種の考え方は List に適しています。

map ですでにこれを行っていますが、flatMap で同じことを行います。どちらの関数も List[A] から List[B] への変換です。唯一の違いは使用できるツールです。map には A を B に変換する関数があり、flatMap には A を List[B] に変換する関数があります。

于 2012-12-29T15:23:01.167 に答える