Este informe presenta un analisis descriptivo y diagnostico enfocado en la rentabilidad de Adidas. El trabajo se concentra en explicar como se relacionan las ventas, la utilidad operativa, el margen operativo y el margen de costo a traves de tres dimensiones principales: ciudad, metodo de venta y tipo de producto.
El objetivo es identificar que ciudades venden mas, cuales convierten mejor sus ventas en utilidad, y como la estructura comercial y de costos ayuda a explicar por que unas ciudades son mas rentables que otras.
La siguiente tabla resume el comportamiento general de la utilidad operativa, el margen operativo, el costo operativo y el margen de costo. Este resumen permite ubicar el nivel central y la dispersion de las variables clave antes de profundizar en el analisis por ciudad, metodo de venta y producto.
tabla_resumen <- tibble(
variable = c("Utilidad operativa", "Margen operativo", "Costo operativo", "Margen de costo"),
minimo = c(min(adidas$utilidad_operativa, na.rm = TRUE),
min(adidas$margen_operativo, na.rm = TRUE),
min(adidas$costo_operativo, na.rm = TRUE),
min(adidas$margen_costo, na.rm = TRUE)),
media = c(mean(adidas$utilidad_operativa, na.rm = TRUE),
mean(adidas$margen_operativo, na.rm = TRUE),
mean(adidas$costo_operativo, na.rm = TRUE),
mean(adidas$margen_costo, na.rm = TRUE)),
mediana = c(median(adidas$utilidad_operativa, na.rm = TRUE),
median(adidas$margen_operativo, na.rm = TRUE),
median(adidas$costo_operativo, na.rm = TRUE),
median(adidas$margen_costo, na.rm = TRUE)),
maximo = c(max(adidas$utilidad_operativa, na.rm = TRUE),
max(adidas$margen_operativo, na.rm = TRUE),
max(adidas$costo_operativo, na.rm = TRUE),
max(adidas$margen_costo, na.rm = TRUE)),
desviacion_estandar = c(sd(adidas$utilidad_operativa, na.rm = TRUE),
sd(adidas$margen_operativo, na.rm = TRUE),
sd(adidas$costo_operativo, na.rm = TRUE),
sd(adidas$margen_costo, na.rm = TRUE))
) %>%
mutate(across(where(is.numeric), ~ round(.x, 4)))
DT::datatable(
tabla_resumen,
caption = "Tabla 1. Resumen estadistico de utilidad, margen y costos",
rownames = FALSE,
options = list(pageLength = 10, dom = "tip")
)
Se inicia con la dimension geografica para identificar cuales ciudades concentran el mayor nivel de ventas totales.
top_15_ventas_ciudad <- ventas_ciudad %>%
slice_max(order_by = ventas_totales, n = 15) %>%
mutate(across(where(is.numeric), ~ round(.x, 4)))
DT::datatable(
top_15_ventas_ciudad,
caption = "Tabla 2. Top 15 ciudades por ventas totales",
rownames = FALSE,
options = list(pageLength = 15, scrollX = TRUE)
)
grafico_ciudades_ventas <- ggplot(top_15_ventas_ciudad, aes(
x = reorder(ciudad, ventas_totales),
y = ventas_totales,
text = paste0("Ciudad: ", ciudad, "<br>Ventas: ", comma(ventas_totales))
)) +
geom_col(fill = "steelblue", color = "black") +
coord_flip() +
scale_y_continuous(labels = comma) +
labs(
title = "Figura 1. Top 15 ciudades por ventas totales",
x = "Ciudad",
y = "Ventas totales"
) +
theme_minimal()
ggplotly(grafico_ciudades_ventas, tooltip = "text")
El grafico anterior permite identificar los mercados geograficos de mayor escala comercial. Sin embargo, vender mas no implica necesariamente ser mas rentable.
Despues de observar la escala de ventas, se compara la utilidad total por ciudad junto con su margen operativo promedio. Esto permite separar ciudades que destacan por volumen de aquellas que ademas convierten mejor las ventas en utilidad.
top_10_utilidad_ciudad <- ventas_ciudad %>%
slice_max(order_by = utilidad_total, n = 10) %>%
arrange(desc(utilidad_total))
factor_ciudad_utilidad <- max(top_10_utilidad_ciudad$utilidad_total) /
max(c(top_10_utilidad_ciudad$margen_operativo_promedio,
top_10_utilidad_ciudad$margen_costo_promedio))
ggplot(top_10_utilidad_ciudad, aes(x = reorder(ciudad, utilidad_total))) +
geom_col(aes(y = utilidad_total), fill = "darkgreen", color = "black") +
geom_line(aes(y = margen_operativo_promedio * factor_ciudad_utilidad, group = 1, color = "Margen operativo"), linewidth = 1.1) +
geom_point(aes(y = margen_operativo_promedio * factor_ciudad_utilidad, color = "Margen operativo"), size = 2.5) +
geom_line(aes(y = margen_costo_promedio * factor_ciudad_utilidad, group = 1, color = "Margen de costo"), linewidth = 1.1) +
geom_point(aes(y = margen_costo_promedio * factor_ciudad_utilidad, color = "Margen de costo"), size = 2.5) +
scale_color_manual(values = c("Margen operativo" = "red", "Margen de costo" = "blue")) +
scale_y_continuous(
labels = comma,
name = "Utilidad operativa total",
sec.axis = sec_axis(
~ . / factor_ciudad_utilidad,
name = "Margenes promedio",
labels = percent_format(accuracy = 1)
)
) +
labs(
title = "Figura 2. Top 10 ciudades por utilidad total, margen operativo y margen de costo",
x = "Ciudad",
color = "Indicador"
) +
theme_minimal() +
theme(axis.text.x = element_text(angle = 35, hjust = 1))
Esta figura muestra que el liderazgo en utilidad no siempre coincide con el liderazgo en margen. Algunas ciudades pueden ganar por escala, mientras otras pueden destacar por eficiencia relativa.
ciudades_objetivo <- c("Birmingham", "New York", "Orlando", "New Orleans", "San Francisco", "Charleston")
participacion_metodo_ciudad <- adidas %>%
filter(ciudad %in% ciudades_objetivo) %>%
group_by(ciudad, metodo_venta) %>%
summarise(ventas_totales = sum(ventas_total, na.rm = TRUE), .groups = "drop") %>%
group_by(ciudad) %>%
mutate(
participacion = ventas_totales / sum(ventas_totales)
) %>%
ungroup() %>%
mutate(
ciudad = factor(ciudad, levels = ciudades_objetivo)
)
grafico_participacion_metodo_ciudad <- ggplot(
participacion_metodo_ciudad,
aes(
x = ciudad,
y = participacion,
fill = metodo_venta,
text = paste0(
"Ciudad: ", ciudad,
"<br>Metodo de venta: ", metodo_venta,
"<br>Ventas: ", scales::comma(ventas_totales),
"<br>Participacion: ", scales::percent(participacion, accuracy = 0.1)
)
)
) +
geom_col(position = "fill", color = "black") +
scale_y_continuous(labels = scales::percent_format(accuracy = 1)) +
labs(
title = "Participacion de ventas por metodo de venta en ciudades seleccionadas",
x = "Ciudad",
y = "Participacion sobre ventas totales",
fill = "Metodo de venta"
) +
theme_minimal() +
theme(axis.text.x = element_text(angle = 25, hjust = 1))
plotly::ggplotly(grafico_participacion_metodo_ciudad, tooltip = "text")
ciudades_objetivo <- c("Birmingham", "New York", "Orlando", "New Orleans", "San Francisco", "Charleston")
top_producto_ciudad <- adidas %>%
filter(ciudad %in% ciudades_objetivo) %>%
group_by(ciudad, producto) %>%
summarise(ventas_totales = sum(ventas_total, na.rm = TRUE), .groups = "drop") %>%
group_by(ciudad) %>%
slice_max(order_by = ventas_totales, n = 1, with_ties = FALSE) %>%
ungroup()
grafico_top_producto_ciudad <- ggplot(
top_producto_ciudad,
aes(
x = reorder(ciudad, ventas_totales),
y = ventas_totales,
fill = producto,
text = paste0(
"Ciudad: ", ciudad,
"<br>Producto lider: ", producto,
"<br>Ventas: ", scales::comma(ventas_totales)
)
)
) +
geom_col(color = "black") +
coord_flip() +
scale_y_continuous(labels = scales::comma) +
labs(
title = "Producto mas vendido por ciudad",
x = "Ciudad",
y = "Ventas totales",
fill = "Producto"
) +
theme_minimal()
plotly::ggplotly(grafico_top_producto_ciudad, tooltip = "text")
Antes de evaluar rentabilidad por canal, es util observar que porcentaje de las ventas totales proviene de cada metodo de venta.
tabla_participacion_metodo <- metodo_participacion %>%
select(metodo_venta, ventas_totales, participacion) %>%
mutate(
ventas_totales = round(ventas_totales, 2),
participacion = round(participacion, 4)
)
DT::datatable(
tabla_participacion_metodo,
caption = "Tabla 3. Participacion de las ventas por metodo de venta",
rownames = FALSE,
options = list(pageLength = 10, dom = "tip")
)
plot_ly(
data = metodo_participacion,
labels = ~metodo_venta,
values = ~ventas_totales,
type = "pie",
textinfo = "label+percent",
hovertemplate = paste(
"<b>Metodo:</b> %{label}<br>",
"<b>Ventas:</b> %{value:,}<br>",
"<b>Participacion:</b> %{percent}<extra></extra>"
)
) %>%
layout(
title = "Figura 3. Participacion de las ventas por metodo de venta"
)
A continuacion se compara cada metodo de venta por escala comercial y por generacion de utilidad.
tabla_metodo_resumen <- metodo_resumen %>%
mutate(across(where(is.numeric), ~ round(.x, 4)))
DT::datatable(
tabla_metodo_resumen,
caption = "Tabla 4. Resumen por metodo de venta",
rownames = FALSE,
options = list(pageLength = 10, scrollX = TRUE)
)
grafico_metodo_ventas_utilidad <- ggplot(metodo_long, aes(
x = metodo_venta,
y = valor,
fill = indicador_label,
text = paste0("Metodo: ", metodo_venta, "<br>", indicador_label, ": ", comma(valor))
)) +
geom_col(position = "dodge", color = "black") +
scale_y_continuous(labels = comma) +
scale_fill_manual(values = c("Ventas totales" = "steelblue", "Utilidad operativa" = "darkgreen")) +
labs(
title = "Figura 4. Ventas totales y utilidad operativa por metodo de venta",
x = "Metodo de venta",
y = "Valor",
fill = "Indicador"
) +
theme_minimal()
ggplotly(grafico_metodo_ventas_utilidad, tooltip = "text")
La siguiente figura retoma el analisis de la distribucion del margen por metodo de venta mediante boxplots. Esto es importante para ver no solo el promedio del margen, sino tambien su dispersion y la presencia de valores atipicos dentro de cada canal.
grafico_box_metodo <- ggplot(adidas, aes(
x = metodo_venta,
y = margen_operativo,
fill = metodo_venta,
text = paste0("Metodo: ", metodo_venta, "<br>Margen: ", percent(margen_operativo, accuracy = 0.1))
)) +
geom_boxplot(color = "black") +
scale_y_continuous(labels = percent_format(accuracy = 1)) +
labs(
title = "Figura 5. Distribucion del margen por metodo de venta",
x = "Metodo de venta",
y = "Margen operativo"
) +
theme_minimal() +
theme(legend.position = "none")
ggplotly(grafico_box_metodo)
Despues del canal, se compara el desempeno por linea de producto.
tabla_producto_resumen <- producto_resumen %>%
mutate(across(where(is.numeric), ~ round(.x, 4)))
DT::datatable(
tabla_producto_resumen,
caption = "Tabla 5. Resumen por tipo de producto",
rownames = FALSE,
options = list(pageLength = 10, scrollX = TRUE)
)
grafico_producto_ventas_utilidad <- ggplot(producto_long, aes(
x = producto,
y = valor,
fill = indicador_label,
text = paste0("Producto: ", producto, "<br>", indicador_label, ": ", comma(valor))
)) +
geom_col(position = "dodge", color = "black") +
scale_y_continuous(labels = comma) +
scale_fill_manual(values = c("Ventas totales" = "steelblue", "Utilidad operativa" = "darkgreen")) +
labs(
title = "Figura 6. Ventas totales y utilidad operativa por tipo de producto",
x = "Producto",
y = "Valor",
fill = "Indicador"
) +
theme_minimal() +
theme(axis.text.x = element_text(angle = 25, hjust = 1))
ggplotly(grafico_producto_ventas_utilidad, tooltip = "text")
Este grafico de dos ejes permite comparar la escala de ventas de cada ciudad con su margen operativo promedio. Primero se observan solo las 10 ciudades que mas venden.
top_10_ventas_ciudad <- ventas_ciudad %>%
slice_max(order_by = ventas_totales, n = 10) %>%
arrange(desc(ventas_totales))
factor_ciudad_ventas_margen <- max(top_10_ventas_ciudad$ventas_totales) / max(top_10_ventas_ciudad$margen_operativo_promedio)
ggplot(top_10_ventas_ciudad, aes(x = reorder(ciudad, ventas_totales))) +
geom_col(aes(y = ventas_totales), fill = "steelblue", color = "black") +
geom_line(aes(y = margen_operativo_promedio * factor_ciudad_ventas_margen, group = 1), color = "red", linewidth = 0.9) +
geom_point(aes(y = margen_operativo_promedio * factor_ciudad_ventas_margen), color = "red", size = 1.8) +
scale_y_continuous(
labels = comma,
name = "Ventas totales",
sec.axis = sec_axis(~ . / factor_ciudad_ventas_margen, name = "Margen operativo promedio", labels = percent_format(accuracy = 1))
) +
labs(
title = "Figura 7. Top 10 ciudades por ventas totales y margen operativo",
x = "Ciudad"
) +
theme_minimal() +
theme(axis.text.x = element_text(angle = 35, hjust = 1))
Adicionalmente, se observa el top 10 de ciudades con mayor margen operativo usando el mismo formato de dos ejes.
top_10_margen_ciudad <- ventas_ciudad %>%
slice_max(order_by = margen_operativo_promedio, n = 10) %>%
arrange(desc(margen_operativo_promedio))
factor_ciudad_margen_top10 <- max(top_10_margen_ciudad$ventas_totales) / max(top_10_margen_ciudad$margen_operativo_promedio)
ggplot(top_10_margen_ciudad, aes(x = reorder(ciudad, margen_operativo_promedio))) +
geom_col(aes(y = ventas_totales), fill = "steelblue", color = "black") +
geom_line(aes(y = margen_operativo_promedio * factor_ciudad_margen_top10, group = 1), color = "red", linewidth = 0.9) +
geom_point(aes(y = margen_operativo_promedio * factor_ciudad_margen_top10), color = "red", size = 1.8) +
scale_y_continuous(
labels = comma,
name = "Ventas totales",
sec.axis = sec_axis(~ . / factor_ciudad_margen_top10, name = "Margen operativo promedio", labels = percent_format(accuracy = 1))
) +
labs(
title = "Figura 8. Top 10 ciudades por margen operativo y ventas totales",
x = "Ciudad"
) +
theme_minimal() +
theme(axis.text.x = element_text(angle = 35, hjust = 1))
De manera similar, este grafico permite ver si los productos que mas venden son tambien los que presentan mejor margen operativo.
factor_producto_ventas_margen <- max(producto_resumen$ventas_totales) / max(producto_resumen$margen_operativo_promedio)
ggplot(producto_resumen, aes(x = reorder(producto, ventas_totales))) +
geom_col(aes(y = ventas_totales), fill = "steelblue", color = "black") +
geom_line(aes(y = margen_operativo_promedio * factor_producto_ventas_margen, group = 1), color = "red", linewidth = 1) +
geom_point(aes(y = margen_operativo_promedio * factor_producto_ventas_margen), color = "red", size = 2.2) +
scale_y_continuous(
labels = comma,
name = "Ventas totales",
sec.axis = sec_axis(~ . / factor_producto_ventas_margen, name = "Margen operativo promedio", labels = percent_format(accuracy = 1))
) +
labs(
title = "Figura 9. Ventas totales y margen operativo por producto",
x = "Producto"
) +
theme_minimal() +
theme(axis.text.x = element_text(angle = 25, hjust = 1))
La siguiente figura resume la relacion entre escala comercial y rentabilidad relativa a nivel de ciudad.
# Base para los puntos
puntos_ciudad <- ventas_ciudad %>%
arrange(ventas_totales)
# Modelo lineal
modelo_margen <- lm(margen_operativo_promedio ~ ventas_totales, data = puntos_ciudad)
# Predicciones para la linea
linea_tendencia <- puntos_ciudad %>%
mutate(margen_predicho = predict(modelo_margen, newdata = puntos_ciudad))
grafico_relacion_ventas_margen <- ggplot() +
geom_point(
data = puntos_ciudad,
aes(
x = ventas_totales,
y = margen_operativo_promedio,
text = paste0(
"Ciudad: ", ciudad,
"<br>Ventas: ", comma(ventas_totales),
"<br>Margen: ", percent(margen_operativo_promedio, accuracy = 0.1)
)
),
color = "steelblue",
size = 2.5,
alpha = 0.8
) +
geom_line(
data = linea_tendencia,
aes(x = ventas_totales, y = margen_predicho),
color = "red",
linewidth = 1
) +
scale_x_continuous(labels = comma) +
scale_y_continuous(labels = percent_format(accuracy = 1)) +
labs(
title = "Figura 10. Relacion entre ventas totales y margen operativo por ciudad",
x = "Ventas totales",
y = "Margen operativo promedio"
) +
theme_minimal()
ggplotly(grafico_relacion_ventas_margen, tooltip = "text")
Este grafico permite verificar si las ciudades que mas venden tambien tienden a tener un margen mas alto, o si por el contrario existe una tension entre volumen y eficiencia.
Finalmente, se compara el margen de costo con el margen operativo para las ciudades con mayor margen operativo y, por separado, para las ciudades con mayor margen de costo.
grafico_margenes_operativo <- ggplot(margenes_top_operativo_long, aes(
x = reorder(ciudad, valor),
y = valor,
fill = tipo_margen,
text = paste0("Ciudad: ", ciudad, "<br>", tipo_margen, ": ", percent(valor, accuracy = 0.1))
)) +
geom_col(position = "dodge", color = "black") +
coord_flip() +
scale_y_continuous(labels = percent_format(accuracy = 1)) +
scale_fill_manual(values = c("Margen operativo" = "darkgreen", "Margen de costo" = "gray60")) +
labs(
title = "Figura 11. Top 10 ciudades por margen operativo: margen operativo vs margen de costo",
x = "Ciudad",
y = "Margen",
fill = "Indicador"
) +
theme_minimal()
ggplotly(grafico_margenes_operativo, tooltip = "text")
grafico_margenes_costo <- ggplot(margenes_top_costo_long, aes(
x = reorder(ciudad, valor),
y = valor,
fill = tipo_margen,
text = paste0("Ciudad: ", ciudad, "<br>", tipo_margen, ": ", percent(valor, accuracy = 0.1))
)) +
geom_col(position = "dodge", color = "black") +
coord_flip() +
scale_y_continuous(labels = percent_format(accuracy = 1)) +
scale_fill_manual(values = c("Margen operativo" = "darkgreen", "Margen de costo" = "gray60")) +
labs(
title = "Figura 12. Top 10 ciudades por margen de costo: margen de costo vs margen operativo",
x = "Ciudad",
y = "Margen",
fill = "Indicador"
) +
theme_minimal()
ggplotly(grafico_margenes_costo, tooltip = "text")
A partir del analisis realizado se pueden extraer varias conclusiones:
En conjunto, el trabajo muestra que la rentabilidad de una ciudad no depende solo de cuanto vende, sino de que tan eficientemente transforma esas ventas en utilidad despues de cubrir sus costos operativos.