Scala - correspondência de padrões

A correspondência de padrões é o segundo recurso mais amplamente usado do Scala, depois dos valores de função e fechamentos. Scala fornece um excelente suporte para correspondência de padrões no processamento de mensagens.

Uma correspondência de padrão inclui uma sequência de alternativas, cada uma começando com a palavra-chave case. Cada alternativa inclui umpattern e um ou mais expressions, que será avaliado se o padrão corresponder. Um símbolo de seta => separa o padrão das expressões.

Experimente o programa de exemplo a seguir, que mostra como comparar com um valor inteiro.

Exemplo

object Demo {
   def main(args: Array[String]) {
      println(matchTest(3))
   }
   
   def matchTest(x: Int): String = x match {
      case 1 => "one"
      case 2 => "two"
      case _ => "many"
   }
}

Salve o programa acima em Demo.scala. Os seguintes comandos são usados ​​para compilar e executar este programa.

Comando

\>scalac Demo.scala
\>scala Demo

Resultado

many

O bloco com as instruções case define uma função, que mapeia inteiros para strings. A palavra-chave match fornece uma maneira conveniente de aplicar uma função (como a função de correspondência de padrões acima) a um objeto.

Experimente o programa de exemplo a seguir, que compara um valor com padrões de diferentes tipos.

Exemplo

object Demo {
   def main(args: Array[String]) {
      println(matchTest("two"))
      println(matchTest("test"))
      println(matchTest(1))
   }
   
   def matchTest(x: Any): Any = x match {
      case 1 => "one"
      case "two" => 2
      case y: Int => "scala.Int"
      case _ => "many"
   }
}

Salve o programa acima em Demo.scala. Os seguintes comandos são usados ​​para compilar e executar este programa.

Comando

\>scalac Demo.scala
\>scala Demo

Resultado

2
many
one

Combinando usando classes de caso

o case classessão classes especiais usadas na correspondência de padrões com expressões de caso. Sintaticamente, essas são classes padrão com um modificador especial:case.

Tente o seguinte, é um exemplo simples de correspondência de padrões usando a classe de caso.

Exemplo

object Demo {
   def main(args: Array[String]) {
      val alice = new Person("Alice", 25)
      val bob = new Person("Bob", 32)
      val charlie = new Person("Charlie", 32)
   
      for (person <- List(alice, bob, charlie)) {
         person match {
            case Person("Alice", 25) => println("Hi Alice!")
            case Person("Bob", 32) => println("Hi Bob!")
            case Person(name, age) => println(
               "Age: " + age + " year, name: " + name + "?")
         }
      }
   }
   case class Person(name: String, age: Int)
}

Salve o programa acima em Demo.scala. Os seguintes comandos são usados ​​para compilar e executar este programa.

Comando

\>scalac Demo.scala
\>scala Demo

Resultado

Hi Alice!
Hi Bob!
Age: 32 year, name: Charlie?

Adicionar a palavra-chave case faz com que o compilador adicione vários recursos úteis automaticamente. A palavra-chave sugere uma associação com expressões de caso na correspondência de padrões.

Primeiro, o compilador converte automaticamente os argumentos do construtor em campos imutáveis ​​(vals). A palavra-chave val é opcional. Se você quiser campos mutáveis, use a palavra-chave var. Portanto, nossas listas de argumentos do construtor agora são mais curtas.

Em segundo lugar, o compilador implementa automaticamente equals, hashCode, e toStringmétodos para a classe, que usam os campos especificados como argumentos do construtor. Portanto, não precisamos mais de nossos próprios métodos toString ().

Finalmente, também, o corpo de Person a classe fica vazia porque não há métodos que precisemos definir!