LASTNONBLANK https://interactivechaos.ovh/es es Nombre del producto más vendido https://interactivechaos.ovh/es/dax/scenario/nombre-del-producto-mas-vendido <span class="field field--name-title field--type-string field--label-hidden">Nombre del producto más vendido</span> <span class="field field--name-uid field--type-entity-reference field--label-hidden"><span lang="" about="/es/user/1" typeof="schema:Person" property="schema:name" datatype="">admin</span></span> <span class="field field--name-created field--type-created field--label-hidden">Mar, 15/01/2019 - 15:14</span> <div class="clearfix text-formatted field field--name-body field--type-text-with-summary field--label-hidden field__item"><p>Calcular el importe total de ventas para el producto más vendido es relativamente fácil. Si el campo que contiene los nombres de los productos es <em>'Product'[ProductName]</em> y la medida <em>[Total sales]</em> suma el campo correspondiente al importe de ventas, bastaría con crear la siguiente medida:</p> <div class="codigo"> <p>max_sales = MAXX(VALUES('Product'[ProductName]); [Total sales])</p> </div> <p>Básicamente estamos extrayendo los nombres de los productos con la función <a href="/dax/function/values">VALUES</a>, calculando las ventas totales para cada uno de ellos y quedándonos con el mayor valor utilizando la función <a href="/dax/function/maxx">MAXX</a>:</p> <img alt="Cifra de ventas totales correspondiente al producto más vendido" data-entity-type="file" data-entity-uuid="4d15db25-b820-4d55-a64a-11e6c7873911" src="/sites/default/files/inline-images/dax_scenario_nombre_producto_mas_vendido_01.JPG" class="align-center" width="465" height="207" loading="lazy" /><p>Sin embargo, extraer el nombre del producto correspondiente a dicha cifra no es tan sencillo. Una estrategia -una vez que sabemos cuál es su cifra de ventas- sería recorrer la lista de nombres de productos, calcular su cifra de ventas, compararla con el valor máximo ya conocido y devolver el nombre si la cifra calculada coincide. En pseudo-código, sería algo así:</p> <div class="codigo"> <p>max_sales = valor de ventas para el producto más vendido</p> <p>Para cada nombre de producto:</p> <p>    sales = valor de ventas</p> <p>    si sales = max_sales:</p> <p>        return nombre de producto</p> </div> <p>Una forma de devolver solo el nombre de producto de interés es recorrer el listado de nombres de producto, comparar su cifra de ventas con la cifra máxima ya calculada y devolviendo un valor no vacío si coinciden y un <a href="/dax/function/blank">BLANK()</a> si no coinciden, y usar a continuación la función iteractiva <a href="/dax/function/firstnonblank">FIRSTNONBLANK</a> que extrae el nombre del producto correspondiente al primer (y único en este ejemplo) valor no vacío. En pseudo-código sería:</p> <div class="codigo"> <p>max_sales = valor de ventas para el producto más vendido</p> <p>return</p> <p>    FIRSTNONBLANK(</p> <p>        Para cada nombre de producto</p> <p>        sales = valor de ventas</p> <p>        si sales = max_sales:</p> <p>            return cualquier valor no vacío</p> <p>        else:</p> <p>            return BLANK()</p> <p>    )</p> </div> <p>Es decir, podemos verlo como si estuviésemos generando una tabla temporal de una única columna en la que todos los valores serían blank salvo el correspondiente al producto para el que se cumpliese la condición sales = max_sales (es decir, al producto más vendido). El código anterior en DAX quedaría de la siguiente forma:</p> <div class="codigo"> <p>Max sales product =</p> <p>    VAR</p> <p>        max_sales = MAXX(VALUES('Product'[ProductName]); [Total sales])</p> <p>    RETURN</p> <p>        FIRSTNONBLANK(</p> <p>            'Product'[ProductName];</p> <p>            IF(</p> <p>                [Total sales] = max_sales ;</p> <p>                1;</p> <p>                BLANK()</p> <p>            )</p> <p>        )</p> </div> <p>Comenzamos calculando el valor máximo de ventas (<em>max_sales</em>) y devolviendo el nombre del producto correspondiente al primer (y único) valor no vacío de una imaginaria tabla intermedia, tabla que creamos a partir de la columna conteniendo los nombres de los productos en la que "sustituímos" el nombre del producto más vendido por un 1 (podría ser cualquier otro valor) y el resto de nombres de productos por un blank utilizando la función <a href="/dax/function/if">IF</a>:</p> <img alt="Nombre del producto con mayores ventas totales" data-entity-type="file" data-entity-uuid="d95f7abc-caec-4c13-a131-40b2d7adf918" src="/sites/default/files/inline-images/dax_scenario_nombre_producto_mas_vendido_02.JPG" class="align-center" width="526" height="396" loading="lazy" /><p>Para confirmar que el resultado es correcto podemos crear una visualización con la lista de productos y sus ventas totales, y ordenar dicha tabla según la cifra de ventas:</p> <img alt="Listado ordenado de productos por sus ventas totales" data-entity-type="file" data-entity-uuid="3ec18874-8211-46d1-a026-3ad2abd9e35a" src="/sites/default/files/inline-images/dax_scenario_nombre_producto_mas_vendido_03.JPG" class="align-center" width="492" height="505" loading="lazy" /><p>Como la "tabla temporal" solo contiene un único valor no vacío, también podríamos haber utilizado la función <a href="/dax/function/lastnonblank">LASTNONBLANK</a>:</p> <div class="codigo"> <p>Max sales product =</p> <p>    VAR</p> <p>        max_sales = MAXX(VALUES('Product'[ProductName]); [Total sales])</p> <p>    RETURN</p> <p>        LASTNONBLANK(</p> <p>            'Product'[ProductName];</p> <p>            IF(</p> <p>                [Total sales] = max_sales ;</p> <p>                1;</p> <p>                BLANK()</p> <p>            )</p> <p>)</p> </div> <img alt="Código alternativo usando la función LASTNONBLANK" data-entity-type="file" data-entity-uuid="91de6bd0-e7e0-403e-8b7b-6fe56db90e0d" src="/sites/default/files/inline-images/dax_scenario_nombre_producto_mas_vendido_04.JPG" class="align-center" width="542" height="402" loading="lazy" /><p> </p> </div> <div class="field field--name-field-funciones-dax-involucradas field--type-entity-reference field--label-above"> <div class="field__label">Funciones DAX involucradas</div> <div class="field__items"> <div class="field__item"><a href="/es/taxonomy/term/39" hreflang="es">MAXX</a></div> <div class="field__item"><a href="/es/taxonomy/term/30" hreflang="es">VALUES</a></div> <div class="field__item"><a href="/es/taxonomy/term/50" hreflang="es">LASTNONBLANK</a></div> <div class="field__item"><a href="/es/taxonomy/term/29" hreflang="es">IF</a></div> <div class="field__item"><a href="/es/taxonomy/term/31" hreflang="es">BLANK</a></div> <div class="field__item"><a href="/es/taxonomy/term/68" hreflang="es">VAR</a></div> </div> </div> Tue, 15 Jan 2019 14:14:28 +0000 admin 378 at https://interactivechaos.ovh