PostgreSQL: Funções Integradas do PostgreSQL: Guia Detalhado

Última atualização: 2026-08-26

1. O Que Você Vai Aprender


2. A História

Alice é uma analista de dados de e-commerce que precisa gerar um relatório mensal de vendas no fim do mês. O relatório deve:

  1. Formatar order_date como 2025-Junho-30
  2. Concatenar o nome do cliente + número do pedido em um título de linha do relatório
  3. Tratar NULL: valores de desconto ausentes assumem padrão 0
  4. Cálculo de dinheiro: total preciso com imposto e líquido após desconto
  5. Uso de sequência: gerar números sequenciais para as linhas do relatório

Alice precisa combinar as funções integradas do PostgreSQL para produzir o relatório.


3. Conceito: Funções Matemáticas

(1) Funções Matemáticas Básicas

Função Significado Exemplo Resultado
ABS(x) Valor absoluto ABS(-15) 15
ROUND(x, n) Arredondar para n decimais ROUND(3.1415, 2) 3.14
CEIL(x) Arredondar para cima CEIL(3.2) 4
FLOOR(x) Arredondar para baixo FLOOR(3.8) 3
MOD(x, y) Módulo MOD(10, 3) 1
POWER(x, y) Potência POWER(2, 10) 1024
SQRT(x) Raiz quadrada SQRT(144) 12
SIGN(x) Sinal SIGN(-5) -1
TRUNC(x, n) Truncar TRUNC(3.1415, 2) 3.14

▶ Exemplo: ROUND para Decimais Fixos

SQL
SELECT
  unit_price,
  ROUND(unit_price, 0) AS rounded_0,
  ROUND(unit_price, 2) AS rounded_2
FROM products
WHERE category = 'Electronics';

Output:

TEXT 📖 Somente leitura
 id | name     | value 
----+----------+-------
  1 | example  | 42
(1 row)

▶ Exemplo: CEIL / FLOOR Arredondamento

SQL
SELECT
  total_amount,
  CEIL(total_amount) AS ceil_value,
  FLOOR(total_amount) AS floor_value,
  total_amount - FLOOR(total_amount) AS decimal_part
FROM orders
WHERE order_status = 'completed';

Output:

TEXT 📖 Somente leitura
 id | name     | value 
----+----------+-------
  1 | example  | 42
(1 row)

(2) ROUND vs TRUNC vs CEIL/FLOOR

Função Comportamento Resultado 3.5 Resultado 3.2 Resultado -3.5
ROUND(x) Arredondar para o inteiro mais próximo 4 3 -4
TRUNC(x) Truncar decimais 3 3 -3
CEIL(x) Arredondar para cima 4 4 -3
FLOOR(x) Arredondar para baixo 3 3 -4

▶ Exemplo: MOD Resto

SQL
SELECT
  order_id,
  total_amount,
  MOD(order_id, 10) AS partition_key,
  total_amount * POWER(1.08, 1) AS with_annual_tax
FROM orders
WHERE order_status = 'completed';

Output:

TEXT 📖 Somente leitura
 id | name     | value 
----+----------+-------
  1 | example  | 42
(1 row)

▶ Exemplo: SQRT e POWER Combinados

SQL
SELECT
  unit_price,
  SQRT(unit_price) AS price_sqrt,
  POWER(unit_price, 1.0 / 3) AS price_cbrt
FROM products
WHERE unit_price > 0
ORDER BY unit_price DESC;

Output:

TEXT 📖 Somente leitura
 id | name     | value 
----+----------+-------
  1 | example  | 42
(1 row)

4. Conceito: Funções de String

(1) Maiúsculas/Minúsculas e Comprimento

Função Significado Exemplo Resultado
LOWER(s) Para minúsculas LOWER('Hello') hello
UPPER(s) Para maiúsculas UPPER('Hello') HELLO
INITCAP(s) Capitalizar primeira letra INITCAP('hello world') Hello World
LENGTH(s) Contagem de caracteres LENGTH('PostgreSQL') 10
BIT_LENGTH(s) Comprimento em bits BIT_LENGTH('A') 8
CHAR_LENGTH(s) Igual a LENGTH CHAR_LENGTH('ABC') 3

▶ Exemplo: Conversão de Maiúsculas/Minúsculas

