From d43eeaa14afb86d50f0be0274cd6256bac9940fa Mon Sep 17 00:00:00 2001 From: "quentin.leblanc@etu.hesge.ch" <quentin.leblanc@etu.hesge.ch> Date: Thu, 20 Feb 2020 15:56:17 +0100 Subject: [PATCH] TP4 --- TP3/build.sbt | 3 ++ TP3/src/main/scala/3.fp.scala | 8 ++-- TP3/src/main/scala/4.lambda.scala | 64 +++++++++++++++++++++++++++ TP3/src/test/scala/4.lambdaTest.scala | 50 +++++++++++++++++++++ 4 files changed, 122 insertions(+), 3 deletions(-) create mode 100644 TP3/src/main/scala/4.lambda.scala create mode 100644 TP3/src/test/scala/4.lambdaTest.scala diff --git a/TP3/build.sbt b/TP3/build.sbt index 6e42885..dcb4679 100644 --- a/TP3/build.sbt +++ b/TP3/build.sbt @@ -3,3 +3,6 @@ name := "TP3" version := "0.1" scalaVersion := "2.13.1" + +libraryDependencies += "org.scalactic" %% "scalactic" % "3.1.0" +libraryDependencies += "org.scalatest" %% "scalatest" % "3.1.0" % "test" \ No newline at end of file diff --git a/TP3/src/main/scala/3.fp.scala b/TP3/src/main/scala/3.fp.scala index 9120c7c..2e89549 100644 --- a/TP3/src/main/scala/3.fp.scala +++ b/TP3/src/main/scala/3.fp.scala @@ -74,7 +74,7 @@ object Serie3 { @scala.annotation.tailrec final def and(xs: List[Boolean] ): Boolean = { xs match { - case true :: Nil => true + case Nil => true case true :: bs => and(bs) case _ => false } @@ -108,8 +108,10 @@ object Serie3 { * implémentation ne peut utiliser aucune fonction de List ! Vous * devez utiliser le pattern matching. */ - def even[A]( as: List[A] ): Boolean = { - len(as)%2 == 0 + final def even[A]( as: List[A] ): Boolean = as match{ + case Nil => true + case _ :: Nil => false + case _ :: _ :: rest => even(rest) } } diff --git a/TP3/src/main/scala/4.lambda.scala b/TP3/src/main/scala/4.lambda.scala new file mode 100644 index 0000000..3ad87fa --- /dev/null +++ b/TP3/src/main/scala/4.lambda.scala @@ -0,0 +1,64 @@ + /* + * Implémenter les fonctions suivantes en suivant les commentaires. + */ + +object Predicates { + + type P[A] = A=>Boolean + + /* + * La méthode 'not' retourne un nouveau prédicat dont le résultat + * est toujours la négation du résultat de l'argument. + */ + def not[A]( p: A =>Boolean ): A =>Boolean = { a:A => + !p(a) + } + + /* + * La méthode 'and' retourne un nouveau prédicat dont le résultat + * est toujours la conjonction des résultats des deux arguments. + */ + def and[A](p1: A =>Boolean, p2: A =>Boolean ): A =>Boolean = { a:A => + p1(a)&&p2(a) + } + + /* + * La fonction 'or' retourne un nouveau prédicat dont le résultat + * est toujours la disjonction des résultats des deux arguments. + */ + def or[A](p1: A =>Boolean, p2: A =>Boolean ): A =>Boolean = { a:A => + p1(a)||p2(a) + } + + /* + * La fonction 'exists' retourne un nouveau prédicat dont le + * résultat est vrai si au moins un des prédicat de l'argument est + * vrai. + */ + def exists[A]( ps: List[A =>Boolean] ): A =>Boolean = { a:A => + @scala.annotation.tailrec + def existRec(rest: List[P[A]], a: A): Boolean = rest match { + case Nil => false + case h :: _ if h(a) => true + case _ :: t => existRec(t, a) + } + existRec(ps, a) + } + + /* + * La fonction 'forall' retourne un nouveau prédicat dont le + * résultat est vrai si et seulement si tous les prédicats de + * l'argument sont vrais. + */ + def forall[A]( ps: List[A =>Boolean] ): A =>Boolean = { a:A => + @scala.annotation.tailrec + def forAllRec(rest: List[P[A]], a:A): Boolean = rest match{ + case Nil => true + case h :: _ if !h(a) => false + case _ :: t => forAllRec(t, a) + } + forAllRec(ps, a) + } + + +} diff --git a/TP3/src/test/scala/4.lambdaTest.scala b/TP3/src/test/scala/4.lambdaTest.scala new file mode 100644 index 0000000..3575b4c --- /dev/null +++ b/TP3/src/test/scala/4.lambdaTest.scala @@ -0,0 +1,50 @@ +import org.scalatest.funsuite.AnyFunSuite + +import Predicates._ + +class PredicatesSuite4 extends AnyFunSuite { + + + val big = (_:Int) >= 100 + val even = (_:Int) % 2 == 0 + + val small = not[Int]( big ) + val bae = and[Int]( big, even ) + val boe = or[Int]( big, even ) + + test("Predicate Evaluation") { + assert( big(200) ) + assert( ! big(19) ) + assert( even(200) ) + assert( ! even(201) ) + } + + test("Predicate negation") { + assert( small(19) ) + assert( !small( 200 ) ) + } + + test("Predicate AND") { + assert( bae( 200 ) ) + assert( !bae( 201 ) ) + } + + test("Predicate OR") { + assert( boe( 201 ) ) + assert( !boe( 19 ) ) + } + + val mul3 = (_:Int ) % 3 == 0 + val ps = List( big, even, mul3 ) + + test("Predicates FORALL") { + assert( forall[Int]( ps )( 402 ) ) + assert( ! forall[Int]( ps )( 200 ) ) + } + + test("Predicates EXISTS") { + assert( exists[Int]( ps )( 18 ) ) + assert( ! exists[Int]( ps )( 1 ) ) + } + +} -- GitLab