Usar funções de iterador
As funções de iterador avaliam uma expressão para cada linha em uma tabela. Elas oferecem flexibilidade e controle sobre como o modelo resume os dados.
As funções de resumo de coluna única, como SUM, COUNT, MIN e MAX, têm funções de iterador equivalentes com um sufixo "X", como SUMX, COUNTX, MINX e MAXX. As funções de iterador especializadas também existem para filtragem, classificação e cálculos semiaditivos ao longo do tempo.
Cada função de iterador exige uma tabela e uma expressão. A tabela pode ser uma tabela de modelo ou qualquer expressão que retorne uma tabela. A expressão deve retornar um único valor para cada linha.
As funções de resumo de coluna única, como SUM, atuam como abreviação. O Power BI converte SUM internamente em SUMX. Por exemplo, ambas as medidas a seguir retornam o mesmo resultado e têm o mesmo desempenho:
Revenue = SUM(Sales[Sales Amount])
Revenue =
SUMX(
Sales,
Sales[Sales Amount]
)
As funções de iterador avaliam a expressão de cada linha em uma tabela usando o contexto de linha, o que significa que elas processam uma linha de cada vez para calcular o resultado final. Em seguida, a tabela é avaliada no contexto de filtro. Por exemplo, se um visual de relatório filtrar pelo ano fiscal FY2020, a tabela Sales conterá apenas as linhas de vendas desse ano.
Importante
O uso de funções de iterador com tabelas grandes e expressões complexas pode diminuir o desempenho. Funções como SEARCH e LOOKUPVALUE podem ser caras. Quando possível, use RELATED para melhorar o desempenho.
Funções de iterador para resumo complexo
As funções de iterador permitem agregar mais de uma única coluna. Por exemplo, uma medida de receita pode multiplicar a quantidade da ordem, o preço unitário e um fator de desconto para cada linha e, em seguida, somar os resultados.
Revenue =
SUMX(
Sales,
Sales[Order Quantity] * Sales[Unit Price] * (1 - Sales[Unit Price Discount Pct])
)
As funções de iterador também podem fazer referência a tabelas relacionadas. A medida de desconto pode usar a função RELATED para acessar o preço de lista na tabela de produtos:
Discount =
SUMX(
Sales,
Sales[Order Quantity]
* (
RELATED('Product'[List Price]) - Sales[Unit Price]
)
)
A imagem a seguir mostra um visual de tabela com as colunas Month, Revenue e Discount. Revenue e Discount são as medidas criadas anteriormente.
Funções de iterador para resumo de maior granularidade
As funções de iterador também podem resumir dados em diferentes níveis de detalhes (granularidade). Por exemplo, talvez você queira calcular uma média no nível do item de linha ou no nível da ordem de venda.
Neste exemplo, a tabela Sales contém uma linha para cada item de linha em uma ordem de venda. Cada linha inclui detalhes, como número da ordem de venda, produto, quantidade vendida, preço unitário e desconto. Várias linhas podem ter o mesmo número de ordem de venda, representando itens diferentes na mesma ordem.
Para calcular a receita média por linha de ordem (item de linha), você pode usar a função AVERAGEX para iterar em cada linha na tabela Sales. A fórmula calcula a receita de cada item de linha e, em seguida, calcula a média do resultado em todos os itens de linha no contexto de filtro atual:
Revenue Avg Order Line =
AVERAGEX(
Sales,
Sales[Order Quantity] * Sales[Unit Price] * (1 - Sales[Unit Price Discount Pct])
)
Se desejar calcular a receita média por ordem de venda (e não por item de linha), você pode usar a função VALUES para obter uma lista de números exclusivos de ordem de venda primeiro. Em seguida, AVERAGEX itera em cada ordem de venda e calcula a média da receita total de cada ordem:
Revenue Avg Order =
AVERAGEX(
VALUES('Sales Order'[Sales Order]),
[Revenue]
)
A função VALUES retorna as ordens de venda exclusivas com base no contexto de filtro atual, portanto, AVERAGEX itera em cada ordem de venda para cada mês.
Classificando com funções de iterador
A função RANKX calcula classificações iterando em uma tabela e avaliando uma expressão para cada linha.
A direção da ordem pode ser crescente ou descendente. A receita de classificação geralmente usa ordem decrescente, portanto, o valor mais alto é classificado em primeiro lugar. A classificação de reclamações, por exemplo, pode usar ordem crescente, de modo que o valor mais baixo seja classificado em primeiro lugar. Por padrão, RANKX usa ordem decrescente e ignora classificações em casos de empate.
Por exemplo, uma medida de classificação de quantidade de produto pode usar RANKX e a função ALL para classificar produtos por quantidade.
Product Quantity Rank =
RANKX(
ALL('Product'[Product]),
[Quantity]
)
A função ALL remove filtros para que RANKX classifique todos os produtos. Na imagem a seguir, dois produtos empatam em décimo lugar, então, o próximo produto é classificado em décimo segundo lugar e a posição 11ª é ignorada.
Você também pode usar a classificação densa, que atribui a próxima classificação após um empate sem pular números. Para usar a classificação densa, a medida pode incluir o argumento DENSE:
Product Quantity Rank =
RANKX(
ALL('Product'[Product]),
[Quantity],
,
,
DENSE
)
Agora, após dois produtos empatarem em décimo lugar, o próximo produto é o décimo primeiro colocado e a numeração continua sequencialmente sem pular a 11ª posição.
Nesse visual, a linha total da medida Product Quantity Rank mostra um, pois o total de todos os produtos também é classificado e há apenas um valor.
Para evitar classificar o total, a medida pode usar a função HASONEVALUE para retornar BLANK, a menos que um único produto seja filtrado.
Product Quantity Rank =
IF(
HASONEVALUE('Product'[Product]),
RANKX(
ALL('Product'[Product]),
[Quantity],
,
,
DENSE
)
)
Agora, o total para Product Quantity Rank está em branco.
A função HASONEVALUE verifica se a coluna de produto tem um único valor no contexto de filtro. Isso é verdadeiro para cada grupo de produtos, mas não para o total, que representa todos os produtos.
As funções de iterador fornecem maneiras poderosas de resumir, agregar e classificar dados em modelos do Power BI. Elas dão suporte a cálculos complexos e permitem que você controle o nível de detalhes em seus relatórios.