SQL
SELECT
  product_name,
  LOWER(product_name) AS lower_name,
  UPPER(product_name) AS upper_name,
  INITCAP(LOWER(product_name)) AS title_name
FROM products
WHERE is_active = true;

Output:

TEXT 📖 Somente leitura
 id | name     | value 
----+----------+-------
  1 | example  | 42
(1 row)

(2) Concatenação e Substring

Função Significado Exemplo Resultado
CONCAT(s1, s2, ...) Concatenar (NULL-safe) CONCAT('A', NULL, 'B') AB
CONCAT_WS(sep, s1, s2) Concatenar com separador CONCAT_WS('-', 'A','B') A-B
`s1 s2` Concatenar (NULL-unsafe)
SUBSTRING(s FROM n FOR len) Substring SUBSTRING('Hello' FROM 2 FOR 3) ell
LEFT(s, n) n caracteres à esquerda LEFT('Hello', 3) Hel
RIGHT(s, n) n caracteres à direita RIGHT('Hello', 2) lo

▶ Exemplo: CONCAT vs ||

SQL
SELECT
  product_name,
  CONCAT(product_name, ' - $', unit_price) AS safe_concat,
  product_name || ' - $' || unit_price AS unsafe_concat,
  CONCAT_WS(' | ', product_name, category, unit_price::TEXT) AS ws_concat
FROM products;

Output:

TEXT 📖 Somente leitura
 id | name     | value 
----+----------+-------
  1 | example  | 42
(1 row)

(3) Encontrar e Substituir

Função Significado Exemplo Resultado
POSITION(sub IN s) Encontrar posição POSITION('sql' IN 'postgresql') 8
STRPOS(s, sub) Igual (args invertidos) STRPOS('postgresql', 'sql') 8
REPLACE(s, from, to) Substituir REPLACE('ABC', 'B', 'X') AXC
OVERLAY(s PLACING t FROM n) Sobrescrever OVERLAY('XXXX' PLACING 'AB' FROM 2) XABX
SPLIT_PART(s, delim, n) Dividir por delimitador, pegar n-ésimo SPLIT_PART('A-B-C', '-', 2) B
TRIM(s) Remover espaços ao redor TRIM(' Oi ') Oi
LTRIM(s) Remover espaços à esquerda LTRIM(' Oi ') Oi
RTRIM(s) Remover espaços à direita RTRIM(' Oi ') Oi
RPAD(s, len, fill) Preencher à direita RPAD('Oi', 5, 'x') Oixxx
LPAD(s, len, fill) Preencher à esquerda LPAD('42', 5, '0') 00042
REVERSE(s) Inverter REVERSE('ABC') CBA

▶ Exemplo: SPLIT_PART para Analisar Campos CSV

SQL
SELECT
  product_name,
  SPLIT_PART(category_path, '/', 1) AS top_category,
  SPLIT_PART(category_path, '/', 2) AS sub_category
FROM products
WHERE category_path LIKE '%/%';

Output:

TEXT 📖 Somente leitura
 id | name     | value 
----+----------+-------
  1 | example  | 42
(1 row)

▶ Exemplo: REPLACE e TRIM Combinados

SQL
SELECT
  TRIM(product_name) AS clean_name,
  REPLACE(product_name, '  ', ' ') AS no_double_spaces
FROM products
WHERE is_active = true;

Output:

TEXT 📖 Somente leitura
 id | name     | value 
----+----------+-------
  1 | example  | 42
(1 row)

▶ Exemplo: LPAD para Formatar Números

SQL
SELECT
  LPAD(product_id::TEXT, 8, '0') AS formatted_id,
  product_name,
  unit_price
FROM products
ORDER BY product_id;

Output:

TEXT 📖 Somente leitura
 id | name     | value 
----+----------+-------
  1 | example  | 42
(1 row)

5. Conceito: Funções de Data

(1) Obtendo o Horário Atual

Função Tipo de retorno Descrição
CURRENT_DATE DATE Data atual
CURRENT_TIME TIME WITH TZ Hora atual (com fuso horário)
CURRENT_TIMESTAMP TIMESTAMP WITH TZ Data e hora atuais
NOW() TIMESTAMP WITH TZ Igual a CURRENT_TIMESTAMP
LOCALTIMESTAMP TIMESTAMP Hora atual (sem fuso horário)
CLOCK_TIMESTAMP() TIMESTAMP WITH TZ Relógio em tempo real (muda a cada chamada)

