Objectives:
1.1.1. Write a function which returns true if a list of integers has at least k elements. Use patterns.
def atLeastk(k: Int, l: List[Int]): Boolean = { if (k == 0) ??? else ??? }
1.1.2. Write a function which returns the first n
elements from a given list. The function should not be implemented as tail-recursive.
def take(n: Int, l: List[Int]): List[Int] = ??? //take(3,List(1,2,3,4,5)) = List(1,2,3)
1.1.3. Write a function which takes a predicate p: Int ⇒ Boolean
, a list l
and returns a sublist of l
containing those elements for which p
is true. The function should be curried.
def takeP(p: Int => Boolean)(l: List[Int]): List[Int] = ??? //takeP(_%2 == 0)(List(1,2,3,4,5,6)) = List(2,4,6)
1.1.4. Write a function which uses a predicate to partition (split) a list.
def part(p: Int => Boolean)(l: List[Int]): (List[Int], List[Int]) = ??? // part(_%2 == 0)(List(1,2,3,4,5,6)) = (List(2,4,6),List(1,3,5))
More general implementation of taken
, dropn
and part
are already implemented in Scala and can be used as member functions of lists. Examples are shown below:
val l = List(1,2,3,4,5,6,7,8,9) l.take(3) l.drop(3) l.partition(_%2 == 0)
In what follows, we shall encode a gradebook as a list of pairs (<name>,<grade>)
, where <name>
is a String and <grade>
is an Int. Example:
val gradebook = List(("G",3), ("F", 10), ("M",6), ("P",4))
To make the type signatures more legible, we can introduce type aliases in Scala:
type Gradebook = List[(String,Int)] //the type Gradebook now refers to a list of pairs of String and Int
Add this type alias to your code before solving the following exercises.
1.2.1. Find the average grade from a gradebook. You must use foldRight
.
def average(g: Gradebook): Double = ???
1.2.2. Write a function which takes a gradebook and returns the percentage of failed vs. passed students, as a pair (x,y).
def percentage(g: Gradebook): (Double,Double) = ???
1.2.3. Write a function which takes a gradebook and returns the list of names which have passed. Use filter and map from Scala.
def pass(g: Gradebook): List[String] = ???
1.2.4. Implement a sorting algorithm such as merge sort (in ascending order) over gradebooks:
def mergeSort(l: Gradebook): Gradebook = { def merge(u: Gradebook, v: Gradebook): Gradebook = ??? ??? }
1.2.5 Using assertions check that our merge sort implementation returns the same lists as the stor from Scala.
Consider the following toy implementation of the type Nat
which encodes natural numbers.
trait Nat {} case object Zero extends Nat {} case class Succ(n: Nat) extends Nat {}
For instance, 3
will be encoded as the value: Succ(Succ(Succ(Zero)))
.
2.1.1. Write a function which implements addition over Nats:
def add(n: Nat, m: Nat): Nat = ???
2.1.2. Write a function which converts a Nat
to an Int
:
def toInt(n: Nat): Int = ???
2.1.3. Write a function which converts an Int
to a Nat
.
def fromInt(i: Int): Nat
In a binary search tree (BST), the key of the current node, is always:
Consider a binary search tree with keys as integers, encoded as follows:
trait ITree {} case object Empty extends ITree case class INode(key: Int, left: ITree, right: ITree) extends ITree
2.2.1. Create the tree shown below:
val tree = ??? /* 5 / \ 2 7 / \ \ 1 3 9 */
2.2.2. Implement the method size
which determines the number of non-empty nodes from the BST.
2.2.3. Define the method contains
, which checks if a given integer is a member of the BST.
2.2.4. Implement the method ins
which inserts a new integer in the BST. Note: the insertion must return a new BST (the binary search tree property mentioned above must hold after insertion).
2.2.5. Implement a method depth
which returns the maximal depth of a BST. Hint: use the method: _.max(_)
.
(!) 2.2.6. Implement a method minimum
which returns the smallest integer from a BST. (If the tree is empty, we return -1). Hint: use the example above, to guide your implementation.
(!) 5.2.7. Implement a method successor(k)
which returns the smallest integer from the BST, which is larger than k
. Use the following examples for your implementation:
5 t.successor(2) = 5 / \ t.successor(5) = 6 2 7 t.successor(7) = 8 / \ 6 8
3.1 Write a function reads the contents of a directory and returns True if a given file is in the folder.
3.2 Look into this example and implement a client and echo server using sockets (we are using the Java classes).
3.3 In the client, send a list to the server. The server will return the maximum number from that list.