Differences

This shows you the differences between two versions of the page.

Link to this comparison view

Both sides previous revision Previous revision
Next revision
Previous revision
fp2023:hw2 [2023/04/07 15:41]
pdmatei
fp2023:hw2 [2024/04/17 18:15] (current)
pdmatei
Line 1: Line 1:
-====== Homework 2. Sets as functions ​======+====== Homework 2. Sets as trees ======
  
  
Line 119: Line 119:
  
 which is more legible and easy to debug. which is more legible and easy to debug.
- 
-====== Homework 1. Sets as functions ====== 
- 
-===== Problem statement ===== 
- 
-Sets are **unordered** collections of **unique** elements. There are several ways to store sets. One of them relies on **characteristic functions**. Such **functional sets** are especially useful if we expect many **insert/​retrieve** operations and less **traversals** in our code. 
- 
-A **characteristic function** of a set $math[A \subseteq U] is a function $math[f: U \rightarrow \{0,1\}] which assigns $math[f(x) = 1] for each element $math[x \in A] and $math[f(x) = 0] for each element $math[x \not\in A]. 
- 
-In our implementation,​ $math[U] will be the set of integers, hence we shall encode only **sets of integers**. Hence, the type of a set will be: 
-<code scala> 
-type Set = Int => Boolean 
-</​code>​ 
- 
-For instance, the set $math[\{1,​2,​3\}] will be encoded by the anonymous function: 
-<code scala> 
-(x: Int) => (x == 1 || x == 2 || x == 3) 
-</​code>​ 
- 
-Also, the empty set can be encoded as: 
-<code scala> 
-(x: Int) => false 
-</​code>​ 
- 
-while the entire set of integers may be encoded as: 
-<code scala> 
-(x: Int) => true 
-</​code>​ 
- 
-**1.** Write a function ''​singleton''​ which takes an integer and returns **the set** containing only that integer: 
-<code scala> 
-def singleton(x:​ Int): Set = ??? 
-</​code>​ 
- 
-Note that ''​singleton''​ could have been equivalently defined as: ''​def singleton(x:​ Int)(e: Int): Boolean = ???'',​ however, the previous variant is more legible, in the sense that it highlights the idea that we are returning **set objects**, namely **characteristic functions**. 
- 
- 
-**2.** Write a function ''​member''​ which takes a set and an integer and checks if the integer is a member of the set. Note that ''​member''​ should be defined and called as a curry function: 
-<code scala> 
-def member(e: Int)(set: Set): Boolean = ??? 
-</​code>​ 
- 
-**3.** Write a function ''​ins''​ which inserts a new element in a set. More precisely, given $math[x] and $math[set], ''​ins''​ returns a new set $math[\{x\} \cup set]. 
-<code scala> 
-def ins(x: Int)(set: Set): Set = ??? 
-</​code>​ 
- 
-**4.** Write a function ''​fromBounds''​ which takes two integer bounds ''​start''​ and ''​stop''​ and returns the set $math[\{start,​ start+1, \ldots, stop\}]. It is guaranteed that $math[start \leq stop] (you do not need to check this condition in your implementation). 
- 
-<code scala> 
-def fromBounds(start:​ Int, stop: Int): Set = ??? 
-</​code>​ 
- 
-**5.** Write the function which performs the union of two sets: 
-<code scala> 
-def union(set1: Set, set2: Set): Set = ??? 
-</​code>​ 
- 
-**6.** Write a function which computes the complement of a set with respect to the set of integers: 
-<code scala> 
-def complement(s1:​ Set): Set = ??? 
-</​code>​ 
- 
-**7.** Write a function which computes the sum of value ''​b''​ to all elements from a set, for given **bounds**. Use a tail-end recursive function: 
-<code scala> 
-  def sumSet(b: Int)(start: Int, stop: Int)(set: Set): Int = { 
-    def auxSum(crt: Int, acc: Int): Int = ??? 
-    ??? 
-  } 
-</​code>​ 
- 
-**8.** Generalise the previous function such that we can **fold** a set using any binary commutative operation over integers. Make sure this is a **left** fold: Folding the set: ''​{x,​y,​z}''​ with ''​b''​ should produce: ''​( (b op x) op y) op z''​ 
-<code scala> 
-  def foldLeftSet 
-     ​(b:​Int) ​                 // initial value  
-     (op: (Int,Int) => Int)   // folding operation 
-     ​(start:​ Int, stop: Int)  // bounds (inclusive) 
-     (set: Set): Int = ???    // the set to be folded 
-</​code>​ 
- 
-**9.** Implement an alternative to the previous function, namely **foldRight**. Applying ''​foldRight''​ on the set ''​{x,​y,​z}''​ with ''​b''​ should produce: ''​a op (b op (c op b))''​. Use direct recursion instead of tail recursion. 
-<code scala> 
-  def foldRightSet 
-     ​(b:​Int) ​                 // initial value  
-     (op: (Int,Int) => Int)   // folding operation 
-     ​(start:​ Int, stop: Int)  // bounds (inclusive) 
-     (set: Set): Int = ???    // the set to be folded 
-</​code>​ 
- 
-**10.** Implement operation ''​filter''​ which takes a set and returns another one containing only those elements that satisfy the predicate: 
-<code scala> 
-def filter(p: Int => Boolean)(set:​ Set): Set = ??? 
-</​code>​ 
- 
-**11.** Implement a function which **partitions** a set into two sets. The left-most contains those elements that satisfy the predicate, while the right-most contains those elements that do not satisfy the predicate. Use pairs. A pair is constructed with simple parentheses. E.g. ''​(1,​2)''​ is a pair of two integers. Suppose ''​val p: (Int,​Int)''​ is another pair of two integers. Then ''​p._1''​ is the left-most part of the pair while ''​p._2''​ is the right-most part of the pair. 
-<code scala> 
-  def partition(p:​ Int => Boolean)(set:​ Set): (Set,Set) = ??? 
-</​code>​ 
- 
-**12.** Implement a function ''​forall''​ which checks if all elements in a given range of a set satisfy a predicate (condition). (Such a condition may be that all elements from given bounds are even numbers). 
-<code scala> 
-  def forall(cond:​ Int => Boolean) // condition to be checked 
-            (start: Int, stop: Int) // start,stop values (inclusive) 
-            (set: Set): Boolean ​ // set to be checked 
-            = ??? 
-</​code>​ 
- 
-**13.** Implement a function ''​exists''​ which checks if a predicate holds for **some** element from the range of a set. Hint: it is easier to implement ''​exists''​ using the logical relation: $math[ \exists x. P(X) \iff \lnot \forall x.\lnot P(X)]. 
- 
-**14.** Implement the function ''​setOfDivByK''​ which returns the set of integers divisible by a value ''​k''​. Use the appropriate functions you have defined. 
-<code scala> 
-def setOfDivByK(k:​ Int): Set = ?? 
-</​code>​ 
- 
-**15.** Implement the function ''​moreDivs''​ which verifies if ''​set1''​ contains more divisors of ''​k''​ than ''​set2'',​ over the range ''​[start,​stop]''​. Use any combination of the previous functions you have defined for your implementation. 
-<code scala> 
-def moreDivs(k: Int)(start: Int, stop:​Int)(set1:​ Set, set2: Set): Boolean = ??? 
-</​code>​ 
  
  
Line 242: Line 124:
  
   * Please follow the [[fp2023:​submission-guidelines| Submission guidelines]] which are the same for all homework.   * Please follow the [[fp2023:​submission-guidelines| Submission guidelines]] which are the same for all homework.
-  * To solve your homework, download the {{:fp2023:???|Project template}}, import it in IntellIJ, and you are all set. Do not rename the project manually, as this may cause problems with IntellIJ.+  * To solve your homework, download the {{:fp2023:h2-word-tree.zip|Project template}}, import it in IntellIJ, and you are all set. Do not rename the project manually, as this may cause problems with IntellIJ.