▶ Exemplo: Obtendo o Horário Atual

SQL
SELECT
  CURRENT_DATE AS today,
  CURRENT_TIMESTAMP AS now_ts,
  NOW() AS now_func,
  LOCALTIMESTAMP AS local_ts;

Output:

TEXT 📖 Somente leitura
 id | name     | value 
----+----------+-------
  1 | example  | 42
(1 row)

(2) Aritmética de Datas

Expressão Significado Exemplo de resultado
DATE '2025-01-15' + 7 Adicionar dias 2025-01-22
DATE '2025-01-15' - DATE '2025-01-01' Diferença em dias 14
NOW() + INTERVAL '30 days' Adicionar intervalo 30 dias depois
NOW() - INTERVAL '1 year' Subtrair intervalo 1 ano atrás
AGE(end, start) Descrição do intervalo 1 ano 2 meses 3 dias
AGE(timestamp) Intervalo desde agora

▶ Exemplo: Aritmética de Datas

SQL
SELECT
  order_date,
  order_date + 7 AS due_date,
  CURRENT_DATE - order_date AS days_ago,
  AGE(CURRENT_DATE, order_date) AS age_since_order
FROM orders
WHERE order_date >= CURRENT_DATE - INTERVAL '90 days';

Output:

TEXT 📖 Somente leitura
 id | name     | value 
----+----------+-------
  1 | example  | 42
(1 row)

(3) EXTRACT e DATE_TRUNC

Uso Significado Exemplo Resultado
EXTRACT(YEAR FROM ts) Extrair ano EXTRACT(YEAR FROM NOW()) 2025
EXTRACT(MONTH FROM ts) Extrair mês EXTRACT(MONTH FROM NOW()) 6
EXTRACT(DAY FROM ts) Extrair dia
EXTRACT(DOW FROM ts) Dia da semana (0=Domingo) 1 (Segunda)
EXTRACT(QUARTER FROM ts) Trimestre 2
EXTRACT(EPOCH FROM ts) Timestamp Unix 1719500400
DATE_TRUNC('month', ts) Truncar para início do mês DATE_TRUNC('month', '2025-06-15') 2025-06-01
DATE_TRUNC('year', ts) Truncar para início do ano 2025-01-01

▶ Exemplo: EXTRACT para Obter Partes da Data

SQL
SELECT
  order_date,
  EXTRACT(YEAR FROM order_date) AS order_year,
  EXTRACT(MONTH FROM order_date) AS order_month,
  EXTRACT(QUARTER FROM order_date) AS order_quarter,
  EXTRACT(DOW FROM order_date) AS weekday
FROM orders
WHERE order_status = 'completed';

Output:

TEXT 📖 Somente leitura
 id | name     | value 
----+----------+-------
  1 | example  | 42
(1 row)

▶ Exemplo: DATE_TRUNC Agregação Mensal

SQL
SELECT
  DATE_TRUNC('month', order_date) AS month_start,
  COUNT(*) AS order_count,
  SUM(total_amount) AS monthly_revenue
FROM orders
WHERE order_status = 'completed'
  AND order_date >= DATE_TRUNC('year', CURRENT_DATE)
GROUP BY DATE_TRUNC('month', order_date)
ORDER BY month_start;

Output:

TEXT 📖 Somente leitura
 count 
-------
     5
(1 row)

(4) TO_CHAR e TO_DATE

Função Finalidade Exemplo
TO_CHAR(ts, fmt) Hora → string TO_CHAR(NOW(), 'YYYY-Month-DD')
TO_DATE(s, fmt) String → data TO_DATE('2025-06-15', 'YYYY-MM-DD')
TO_TIMESTAMP(s, fmt) String → timestamp TO_TIMESTAMP('2025-06-15 14:30', 'YYYY-MM-DD HH24:MI')

Modelos de formato comuns:

Modelo Significado Exemplo de saída
YYYY Ano com 4 dígitos 2025
YY Ano com 2 dígitos 25
Month Nome completo do mês June
MON Mês abreviado Jun
MM Mês com 2 dígitos 06
DD Dia com 2 dígitos 15
HH24 24 horas 14
MI Minuto 30
SS Segundo 45

▶ Exemplo: TO_CHAR Formatação de Data

