Entendendo de uma vez por todas Expressões Regulares: Parte 7— Regex no mundo JavaScript

Fala meu povo, tudo bem com vocês? Seguindo no penúltimo artigo da série regex, hoje falaremos (finalmente) sobre como utilizar as expressões regulares no mundo JavaScript.

Mas antes de tudo, se você chegou direto nesse tópico e ainda não tem tanta familiaridade, da uma olhada no post onde tudo começou.

Sem mais delongas, let's do it!


Declaração

Como a maioria dos objetos JavaScript, temos duas maneiras de declarar uma expressão regular, invocando o construtor ou de maneira literal.

Constructor

A primeira forma (e menos usada), é chamando o construtor do objeto RegExp:

O primeiro argumento que o objeto recebe (nosso padrão), pode ser qualquer coisa (JavaScript feelings). Porém, para o bom uso, ele deve ser uma string ou uma outra regex (sim, outra regex).

No caso da String, é necessário entender que as vezes precisaremos escapar os caracteres que possam ter outro significado. Quem aqui nunca usou um \n pra dar aquela quebra de linha?

Então, se quisermos considerar que a barra seja de fato uma barra, e não um "efeito especial", precisamos escapa-la com outra barra (._.):

const regex = new RegExp('\\w')

O segundo parâmetro é a flag que adiciona um comportamento em nosso motor da Regex. A mais popular e já comentada bastante é a flag g , que permite que o motor continue procurando por todo o alvo o seu padrão. Mas também existe outras bem importantes, como:

  • i : Ignora o case, ou seja, não difere letras maiúsculas ou minúsculas;
  • m : Permite que o padrão seja aplicado em múltiplas linhas. Bem útil no caso onde temos que aplicar âncoras e ainda assim queremos aplicar em várias linhas;
  • y : Força a regex só trazer os matches consecutivos, ou seja, se você tem um alvo que tem 2 resultados consecutivos e em seguida um caractere (ou conjunto) que não bate com seu padrão, ele só traz os primeiros resultados.
  • u : Habilita a capacidade da Regex engine de entender caracteres unicode e captura-los corretamente (exemplo: 𝌆).

Esses são as flags que o JavaScript aceita, mas se você é de outra linguagem, talvez tenha mais tipos diferentes.

Passando então a nossa expressão e a flag, temos uma declaração semelhante a essa:

const regex = new RegExp('\\w','g')

Literal

A segunda forma de declarar uma expressão regular é fazendo da forma literal, ou seja, passando uma expressão entre duas barras / e em seguida, passando as flags:

const regex = /\w/g

Bem mais fácil, não?

Mas Raul, quando eu uso uma ou outra?

Bom, lembra quando eu disse que podemos trabalhar as expressões por partes? Vamos pensar em uma expressão regular para capturar datas no formato DD/MM/YYYY:

Alvo

07/07/1995
14/08/1996
27/01/1937
08/01/1999
08/01/2099
08/21/2099
08/01/2399

Padrão

  • Dia: [0-3]\d\/
  • Mês: [01]\d\/
  • Ano: [12][0129]\d{2}

Poderíamos juntar todas essas expressões e declara-la de forma literal:

const dataPattern = /[0-3]\d\/[01]\d\/[12][0129]\d{2}/g

Entretanto, perceba que se um dia você resolver que precisa alterar sua expressão, vai bater o olho e sentir uma leve dificuldade de saber o que é o que. Então, como poderíamos resolver isso?

Bom, podemos declarar algumas variáveis com o pattern em string e depois concatena-los, passando para o construtor:

Sim, tivemos que escapar cada barra invertida que encontramos, mas agora o código (apesar de maior) ficou claro e caso precisamos alterar o pattern futuramente, não ficaremos confusos e com frio!


Métodos

Finalmente vamos começar a ver os métodos dos objetos do tipo RegExp. Assim como a maioria dos tipos de dados em Javascript, RegExp também possui vários métodos, mas vamos nos focar nos dois principais, exec e test . E talvez o segundo seja ainda mais útil que o segundo do ponto de vista do dia-a-dia.

Exec

Esse é o método que você irá utilizar quando você precisa recuperar o dado que está filtrando. Ele é aquele tipo de função em que precisamos iterar através de um while , pois, a cada vez que você executa o método, ele pula para o próximo resultado.

Para provar isso, veja o exemplo abaixo:

Perceba que no último console, chamamos o método novamente e ele foi para o próximo resultado da regex.

Aplicando o while para pegarmos todas as ocorrências, temos:

Quando o resultado de pattern.exec for undefined, automaticamente o while receberá false e sairá do loop.

Estrutura do resultado

Quando executamos o método exec , temos um um array e em seguida, esse array é atualizado e transformado em um object com algumas informações. São elas:

  1. O resultado encontrado. Você pode acessar através de: resultado[0]
  2. O index, ou seja, em qual posição do alvo foi encontrado aquele resultado. Você pode acessar através de: resultado.index
  3. O input, ou seja, qual alvo que estava sendo avaliado naquele momento. Você pode acessar através de resultado.input

Assim, perceba que é dentro do laço while que você extrairá seus dados.


Test

O método test, como disse anteriormente, talvez seja muito mais útil que o exec no dia-a-dia. Mas, porque?

Bem, o test apenas valida se aquele alvo contém o padrão que você definiu, retornando um true ou false .

Para entender melhor, vamos ver o exemplo abaixo:

Aqui, utilizamos o padrão de quebrar em partes a regex. Ficou um pouco confuso porque como visto no artigo sobre meta-caractere (LINK) e grupos (LINK), o () é avaliado como criação de um grupo, logo, precisamos escapa-lo com uma barra invertida ( \ ). Porém como já visto, em strings precisamos escapar a barra invertida também.

O resultado do primeiro console é expressão criada. O do segundo é o teste de verdadeiro ou falso para saber se aquele alvo obedece a nossa expressão. Dessa maneira, podemos ter algo parecido com:

if(regexTelefone.test(alvo)){
//Faça alguma lógica/ação
}else{
throw new Error('Número de telefone fora da máscara')
}

Mais e mais usos de Regex

Além dos métodos da própria regex, há outros tipos de dados que aceitam expressões regulares como parâmetro ou usamos regex manipular resultados. Abaixo alguns deles:

String.replace

String.split

String.match

Array.filter


Conclusão

Com isso, fechamos a saga das expressões regulares (mentira, ainda tem um bônus). Espero ter consigo fazer você pelo menos sentir interesse de usar pequenas expressões no dia-a-dia, afinal, podemos usa-las em diversos lugares que não foram citados, como por exemplo, o próprio terminal.

Obrigado por ter acompanhado até aqui! E…

For sure! =p

Fontes

One clap, two clap, three clap, forty?

By clapping more or less, you can signal to us which stories really stand out.