Scala - Extracteurs

Un extracteur dans Scala est un objet qui a une méthode appelée unapplycomme l'un de ses membres. Le but de cette méthode unapply est de faire correspondre une valeur et de la démonter. Souvent, l'objet extracteur définit également une méthode doubleapply pour les valeurs de construction, mais ce n'est pas obligatoire.

Exemple

Prenons un exemple d'objet définit les deux apply et unapplyméthodes. La méthode apply a la même signification que toujours: elle transforme Test en un objet qui peut être appliqué aux arguments entre parenthèses de la même manière qu'une méthode est appliquée. Vous pouvez donc écrire Test ("Zara", "gmail.com") pour construire la chaîne "[email protected]".

le unapply est ce qui transforme la classe Test en une extractor et il renverse le processus de construction de apply. Où apply prend deux chaînes et en forme une chaîne d'adresse e-mail, unapply prend une adresse e-mail et renvoie potentiellement deux chaînes: leuser et le domain de l'adresse.

le unapplydoit également gérer le cas où la chaîne donnée n'est pas une adresse e-mail. C'est pourquoi unapply renvoie un type Option sur des paires de chaînes. Son résultat est soitSome (user, domain)si la chaîne str est une adresse e-mail avec les parties utilisateur et domaine données, ou None, si str n'est pas une adresse e-mail. Voici quelques exemples comme suit.

Syntaxe

unapply("[email protected]") equals Some("Zara", "gmail.com")
unapply("Zara Ali") equals None

L'exemple de programme suivant montre un objet extracteur pour les adresses e-mail.

Exemple

object Demo {
   def main(args: Array[String]) {
      println ("Apply method : " + apply("Zara", "gmail.com"));
      println ("Unapply method : " + unapply("[email protected]"));
      println ("Unapply method : " + unapply("Zara Ali"));
   }
   
   // The injection method (optional)
   def apply(user: String, domain: String) = {
      user +"@"+ domain
   }

   // The extraction method (mandatory)
   def unapply(str: String): Option[(String, String)] = {
      val parts = str split "@"
      
      if (parts.length == 2){
         Some(parts(0), parts(1)) 
      } else {
         None
      }
   }
}

Enregistrez le programme ci-dessus dans Demo.scala. Les commandes suivantes sont utilisées pour compiler et exécuter ce programme.

Commander

\>scalac Demo.scala
\>scala Demo

Production

Apply method : [email protected]
Unapply method : Some((Zara,gmail.com))
Unapply method : None

Correspondance de motifs avec des extracteurs

Lorsqu'une instance d'une classe est suivie de parenthèses avec une liste de zéro ou plusieurs paramètres, le compilateur appelle le applyméthode sur cette instance. Nous pouvons définir appliquer à la fois dans les objets et dans les classes.

Comme mentionné ci-dessus, le but de la unapplyméthode consiste à extraire une valeur spécifique que nous recherchons. Il fait l'opération inverseapplyEst-ce que. Lors de la comparaison d'un objet extracteur à l'aide dumatch déclaration le unapply La méthode sera automatiquement exécutée.

Essayez l'exemple de programme suivant.

Exemple

object Demo {
   def main(args: Array[String]) {
      val x = Demo(5)
      println(x)

      x match {
         case Demo(num) => println(x+" is bigger two times than "+num)
         
         //unapply is invoked
         case _ => println("i cannot calculate")
      }
   }
   def apply(x: Int) = x*2
   def unapply(z: Int): Option[Int] = if (z%2==0) Some(z/2) else None
}

Enregistrez le programme ci-dessus dans Demo.scala. Les commandes suivantes sont utilisées pour compiler et exécuter ce programme.

Commander

\>scalac Demo.scala
\>scala Demo

Production

10
10 is bigger two times than 5