SQL
SELECT
  order_id,
  TO_CHAR(order_date, 'YYYY-Month-DD') AS formatted_date,
  TO_CHAR(order_date, 'YYYY-MM-DD HH24:MI:SS') AS full_datetime,
  TO_CHAR(total_amount, 'FM$999,999.00') AS formatted_amount
FROM orders
WHERE order_status = 'completed';

Output:

TEXT 📖 Somente leitura
 id | name     | value 
----+----------+-------
  1 | example  | 42
(1 row)

▶ Exemplo: TO_DATE String para Data

SQL
SELECT
  TO_DATE('2025-06-15', 'YYYY-MM-DD') AS parsed_date,
  TO_DATE('15/06/2025', 'DD/MM/YYYY') AS eu_date,
  TO_DATE('Jun 15 2025', 'Mon DD YYYY') AS us_date;

Output:

TEXT 📖 Somente leitura
 id | name     | value 
----+----------+-------
  1 | example  | 42
(1 row)

6. Conceito: Funções Condicionais

(1) COALESCE

COALESCE(val1, val2, ...) retorna o primeiro argumento não NULL e é a função de tratamento de NULL mais comum.

Expressão Resultado
COALESCE(NULL, NULL, 'padrão') padrão
COALESCE(100, 0) 100
COALESCE(NULL, 0) 0

▶ Exemplo: COALESCE para Descontos Ausentes

SQL
SELECT
  product_name,
  unit_price,
  discount_rate,
  COALESCE(discount_rate, 0) AS safe_discount,
  unit_price * (1 - COALESCE(discount_rate, 0)) AS net_price
FROM products;

Output:

TEXT 📖 Somente leitura
 count 
-------
     5
(1 row)

(2) NULLIF

NULLIF(val1, val2) retorna NULL quando os dois valores são iguais, caso contrário retorna val1. Comumente usado para evitar erros de divisão por zero.

Expressão Resultado
NULLIF(100, 100) NULL
NULLIF(100, 0) 100
100 / NULLIF(0, 0) NULL (em vez de erro)

▶ Exemplo: NULLIF para Prevenir Divisão por Zero

SQL
SELECT
  product_name,
  unit_price,
  total_sold,
  unit_price / NULLIF(total_sold, 0) AS revenue_per_unit
FROM products
WHERE is_active = true;

Output:

TEXT 📖 Somente leitura
 id | name     | value 
----+----------+-------
  1 | example  | 42
(1 row)

(3) GREATEST / LEAST

Função Significado Exemplo Resultado
GREATEST(a, b, c) Retornar o máximo GREATEST(10, 20, 5) 20
LEAST(a, b, c) Retornar o mínimo LEAST(10, 20, 5) 5

▶ Exemplo: GREATEST / LEAST

SQL
SELECT
  product_name,
  unit_price,
  COALESCE(discount_rate, 0) AS discount,
  unit_price * (1 - GREATEST(COALESCE(discount_rate, 0), 0.5)) AS capped_net_price,
  LEAST(unit_price, 999.99) AS price_cap
FROM products
WHERE is_active = true;

Output:

TEXT 📖 Somente leitura
 count 
-------
     5
(1 row)

(4) Comparação de Funções Condicionais

Função Cenário Tratamento de NULL
COALESCE(a, b) Fornecer um padrão Retorna o primeiro não NULL
NULLIF(a, b) NULL quando valores iguais Não trata NULL
GREATEST(a, b) Pegar o máximo Retorna NULL se algum for NULL
LEAST(a, b) Pegar o mínimo Retorna NULL se algum for NULL

7. Conceito: Funções de Sequência

(1) Funções de Operação de Sequência

Função Significado Exemplo
NEXTVAL('seq_name') Incrementar e retornar próximo valor NEXTVAL('order_id_seq') → 1001
CURRVAL('seq_name') Retornar último NEXTVAL da sessão atual CURRVAL('order_id_seq') → 1001
SETVAL('seq_name', n) Definir o valor atual da sequência SETVAL('order_id_seq', 5000)
SETVAL('seq_name', n, false) Definir valor; próximo NEXTVAL retorna n SETVAL('order_id_seq', 5000, false)

▶ Exemplo: NEXTVAL para Gerar Números

SQL
INSERT INTO orders (order_id, customer_id, total_amount, order_date)
VALUES (NEXTVAL('order_id_seq'), 1001, 299.99, CURRENT_DATE);

