Commit 41a483e0 authored by Tim Hegemann's avatar Tim Hegemann
Browse files

init fp03

parent 34d70409
......@@ -11,6 +11,7 @@ usually marked with `???`.
|---------------------------------|-------------------------------------------------------------------|
| 1: Functional Data Structures | \<no templates\> |
| 2: Error Handling | [`fp02`](src/main/scala/fp02) |
| 3: Strictness and Lazyness | [`fp03`](src/main/scala/fp03) |
## Usage tips:
To keep your local solutions to the exercises when pulling from the repository,
......
package fp03.lev
object Levenshtein {
def levenshtein(s1: String, s2: String): Int = ???
def main(args: Array[String]): Unit = {
val s1 = "Mitternachtsmahl"
val s2 = "Mietpreisbremse"
val start = System.nanoTime()
val res = levenshtein(s1, s2)
println(s"Time: ${(System.nanoTime() - start) / 1e9}; Result: $res")
}
}
package fp03
sealed trait Stream[+A] {
import Stream._ // make methods from companion object available
def headOption: Option[A] = this match {
case Empty => None
case Cons(h, _) => Some(h())
}
def toList: List[A] = {
@annotation.tailrec
def go(s: Stream[A], acc: List[A]): List[A] = s match {
case Cons(h, t) => go(t(), h() :: acc)
case _ => acc
}
go(this, List()).reverse
}
def take(n: Int): Stream[A] = this match {
case Cons(h, t) =>
if (n > 1) cons(h(), t().take(n - 1))
else if (n == 1) cons(h(), empty)
else empty
case Empty => empty
}
@annotation.tailrec
final def drop(n: Int): Stream[A] = this match {
case Cons(_, t) => if (n > 0) t().drop(n - 1) else this
case Empty => this
}
def foldRight[B](z: => B)(f: (A, => B) => B): B = this match {
case Cons(x, xs) => f(x(), xs().foldRight(z)(f))
case Empty => z
}
def exists(p: A => Boolean): Boolean =
foldRight(false)((a, b) => p(a) || b)
def forAll(p: A => Boolean): Boolean =
foldRight(true)((a, b) => p(a) && b)
// Aufgabe 1: map, filter, append, flatMap
// Use the smart constructors from the Stream object
def append[B >: A](b: => Stream[B]): Stream[B] = ???
// Aufgabe 2: takeWhile
// a)
def takeWhile(p: A => Boolean): Stream[A] = ???
// b)
def takeWhileViaFoldRight(p: A => Boolean): Stream[A] = ???
// c)
def takeWhileViaUnfold(p: A => Boolean): Stream[A] = ???
// Aufgabe 3: tails
def tails: Stream[Stream[A]] = ???
}
case object Empty extends Stream[Nothing]
case class Cons[+A](h: () => A, t: () => Stream[A]) extends Stream[A]
object Stream {
def cons[A](h: => A, t: => Stream[A]): Stream[A] = {
lazy val head = h
lazy val tail = t
Cons(() => head, () => tail)
}
def empty[A]: Stream[A] = Empty
def apply[A](as: A*): Stream[A] =
if (as.isEmpty) empty
else cons(as.head, apply(as.tail: _*))
def unfold[A, S](z: S)(f: S => Option[(A, S)]): Stream[A] =
f(z) match {
case Some((h, s)) => cons(h, unfold(s)(f))
case None => empty
}
}
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment