1. Faro

Nivel 9 · Desafío final: foto del catálogo

La solicitud

De Jessica Turner, Gerente de Merchandising

“La reunión de la junta es el jueves y necesito una foto rápida del catálogo: una lista de precios con nuestro precio de oferta planeado del 10 %, la proporción del costo en cada precio y una lista limpia de los canales de venta y estados de pedido que usamos.”

Tu objetivo

Paso 1 de 3. Desde products, devuelve product_id, name, unit_price y sale_price, donde sale_price es unit_price reducido un 10 %, redondeado a 2 decimales.

  • Lee de la tabla productspendiente
  • Muestra exactamente product_id name unit_price sale_pricependiente
  • 120 filaspendiente

Paso 1 · tu consulta

SQL

Cargando el editor…

    ResultadoVista previa de products · presiona Ejecutar para ver el tuyo
    Vista previa de products
    product_idnamecategorysubcategoryunit_price
    101Vale Velvet LoveseatFurnitureSofas1659.00
    102Alder Oak Coffee TableFurnitureTables919.00
    103Orchard Rattan Dining ChairFurnitureChairs789.00
    104Upland Oak BookcaseFurnitureStorage429.00

    Mote revisa tu resultado

    Presiona Ejecutar. Cada fila que cumple el objetivo se vuelve una luciérnaga en tu linterna.

    Paso 2 · tu consulta

    SQL

    Cargando el editor…

      ResultadoVista previa de products · presiona Ejecutar para ver el tuyo
      Vista previa de products
      product_idnamecategorysubcategoryunit_price
      101Vale Velvet LoveseatFurnitureSofas1659.00
      102Alder Oak Coffee TableFurnitureTables919.00
      103Orchard Rattan Dining ChairFurnitureChairs789.00
      104Upland Oak BookcaseFurnitureStorage429.00

      Mote revisa tu resultado

      Presiona Ejecutar. Cada fila que cumple el objetivo se vuelve una luciérnaga en tu linterna.

      Paso 3 · tu consulta

      SQL

      Cargando el editor…

        ResultadoVista previa de orders · presiona Ejecutar para ver el tuyo
        Vista previa de orders
        order_idcustomer_idorder_datestatuschannel
        10011252023-01-01 20:51:19completedweb
        10021562023-01-02 07:58:46completedweb
        1003222023-01-02 10:25:27completedmarketplace
        1004482023-01-02 11:21:51completedmarketplace

        Mote revisa tu resultado

        Presiona Ejecutar. Cada fila que cumple el objetivo se vuelve una luciérnaga en tu linterna.

        Tablas

        Datos de la tienda Harbor & Pine, listos para consultar.

        products120 filas · 8 columnas
        • product_idinteger
        • namevarchar
        • categoryvarchar
        • subcategoryvarchar
        • unit_pricedecimal
        • unit_costdecimal
        • launched_ondate
        • is_activeboolean
        Primeras 5 filas de products
        product_idnamecategorysubcategoryunit_priceunit_costlaunched_onis_active
        101Vale Velvet LoveseatFurnitureSofas1659.00NULL2023-09-11true
        102Alder Oak Coffee TableFurnitureTables919.00503.502024-05-16true
        103Orchard Rattan Dining ChairFurnitureChairs789.00429.872023-05-27true
        104Upland Oak BookcaseFurnitureStorage429.00214.702022-12-20true
        105Avery Leather Bed FrameFurnitureBeds449.00232.702021-08-31true
        orders12,000 filas · 7 columnas
        • order_idinteger
        • customer_idinteger
        • order_datetimestamp
        • statusvarchar
        • channelvarchar
        • shipping_feedecimal
        • coupon_codevarchar
        Primeras 5 filas de orders
        order_idcustomer_idorder_datestatuschannelshipping_feecoupon_code
        10011252023-01-01 20:51:19completedweb0.00NULL
        10021562023-01-02 07:58:46completedweb0.00NULL
        1003222023-01-02 10:25:27completedmarketplace4.99WELCOME10
        1004482023-01-02 11:21:51completedmarketplace4.99WELCOME10
        1005822023-01-02 11:43:36completedweb0.00WELCOME10
        customers2,018 filas · 9 columnas
        • customer_idinteger
        • first_namevarchar
        • last_namevarchar
        • emailvarchar
        • cityvarchar
        • statevarchar
        • signup_datedate
        • segmentvarchar
        • referral_sourcevarchar
        Primeras 5 filas de customers
        customer_idfirst_namelast_nameemailcitystatesignup_datesegmentreferral_source
        1OwenHudsonowen.hudson@icloud.comSan FranciscoCA2022-06-02consumersearch
        2DouglasMendozadmendoza69@gmail.comAtlantaGA2022-06-02consumerNULL
        3HenryBrookshbrooks@lakesidecafe.comLos AngelesCA2022-06-04businessNULL
        4BrianGrahambgraham@bluecedarhomes.comSeattleWA2022-06-06businesspinterest
        5KyleJimenezkjimenez27@yahoo.comIndianapolisIN2022-06-07consumerNULL
        order_items30,338 filas · 6 columnas
        • order_item_idinteger
        • order_idinteger
        • product_idinteger
        • quantityinteger
        • unit_pricedecimal
        • discount_pctdecimal
        Primeras 5 filas de order_items
        order_item_idorder_idproduct_idquantityunit_pricediscount_pct
        11001121931.990.00
        21001154311.990.00
        31002154411.990.00
        410021941149.000.00
        51002193219.990.00
        returns1,673 filas · 5 columnas
        • return_idinteger
        • order_item_idinteger
        • returned_ondate
        • reasonvarchar
        • refund_amountdecimal
        Primeras 5 filas de returns
        return_idorder_item_idreturned_onreasonrefund_amount
        1142023-01-10damaged83.69
        2422023-01-10wrong_item19.99
        31052023-01-14wrong_item10.99
        4242023-01-16changed_mind26.99
        51262023-01-16late20.99
        employees60 filas · 8 columnas
        • employee_idinteger
        • first_namevarchar
        • last_namevarchar
        • departmentvarchar
        • titlevarchar
        • manager_idinteger
        • hire_datedate
        • salaryinteger
        Primeras 5 filas de employees
        employee_idfirst_namelast_namedepartmenttitlemanager_idhire_datesalary
        1CatherineHaleExecutiveChief Executive OfficerNULL2016-03-01285000
        2RobertKimExecutiveChief Operating Officer12017-01-09235000
        3MeganCollinsSalesHead of Sales12018-04-16172000
        4ChloeGutierrezSalesAccount Executive32020-01-2172000
        5FrankBellSalesAccount Executive32023-05-2173000
        web_sessions40,000 filas · 7 columnas
        • session_idinteger
        • customer_idinteger
        • started_attimestamp
        • devicevarchar
        • sourcevarchar
        • pages_viewedinteger
        • convertedboolean
        Primeras 5 filas de web_sessions
        session_idcustomer_idstarted_atdevicesourcepages_viewedconverted
        1NULL2023-01-01 23:02:24mobilepaid1false
        2182023-01-01 15:07:49desktoppaid1false
        3NULL2023-01-01 16:55:46desktopdirect7false
        4NULL2023-01-01 12:43:28mobileorganic3false
        5NULL2023-01-01 13:06:21mobilesocial2false
        marketing_spend3,276 filas · 3 columnas
        • spend_datedate
        • channelvarchar
        • amountdecimal
        Primeras 5 filas de marketing_spend
        spend_datechannelamount
        2023-01-01paid492.99
        2023-01-01email37.38
        2023-01-01social200.53
        2023-01-02paid709.13
        2023-01-02email64.13

        La lección

        Los Desafíos finales son casos pequeños. Cada paso se revisa por separado y, juntos, responden la solicitud completa. Este usa todo lo del capítulo: elegir columnas, calcular nuevas, nombrarlas, redondear y eliminar duplicados.

        Paso 1: la lista de precios de oferta

        Un descuento del 10 % significa que el cliente paga el 90 % del precio, así que el precio de oferta es unit_price * 0.9. Escribirlo como una multiplicación es más claro y menos propenso a errores que unit_price - unit_price * 0.1, aunque ambos dan la misma respuesta. Redondea el resultado a centavos y ponle un alias legible:

        ROUND(unit_price * 0.9, 2) AS sale_price

        Mantén el unit_price original a su lado. Quienes leen una lista de precios quieren comparar los dos números uno junto al otro, y un analista que muestra la entrada junto a la salida hace que los errores sean fáciles de detectar.

        Paso 2: proporción del costo

        Los equipos de finanzas suelen hablar del costo como una proporción del precio (la vista inversa del margen). Si una lámpara se vende por 80 y cuesta 32, la proporción del costo es 40 %. La expresión es unit_cost / unit_price * 100. Algunos productos no tienen costo registrado, así que su proporción de costo es NULL. Déjalos como NULL: un costo desconocido no es un costo cero, y rellenar con 0 haría que esos artículos parecieran ganancia pura en la diapositiva de la junta.

        Una comprobación rápida que hacen los analistas con una columna como esta: ¿todos los valores están entre 0 y 100? Una proporción de costo superior a 100 significa que el producto se vende con pérdida, algo que vale la pena señalarle a Jessica en lugar de pasarlo en silencio.

        Paso 3: canales y estados

        SELECT DISTINCT channel, status FROM orders lista cada combinación una vez. Con tres canales y cuatro estados esperarías como máximo doce filas. Si ves menos, alguna combinación nunca ocurre. Si ves más, los datos tienen variantes de escritura, y eso ya es un hallazgo.

        Qué comprobaría quien revisa

        • Cada columna calculada tiene un alias claro.
        • El redondeo ocurre una sola vez, sobre el valor final.
        • Los NULL se dejan como NULL salvo que haya una razón de negocio para rellenarlos.
        • El resultado tiene solo las columnas que se pidieron.

        Esos cuatro hábitos te ahorrarán la mayoría de los comentarios que recibirías en una revisión de código como analista junior.

        Errores comunes

        • Multiplicar por el descuento en lugar de por lo que queda. unit_price * 0.1 es el 10 % que se quita, no el precio de oferta. El cliente paga el 90 %, así que escribe unit_price * 0.9.
        • Redondear las entradas en lugar del resultado. ROUND(unit_price, 2) * 0.9 aún puede devolver tres decimales. Redondea una sola vez, alrededor de toda la expresión: ROUND(unit_price * 0.9, 2).
        • Convertir un costo que falta en 0. Una proporción de costo desconocida debe seguir siendo NULL; un 0 le dice al lector que el producto no cuesta nada fabricarlo.
        • Esperar que DISTINCT funcione solo con la primera columna. SELECT DISTINCT channel, status elimina los pares duplicados, así que cada canal aparece una vez por cada estado que tiene, no una sola vez en total.

        En SQL Server

        Los tres pasos se ejecutan allí sin cambios: la aritmética con decimales, ROUND(x, 2) y SELECT DISTINCT se comportan igual. La diferencia que hay que recordar es la unión de texto, que usa + en lugar de ||.

        Elige qué puede ejecutarse en este sitio. Puedes cambiarlo cuando quieras desde "Configurar cookies", al pie de cada página.