Output:

TEXT 📖 Somente leitura
INSERT 0 1

▶ Exemplo: CURRVAL para Visualizar Valor Atual

SQL
SELECT
  NEXTVAL('report_seq') AS report_number,
  CURRVAL('report_seq') AS current_seq;

Output:

TEXT 📖 Somente leitura
 id | name     | value 
----+----------+-------
  1 | example  | 42
(1 row)

(2) SETVAL para Redefinir uma Sequência

Chamada Próximo NEXTVAL retorna
SETVAL('seq', 100) 101
SETVAL('seq', 100, false) 100
SETVAL('seq', 1, false) 1 (redefinir para início)

▶ Exemplo: SETVAL para Redefinir uma Sequência

SQL
-- Redefinir sequência para começar de 1 novamente
SELECT SETVAL('order_id_seq', 1, false);

-- Definir sequência para um valor alto específico (ex., após migração de dados)
SELECT SETVAL('order_id_seq', (SELECT MAX(order_id) FROM orders));

Output:

TEXT 📖 Somente leitura
 id | name     | value 
----+----------+-------
  1 | example  | 42
(1 row)

8. Fluxograma: Escolhendo uma Função

100%
flowchart TD
    A[Qual operação você precisa?] --> B{Tipo de dado?}
    B -->|Numérico| C{O que você precisa?}
    B -->|String| D{O que você precisa?}
    B -->|Data| E{O que você precisa?}
    B -->|Tratamento de NULL| F[COALESCE / NULLIF]
    C -->|Arredondar| G[ROUND / TRUNC]
    C -->|Arredondar para inteiro| H[CEIL / FLOOR]
    C -->|Calcular| I[ABS / MOD / POWER / SQRT]
    D -->|Concatenar| J[CONCAT / ||]
    D -->|Substring| K[SUBSTRING / LEFT / RIGHT]
    D -->|Substituir| L[REPLACE / SPLIT_PART]
    D -->|Maiúsculas/Minúsculas| M[LOWER / UPPER / INITCAP]
    D -->|Remover espaços| N[TRIM / LTRIM / RTRIM]
    E -->|Hora atual| O[NOW / CURRENT_TIMESTAMP]
    E -->|Extrair parte| P[EXTRACT]
    E -->|Truncar| Q[DATE_TRUNC]
    E -->|Formatar| R[TO_CHAR]
    E -->|Analisar| S[TO_DATE / TO_TIMESTAMP]

    style A fill:#e1f5fe
    style F fill:#c8e6c9

9. Exemplo Abrangente

Alice produziu um relatório mensal de vendas completo.

SQL
-- Etapa 1: Relatório de receita mensal com formatação de data
SELECT
  TO_CHAR(DATE_TRUNC('month', order_date), 'YYYY-Month') AS report_month,
  COUNT(*) AS order_count,
  SUM(total_amount)::NUMERIC(12,2) AS gross_revenue,
  SUM(total_amount * 0.08)::NUMERIC(12,2) AS tax_collected,
  SUM(total_amount * 1.08)::NUMERIC(12,2) AS total_with_tax
FROM orders
WHERE order_status = 'completed'
  AND order_date >= DATE_TRUNC('year', CURRENT_DATE)
GROUP BY DATE_TRUNC('month', order_date)
ORDER BY report_month;

-- Etapa 2: Resumo de produtos com formatação de string e tratamento de NULL
SELECT
  LPAD(p.product_id::TEXT, 6, '0') AS product_code,
  INITCAP(LOWER(p.product_name)) AS display_name,
  CONCAT('$', ROUND(p.unit_price, 2)) AS price_label,
  COALESCE(p.discount_rate, 0) AS discount,
  ROUND(p.unit_price * (1 - COALESCE(p.discount_rate, 0)), 2) AS net_price,
  LEAST(ROUND(p.unit_price * (1 - COALESCE(p.discount_rate, 0)), 2), 999.99) AS capped_price
FROM products p
WHERE p.is_active = true
  AND p.unit_price > NULLIF(p.cost_price, 0)
ORDER BY net_price DESC;

