SAMEPERIODLASTYEAR e DATEADD em DAX: o que faz e quando usar (com exemplos)
Entenda SAMEPERIODLASTYEAR e DATEADD DAX na prática: sintaxe, exemplos, armadilhas de calendário e boas práticas para comparar com o período anterior.
Comparar com o ano passado parece trivial, até o número vir errado
Toda diretoria quer a mesma coisa no dashboard: quanto vendemos agora versus o mesmo período do ano passado. Parece uma conta de subtração. Mas é justamente aqui que a maioria dos modelos de Power BI quebra, retorna valores em branco sem explicação ou, pior, mostra um crescimento que não existe. O par de funções SAMEPERIODLASTYEAR e DATEADD DAX existe exatamente para resolver isso, e usá-las bem separa um relatório confiável de um que ninguém audita duas vezes.
Este artigo explica o que cada função faz, mostra a sintaxe real, dá exemplos conceituais que você pode adaptar e, principalmente, lista as armadilhas que fazem o resultado sair errado. Se a sua empresa depende dessas comparações para decidir orçamento, meta e comissão, vale ler até o fim.
O que é time intelligence e por que ele depende de uma tabela calendário
As funções de inteligência de tempo do DAX operam sobre datas. Elas pegam o conjunto de datas que está no contexto de filtro atual, por exemplo o mês de março de 2026, e o deslocam no tempo para produzir um novo conjunto de datas, por exemplo março de 2025. Esse novo conjunto vira o filtro de uma medida qualquer.
Para que isso funcione, o motor precisa de uma tabela de datas contínua e marcada como tabela de datas. Não é opcional, é pré-requisito. Uma tabela calendário adequada tem estas características:
- Uma linha por dia, sem lacunas, cobrindo todo o intervalo de dados mais os anos de comparação.
- Uma coluna de data com tipo de dados Date, granularidade de dia e nenhum horário embutido.
- Marcação como tabela de datas no modelo, via "Marcar como tabela de datas" no Power BI Desktop.
- Relacionamento ativo com a tabela fato pela coluna de data.
Se você ainda usa a data direto da tabela fato, ou confia na hierarquia automática de datas do Power BI, é hora de parar. A hierarquia automática cria tabelas ocultas por coluna, incha o modelo e não serve para comparações sérias. Tratamos disso em detalhe no nosso guia de modelagem e DAX: boas práticas no Power BI, e é a base de qualquer projeto de Power BI que a Fynx entrega.
Vale lembrar como o motor VertiPaq armazena isso por baixo: ele comprime colunas por cardinalidade. Uma coluna de data limpa, sem componente de hora, tem cardinalidade baixa e comprime muito bem. Uma coluna datetime com segundos explode a cardinalidade e degrada tanto a compressão quanto o desempenho das funções de tempo.
SAMEPERIODLASTYEAR: o atalho para o mesmo período um ano atrás
A função SAMEPERIODLASTYEAR recebe uma coluna de datas e devolve as mesmas datas deslocadas exatamente um ano para trás. É especializada, faz só isso, e é a mais legível quando o requisito é literalmente comparar com o ano anterior.
A sintaxe é direta:
SAMEPERIODLASTYEAR(Calendario[Data])
Ela quase nunca aparece sozinha. O padrão é usá-la dentro de CALCULATE para reescrever o contexto de filtro de uma medida existente. Conceitualmente:
Vendas Ano Anterior = CALCULATE([Vendas], SAMEPERIODLASTYEAR(Calendario[Data]))
Aqui [Vendas] é a sua medida base, algo como SUM(Fato[Valor]). O CALCULATE troca o conjunto de datas do contexto atual pelo mesmo período do ano passado, e a medida recalcula sobre esse novo conjunto. Se o usuário está olhando março de 2026, a medida devolve as vendas de março de 2025. Se ele desce para o dia 15 de março, devolve o dia 15 de março do ano anterior.
A grande vantagem é o tratamento de anos bissextos. SAMEPERIODLASTYEAR entende que fevereiro de um ano bissexto tem 29 dias e faz o alinhamento de forma coerente, sem você precisar tratar isso na mão.
DATEADD: a função geral para deslocar qualquer intervalo
DATEADD é a versão flexível. Em vez de assumir um ano para trás, você diz quantos períodos deslocar e qual a unidade. A sintaxe tem três argumentos:
DATEADD(Calendario[Data], número_de_intervalos, intervalo)
O segundo argumento é um inteiro, positivo para frente ou negativo para trás. O terceiro é uma das quatro unidades aceitas: DAY, MONTH, QUARTER ou YEAR. Alguns exemplos conceituais:
- Ano anterior:
DATEADD(Calendario[Data], -1, YEAR) - Mês anterior:
DATEADD(Calendario[Data], -1, MONTH) - Trimestre anterior:
DATEADD(Calendario[Data], -1, QUARTER) - Mesmo período daqui a um ano, para projeção:
DATEADD(Calendario[Data], 1, YEAR)
Repare que DATEADD(Calendario[Data], -1, YEAR) produz o mesmo resultado que SAMEPERIODLASTYEAR(Calendario[Data]). As duas são equivalentes para o caso de um ano atrás. A diferença é semântica e de intenção, não de resultado.
Um detalhe importante de comportamento: DATEADD não é uma soma ingênua de datas. Ela é consciente de calendário. Se você deslocar 31 de janeiro em um mês, ela não tenta criar um 31 de fevereiro inexistente. O motor ajusta a projeção para o fim de mês correspondente dentro do conjunto de datas presente, respeitando o número de dias de cada mês.
SAMEPERIODLASTYEAR ou DATEADD: qual escolher
Na prática, a escolha é sobre legibilidade e flexibilidade. A tabela abaixo resume:
| Critério | SAMEPERIODLASTYEAR | DATEADD |
|---|---|---|
| Deslocamento | Fixo em um ano para trás | Qualquer quantidade, para frente ou para trás |
| Unidades suportadas | Apenas ano | DAY, MONTH, QUARTER, YEAR |
| Legibilidade | Alta, o nome já diz tudo | Média, exige ler os argumentos |
| Caso de uso ideal | Comparação ano contra ano | Mês anterior, trimestre anterior, projeções, deslocamentos custom |
| Anos bissextos | Tratados automaticamente | Tratados automaticamente |
A recomendação honesta de consultor: use SAMEPERIODLASTYEAR quando o requisito for exatamente ano contra ano, porque quem for manter o relatório entende na hora. Use DATEADD para todo o resto, ou quando quiser padronizar todas as medidas de comparação com uma única função e só variar os parâmetros. Não existe ganho de desempenho relevante entre uma e outra no caso de um ano, então decida pela clareza.
Onde DATEADD realmente brilha é em cenários de mês anterior e trimestre anterior, que SAMEPERIODLASTYEAR simplesmente não cobre. Também é a escolha para deslocar para o futuro, útil em medidas de baseline para projeção.
As armadilhas que fazem o número sair errado
Aqui está o valor prático deste artigo. Time intelligence falha quase sempre pelos mesmos motivos.
Falta de tabela calendário contínua. Se a tabela de datas tiver lacunas, ou não cobrir o ano anterior, o deslocamento devolve vazio. Um erro clássico é a tabela começar em 2025 quando os dados vão até 2024 no comparativo. Garanta que o calendário cubra do primeiro ao último dia relevante, inclusive os anos de comparação.
Tabela não marcada como tabela de datas. Sem a marcação, o Power BI pode não aplicar corretamente a remoção implícita de filtros que as funções de tempo esperam. O sintoma é resultado inconsistente ao mudar o nível de granularidade do visual.
Usar a coluna de data da tabela fato em vez da dimensão calendário. As funções de tempo precisam operar sobre a dimensão de datas ligada por relacionamento. Passar a coluna da fato quebra a lógica de contexto e costuma retornar totais errados.
Filtro de ano fiscal ou intervalo parcial. Se o usuário filtra um intervalo que não fecha um ano completo, o deslocamento respeita esse intervalo parcial. Isso é correto, mas gera confusão quando alguém espera o ano cheio. Deixe claro no visual o que está sendo comparado.
Comparar mês corrente incompleto. Em março ainda em andamento, comparar contra março inteiro do ano passado infla a queda. Para isso existem variações com DATESMTD ou filtros de dia equivalente, que exigem tratamento explícito. Não é bug da função, é requisito de negócio mal especificado.
Relacionamento inativo ou papel duplo de data. Modelos com data de pedido e data de entrega precisam de USERELATIONSHIP dentro do CALCULATE, senão a função de tempo age sobre a relação ativa que talvez não seja a desejada.
A tabela a seguir mapeia sintoma e causa provável, que é como fazemos o diagnóstico em projetos de sustentação de BI:
| Sintoma no relatório | Causa mais provável |
|---|---|
| Medida do ano anterior sempre em branco | Calendário não cobre o ano anterior ou não está marcado como tabela de datas |
| Total geral correto, mas linhas erradas | Uso da coluna de data da fato em vez da dimensão |
| Comparação varia ao mudar o visual | Falta de marcação como tabela de datas |
| Queda exagerada no mês atual | Comparação de mês incompleto contra mês completo |
| Valor comparado ignora o filtro esperado | Relacionamento inativo sem USERELATIONSHIP |
Boas práticas para comparações de período que sobrevivem à auditoria
Depois de anos entregando modelos que a diretoria realmente usa, estas práticas são inegociáveis.
Construa uma única tabela calendário central, contínua, marcada como tabela de datas, e faça todas as medidas de tempo apontarem para ela. Nada de calendário por assunto.
Crie a medida base primeiro, por exemplo Vendas, e derive as comparações a partir dela com CALCULATE. Nunca repita a lógica de soma dentro da medida de comparação. Isso mantém consistência e facilita manutenção.
Padronize a nomenclatura. Se toda medida de ano anterior termina em "AA" e toda variação percentual em "% AA", qualquer pessoa lê o modelo sem manual. Combine SAMEPERIODLASTYEAR para o comparativo anual e DATEADD para as variações de mês e trimestre, mantendo o mesmo padrão de nome.
Trate a divisão de variação percentual com DIVIDE, que já lida com o denominador zero e evita erro visível ao usuário. Uma variação percentual conceitual fica assim:
Var % AA = DIVIDE([Vendas] - [Vendas AA], [Vendas AA])
Documente a intenção. Se a comparação é ano fiscal e não ano civil, isso muda a tabela calendário e precisa estar escrito. Governança de modelo não é burocracia, é o que evita retrabalho, e conecta com o trabalho de governança de dados que fazemos junto às áreas de negócio.
Se o seu ambiente já está em Microsoft Fabric, lembre que essas medidas rodam igual, seja em modelo Import ou Direct Lake lendo do OneLake. A lógica DAX de tempo não muda com a arquitetura de armazenamento, o que muda é o desempenho e o custo de capacidade. A engenharia por trás disso, modelagem dimensional e pipelines confiáveis, é escopo de engenharia de dados.
Um exemplo conceitual de conjunto de medidas
Para deixar concreto, um pacote mínimo de medidas de comparação que cobre a maior parte das perguntas de negócio:
Vendas = SUM(Fato[Valor]), a medida base.Vendas AA = CALCULATE([Vendas], SAMEPERIODLASTYEAR(Calendario[Data])), ano contra ano.Vendas Mês Anterior = CALCULATE([Vendas], DATEADD(Calendario[Data], -1, MONTH)), mês sobre mês.Vendas Trim Anterior = CALCULATE([Vendas], DATEADD(Calendario[Data], -1, QUARTER)), trimestre sobre trimestre.Var % AA = DIVIDE([Vendas] - [Vendas AA], [Vendas AA]), o crescimento percentual anual.
Com essas cinco medidas e uma boa tabela calendário, você atende dashboards de vendas, financeiro e operações sem reescrever fórmula. É esse tipo de padronização que reduz o custo de manutenção do BI ao longo do tempo e é uma das primeiras coisas que olhamos num discovery e assessment.
Perguntas frequentes
SAMEPERIODLASTYEAR e DATEADD dão o mesmo resultado?
Para deslocamento de exatamente um ano para trás, sim, são equivalentes. SAMEPERIODLASTYEAR(Calendario[Data]) produz o mesmo conjunto de datas que DATEADD(Calendario[Data], -1, YEAR). A diferença é que DATEADD também faz mês, trimestre e deslocamento para o futuro, enquanto SAMEPERIODLASTYEAR só faz ano para trás. Escolha pela clareza e pela necessidade de flexibilidade.
Por que minha medida de ano anterior fica em branco?
Quase sempre por causa da tabela calendário. Ou ela não cobre o ano de comparação, ou tem lacunas de dias, ou não foi marcada como tabela de datas no modelo. Verifique também se você está usando a coluna de data da dimensão calendário e não a da tabela fato. Corrigido isso, o vazio costuma desaparecer.
Preciso mesmo de uma tabela calendário separada?
Sim. As funções de inteligência de tempo do DAX foram desenhadas para operar sobre uma dimensão de datas dedicada, contínua e marcada como tal. Depender da coluna de data da fato ou da hierarquia automática de datas do Power BI leva a resultados inconsistentes e a um modelo mais pesado. É a base de qualquer projeto sério.
DATEADD funciona com semana?
Não diretamente. DATEADD aceita apenas DAY, MONTH, QUARTER e YEAR. Para comparar semana contra semana, você precisa de colunas próprias de semana na tabela calendário e de uma lógica de filtro específica, geralmente com CALCULATE e filtros sobre essas colunas, não com DATEADD direto.
Essas funções mudam no Microsoft Fabric ou no modo Direct Lake?
A lógica DAX é a mesma. Você escreve SAMEPERIODLASTYEAR e DATEADD igual, seja em modelo Import, DirectQuery ou Direct Lake lendo do OneLake. O que muda é o desempenho e o consumo de capacidade, medido em Capacity Units nas SKUs do Fabric. A fórmula e o requisito de tabela calendário continuam valendo.
Como comparar apenas o período já decorrido do mês atual?
Comparar um mês em andamento contra o mês inteiro do ano passado distorce a análise. A solução é limitar a comparação ao mesmo número de dias decorridos, combinando funções como DATESMTD com filtros de dia equivalente. Isso exige tratamento explícito na medida, porque é uma regra de negócio, não um comportamento padrão das funções de tempo.
Conclusão
SAMEPERIODLASTYEAR e DATEADD resolvem a comparação com período anterior de forma limpa, desde que o modelo tenha uma tabela calendário contínua e bem marcada. A função especializada ganha em legibilidade para ano contra ano, e a genérica ganha em flexibilidade para mês, trimestre e projeções. O que separa o relatório confiável do enganoso não é a fórmula em si, é a disciplina de modelagem por trás dela.
Se a sua empresa convive com comparativos que ninguém confia, ou quer padronizar o BI de vez, fale com a gente. A Fynx tem seis anos de mercado, mais de 50 clientes e mais de 2.000 soluções Microsoft entregues, e a gente resolve isso na raiz.
Quer aplicar isso na sua empresa?
A Fynx implementa BI, Power BI e Power Platform de ponta a ponta. Conte seu cenário e devolvemos um diagnóstico direto ao ponto.
Falar com um especialista