-- Etapa 3: Resumo de pedidos por cliente com cálculo de idade
SELECT
  CONCAT(c.first_name, ' ', c.last_name) AS customer_name,
  COUNT(o.order_id) AS total_orders,
  SUM(o.total_amount)::NUMERIC(12,2) AS lifetime_value,
  AGE(MAX(o.order_date), MIN(o.order_date)) AS customer_span,
  EXTRACT(YEAR FROM AGE(CURRENT_DATE, c.register_date)) AS years_since_join
FROM customers c
JOIN orders o ON o.customer_id = c.customer_id
WHERE o.order_status = 'completed'
GROUP BY c.customer_id, c.first_name, c.last_name, c.register_date
ORDER BY lifetime_value DESC
FETCH FIRST 25 ROWS ONLY;

❓ Perguntas Frequentes

P: Qual é a diferença entre CONCAT e ||? R: CONCAT ignora NULL (concatena as partes não NULL), enquanto || retorna NULL para todo o resultado se algum operando for NULL. Para concatenação NULL-safe, use CONCAT ou CONCAT_WS.

P: ROUND(2.5) é igual a 2 ou 3? R: O ROUND do PostgreSQL usa "arredondamento bancário" (round half to even), então ROUND(2.5) = 2 e ROUND(3.5) = 4. Isso difere do arredondamento em algumas linguagens.

P: EXTRACT(DOW FROM date) retorna 0 ou 7 para Domingo? R: DOW retorna 0–6, onde 0 é Domingo, 1 é Segunda-feira e 6 é Sábado. Para o padrão ISO (1=Segunda, 7=Domingo), use EXTRACT(ISODOW FROM date).

P: DATE_TRUNC pode truncar para a hora? R: Sim. DATE_TRUNC suporta níveis de precisão incluindo microssegundo, milissegundo, segundo, minuto, hora, dia, semana, mês, trimestre, ano, década, século e milênio.

P: COALESCE pode aceitar tipos diferentes? R: Sim, mas todos os argumentos devem ser implicitamente conversíveis para o mesmo tipo. Por exemplo, COALESCE(NULL, 0, 0.5) converte todos os valores para NUMERIC.

P: CURRVAL pode ser usado antes de chamar NEXTVAL? R: Não. CURRVAL requer que a sessão atual já tenha chamado NEXTVAL naquela sequência, caso contrário gera erro "currval of sequence is not yet defined in this session".

P: O que significa o prefixo FM ao formatar números com TO_CHAR? R: FM (Fill Mode) remove o preenchimento de zeros à esquerda e espaços à direita. TO_CHAR(42, 'FM00000') = '42' (sem zeros à esquerda), enquanto TO_CHAR(42, '00000') = '00042'.

P: Qual é a diferença entre AGE e subtração para diferenças de data? R: DATE1 - DATE2 retorna um número inteiro de dias; AGE(DATE1, DATE2) retorna um INTERVAL incluindo anos, meses e dias (ex., 1 ano 2 meses 3 dias) — mais amigável para humanos, mas menos preciso que a subtração.


📖 Resumo


📝 Exercícios

  1. ⭐ Escreva uma consulta que selecione product_name e unit_price de products, use CONCAT para construir um rótulo de preço (formato R$99,99), use ROUND para manter dois decimais e ordene por preço decrescente.

  2. ⭐⭐ Escreva uma consulta que gere um relatório mensal de vendas de 2025: agrupe por mês com DATE_TRUNC('month', order_date), formate o mês com TO_CHAR como YYYY-MM, compute a contagem mensal de pedidos e o valor total (NUMERIC(12,2)) e use COALESCE para tratar possíveis descontos NULL.

  3. ⭐⭐⭐ Escreva uma consulta que gere uma linha de relatório por cliente: junte o nome com CONCAT_WS, compute a duração de registro do cliente com AGE, extraia o ano de registro com EXTRACT, limite o desconto a 50% com GREATEST, previna divisão por zero ao computar o valor médio do pedido com NULLIF, formate o ID do cliente como um número de 6 dígitos com LPAD e, finalmente, gere a sequência da linha do relatório com NEXTVAL('report_seq').

Web-Tutorial.com

Equipe Técnica Web-Tutorial

Uma plataforma de tutoriais mantida por diversos desenvolvedores. Cada tutorial é escrito e revisado por profissionais da área correspondente. Trabalhamos para manter nosso conteúdo preciso e confiável — se encontrar algum problema, avise-nos.

100%