Σχολιασμός/Παρουσίαση του Dataset

Περιγραφή του dataset

This dataset contains two related tables: sales and ingredients. It is designed for projects focusing on sales forecasting, ingredient optimization, and supply chain management for a pizza delivery business. By leveraging historical data, users can build predictive models to minimize ingredient waste, prevent stockouts, and optimize purchasing strategies.

Περιγραφή των μεταβλητών

  1. Sales Table:

    Shape: 48,620 rows × 16 columns
    Columns:
    pizza_id: Unique identifier for a pizza
    - type: num
    - range: [1:48620]
    order_id: Unique identifier for a sales order
    - type: num
    - range: [1:21350]
    pizza_name_id: Identifier linking the pizza to its recipe
    - type: chr
    quantity: Number of pizzas sold
    - type: num
    - range: [1:4]
    order_date: The date of the order
    - type: POSIXct
    order_time: The time of the order
    - type: POSIXct
    unit_price: Price per unit of pizza - type: num
    - range: [9.75:35.95]
    total_price: quantity x unit_price
    - type: num
    - rage: [9.75:83]
    pizza_size: Size of the pizza
    - type: chr
    - values: “S”, “M”, “L”, “XL”, “XXL”
    pizza_category: Category of the pizza
    - type: chr
    - values: “Classic”, “Supreme”, “Veggie”, “Chicken”
    pizza_ingredients: Ingredients used in the pizza
    - type: chr

  2. Ingredients Table:

    Shape: 518 rows × 4 columns Columns: pizza_name_id: Identifier linking the pizza to its recipe. - type: chr pizza_name: Name of the pizza. - type: chr pizza_ingredients: List of ingredients in the pizza. - type: chr Items_Qty_In_Grams: Quantity of each ingredient in grams. - type: num - range: [5:200]

Αιτιολόγηση της επιλογής σε σχέση με την Επιχειρηματική Αναλυτική

Για την Domino’s Pizza, η Επιχειρηματική Αναλυτική (ΕΑ) χρησιμοποιείται κυρίως για βελτίωση της ταχύτητας εξυπηρέτησης, πρόβλεψη ζήτησης και καλύτερη εμπειρία πελάτη. Παρακάτω φαίνονται οι βασικές μέθοδοι, οι στόχοι τους και ο τύπος επιχειρηματικής αναλυτικής στον οποίο ανήκουν.

Πρόβλεψη Ζήτησης

Demand planning is knowing what our consumers want before they do. If we are doing our job, we know they’re going to have a pizza next Thursday before they do,” quips Darren O’Keefe, Head of Inventory at Domino’s Pizza UK & Ireland Ltd.

Μέθοδος/τεχνική

  • Ανάλυση ιστορικών δεδομένων παραγγελιών
  • Machine learning μοντέλα πρόβλεψης
  • Ανάλυση εποχικότητας (ώρα, ημέρα, καιρός, events)

Στόχος/πρόκληση

  • Να προβλέπεται πόσες παραγγελίες θα γίνουν
  • Καλύτερη διαχείριση αποθεμάτων και προσωπικού
  • Μείωση χρόνου αναμονής

Τύπος ΕΑ

  • Predictive Analytics (Προγνωστική Αναλυτική)

“We don’t fall victim to fashionable tech, but rather listen to our customers and internal stakeholders to understand their objectives and visions,” explains Sody Kahlon, Chief Information & Technology Officer at Domino’s Pizza UK & Ireland Ltd. “This then allows us to adopt the most relevant solution to meet their needs. The realm of AI has opened our choices to further increase our personalization, enhance internal efficiencies, derive rapid conclusions from data insights, improve our forecasting, strengthen our cybersecurity, and experiment with novel innovation.”

Πρόβλεψη Παραγγελίας

Μέθοδος/τεχνική

  • Ανάλυση συμπεριφοράς πελατών στην εφαρμογή
  • Αλγόριθμοι πιθανότητας αγοράς
  • Big Data από προηγούμενες παραγγελίες

Στόχος/πρόκληση

  • Να προβλέπει ότι ο πελάτης πιθανότατα θα κάνει παραγγελία
  • Να ξεκινά νωρίτερα η προετοιμασία της πίτσας
  • Μείωση χρόνου παράδοσης

Τύπος ΕΑ

  • Predictive Analytics (Προγνωστική Αναλυτική)

The company created a data lake consisting of key order information by taking advantage of Amazon Simple Storage Service (Amazon S3) for data storage and AWS Glue for data quering. It also uses Amazon SageMaker to build and train machine learning models to predict the likelihood that an order will be placed, so a store can begin making that order right before it is placed.

Διερεύνηση συσχετίσεων

Αναγνώριση πιθανών σχέσεων μεταξύ μεταβλητών και ερμηνεία τους

Σχέση quantity και total_price Αναμένουμε θετική συσχέτιση (πολύ κοντά στο 1)
- Ερμηνεία: Όσο περισσότερες πίτσες αγοράζει ένας πελάτης σε μια γραμμή παραγγελίας, τόσο αυξάνεται το συνολικό κόστος. Αν η συσχέτιση δεν είναι 1.0, είναι γιατί οι πίτσες έχουν διαφορετικές τιμές μονάδας (unit_price).

Σχέση unit_price και quantity Αναμένουμε θετική συσχέτιση (>0.5)
- Ερμηνεία: Είναι λογικό οι πίτσες με μεγαλύτερη ζήτηση να έχουν μεγαλύτερη τιμή ανά τεμάχιο. Εάν η τιμή είναι πολύ κοντά στο μηδέν, αυτό σημαίνει ότι οι πελάατες αγοράζουν την ίδια ποσότητα πίτσας ανεξάρτητα απόο την τιμή της.

Σχέση unit_price και total_price Αναμένουμε θετική συσχέτιση (>0.5)
- Ερμηνεία: Με βάση τις παραπάνω υποθέσεις μας, αναμένουμε και τη σχέση μεταξύ τιμής τεμαχίου και συνολικής τιμής να είναι θετική. Δηλαδή, όσο αυξάνεται η μία να αυξάνεται και η άλλη.

Υπολογισμός συντελεστών συσχέτισης μεταξύ αριθμητικών μεταβλητών

# Δημιουργία ενός subset μόνο με τις αριθμητικές μεταβλητές
numeric_vars <- Pizza_Sale[, c("quantity", "unit_price", "total_price")]

# Υπολογισμός του πίνακα συσχέτισης
cor_matrix <- cor(numeric_vars, use = "complete.obs")

# Εμφάνιση του πίνακα
print(cor_matrix)
##                quantity  unit_price total_price
## quantity    1.000000000 0.007143956   0.5419504
## unit_price  0.007143956 1.000000000   0.8360716
## total_price 0.541950378 0.836071621   1.0000000

Ενδεικτικά Διαγράμματα των Βασικών Παραμέτρων

Σχέση unit_price και quantity

# Scatter plot
library(ggplot2)

ggplot(Pizza_Sale, aes(x = unit_price, y = quantity)) +
  geom_point(size = 3, alpha = 0.7) +
  scale_y_continuous(breaks = seq(0, 10000, by = 2500)) +  # από 0 έως 10χιλ, με βήμα 2.5χιλ
  labs(
    title = "Σχέση τιμής τεμαχίου και ποσότητας",
    x = "Τιμή τεμαχίου",
    y = "Ποσότητα (σε τεμάχια)"
  )

Παρατηρούμε τόσο από τον συντελεστή συσχέτισης όσο και από το διάγραμμα, ότι η τιμή τεμαχίου και η ποσότητα δεν έχουν τόσο ισχυρή σχέση όσο αναμέναμε. Αντίθετα, οι πελάτες φαίνεται να αγοράζουν σχεδόν την ίδια ποσότητα πίτσας ανεξάρτητα από την τιμή.

Εδώ διαπιστώνουμε ότι η αρχική μας υπόθεση ήταν εσφαλμένη, καθώς σημαντικός παράγοντας είναι και το είδος της πίτσας. Δεν αναφερόμαστε στην ίδια πίτσα με διαφορετικές τιμές, αλλά σε διαφορετικές πίτσες. Το γεγονός ότι η ζήτηση δεν επηρεάζεται τόσο από την τιμή τεμαχίου δείχνει ότι η τιμή της κάθε πίτσας είναι αντιπροσωπευτική της αντιλαμβανόμενης αξίας της από τον πελάτη.

Σχέση total_price και pizza_category

# Boxplot

ggplot(Pizza_Sale, aes(x = pizza_category, y = total_price, fill = factor(pizza_category))) +
geom_boxplot() +
scale_y_continuous(breaks = seq(0, 90, by = 2)) +  # από 0 έως 90, με βήμα 2
labs(
  title = "Σχέση κατηγορίας πίτσας και συνολικής τιμής ενός είδους πίτσας ανά παραγγελία",
  x = "Κατηγορία πίτσας",
  y = "Συνολική τιμή"
) +
theme(legend.position = "none")
## Warning: Removed 7 rows containing non-finite outside the scale range
## (`stat_boxplot()`).

Παρατηρούμε ότι περισσότερα λεφτά δίνουν οι πελάτες για να αγοράσουν πίτσες των κατηγοριών Veggie και Chicken, αφού η διάμεσός τους φτάνει σχεδόν τα 17$ συνολικής τιμής. Δηλαδή το 50% των πελατών που αγοράζουν Chicken pizza δίνει πάνω από 17 δολλάρια και το 50% των πελατών που αγοράζουν Veggie pizza δίνει πάνω απο 17 δολλάρια.

Επίσης, παρατηρούμε ότι η μεταβλητότητα των τιμών είναι μεγαλύτερη στις Supreme πίτσες, με το εύρος των συνολικών τιμών να κυμαίνεται μεταξύ 16 και 21 δολλαρίων.

Ακόμη, οι περισσότεροι outliers (16) εντοπίζονται στις Classic πίτσες, οι οποίες φαίνεται να έχουν περισσότερες παραγγελίες που “εκτοξεύουν” τον τζίρο.

Πωλήσεις ανά order_time

ggplot(data = Pizza_Sale, aes(x = order_time)) +
geom_histogram(fill = "tomato", color = "white") +
scale_x_datetime(
    breaks = seq(from = min(Pizza_Sale$order_time), 
                 to = max(Pizza_Sale$order_time), 
                 by = "30 min"),
    date_labels = "%H:%M"
) +
coord_flip() +
labs(
  title = "Πωλήσεις ανά ώρα της ημέρας",
  x = "Ώρα της ημέρας",
  y = "Συχνότητα"
) +
theme_minimal()
## `stat_bin()` using `bins = 30`. Pick better value `binwidth`.

Παρατηρούμε ότι οι ώρες αιχμής στα Domino’s (πάνω πό 2000 παραγγελίες) είναι μεταξύ 12:00-14:00 και μεταξύ 17:00-19:30. Οι περισσότερες παραγγελίες κατά τη διάρκεια της ημέρας (>3000) είναι μεταξύ 12:30-13:30.

Σχέση μεταξύ pizza_category και quantity

ggplot(Pizza_Sale, aes(x = pizza_category, y = quantity, fill = factor(pizza_category), color = "white")) +
geom_bar(stat = "summary", fun = "sum") +
labs(
  x = "Κατηγορία πίτσας",
  y = "Ποσότητα"
) +
theme(legend.position = "none")

Παρατηρούμε ότι τις περισσότερες πωλήσεις είχε η κατηγορία Classic, με σχεδόν 15000 τεμάχια, ενώ τελευταία σε πωλήσεις είναι η κατηγορία Chicken, με μικρή διαφορά όμως από τις υπόλοιπες.

Fitted Μοντέλα Γραμμικής Παλινδρόμησης

Με μία ανεξάρτητη μεταβλητή

total_quantity <- aggregate(Items_Qty_In_Grams ~ pizza_name_id, 
                           data = Pizza_ingredients, 
                           FUN = sum)

price_per_pizza <- aggregate(unit_price ~ pizza_name_id,
                             data = Pizza_Sale,
                             FUN = mean)

final <- merge(total_quantity, price_per_pizza, by = "pizza_name_id")

m <- lm(unit_price ~ Items_Qty_In_Grams, data = final)

# Add regression line to plot:
ggplot(final, aes(Items_Qty_In_Grams , unit_price)) +
  geom_point() + 
  geom_abline(aes(intercept = coef(m)[1], slope = coef(m)[2]), colour = "red") +
  labs(title = "Σχέση Τιμής Πίτσας και Βάρους Υλικών",
       x = "Συνολικό Βάρος (g)",
       y = "Τιμή Μονάδας (€)") +
  theme_minimal()

Παρατηρούμε ότι όσο αυξάνονται οι ποσότητες των υλικών (σε γραμμάρια) σε μια πίτσα τόσο αυξάνεται και η τιμή της.

Σχετικά διαγράμματα

plot(m)

Με δύο ανεξάρτητες μεταβλητές

# Υπολογισμός βάρους ΚΑΙ πλήθους υλικών ανά πίτσα
ingredients_summary <- aggregate(Items_Qty_In_Grams ~ pizza_name_id, 
                                data = Pizza_ingredients, 
                                FUN = function(x) c(Sum = sum(x), Count = length(x)))

# Μετατροπή σε καθαρό dataframe
ingredients_summary <- data.frame(pizza_name_id = ingredients_summary$pizza_name_id,
                                  total_weight = ingredients_summary$Items_Qty_In_Grams[,1],
                                  num_ingredients = ingredients_summary$Items_Qty_In_Grams[,2])

# Merge με τις τιμές
final2 <- merge(ingredients_summary, price_per_pizza, by = "pizza_name_id")

# Μοντέλο
m2 <- lm(unit_price ~ total_weight + num_ingredients, data = final2)

# Add regression line to plot:
ggplot(final2, aes(x = total_weight, y = unit_price)) +
  geom_point(aes(size = num_ingredients), color = "steelblue") + 
  geom_smooth(method = "lm", formula = y ~ x, color = "red") +
  labs(title = "Πολυμεταβλητό Μοντέλο: Τιμή vs Βάρος & Πλήθος Υλικών",
       subtitle = "Το μέγεθος των σημείων αντιστοιχεί στον αριθμό των υλικών",
       x = "Συνολικό Βάρος (g)",
       y = "Τιμή Μονάδας (€)",
       size = "Πλήθος Υλικών") +
  theme_minimal()

Παρατηρούμε ότι όσο αυξάνονται οι ποσότητες των υλικών (σε γραμμάρια) σε μια πίτσα τόσο αυξάνεται και η τιμή της. Όσον αφορά το πλήθος των διαφορετικών υλικών ανά πίτσα, παρατηρούμε ότι δεν υπάρχει άμεση συσχέτιση με την τιμή της πίτσας, καθώς υπάρχουν μεγάλες κουκκίδες σε όλο το μήκος του ευθύγραμμου τμήματος.

Σχετικά διαγράμματα

plot(m2)

Διερεύνηση των SSE και R-squared

SSE με την προσθήκη ανεξάρτητης μεταβλητής

SSE1 <- sum(m$residuals^2)
SSE2 <- sum(m2$residuals^2)
SSE1
## [1] 607.7683
SSE2
## [1] 578.6697

Ένα κριτήριο ικανοποιητικής προσέγγισης (εκτίμησης) είναι δυνατόν να στηριχθεί στην ελαχιστοποίηση μιας κατάλληλα επιλεγμένης συνάρτησης της απόκλισης αυτού που παρατηρείται (yi) από αυτό που εκτιμάται ότι πρέπει να παρατηρηθεί (a + bxi).

Επομένως με την προσθήκη της δεύτερης ανεξάρτητης μεταβλητής βελτιώνεται η προσέγγισή μας.

R-squared

Παίρνουμε ως μοντέλο βάσης το m (άρα ως SST το SSE1) και ως SSE το SSE2. Έτσι:

R_squared <- 1 - (SSE2/SSE1)
R_squared
## [1] 0.04787768

Το R_squared είναι πολύ πιο κοντά στο 0 απ’ ό,τι στο 1.

Το R^2 μας δείχνει την προστιθέμενη αξία από τη χρήση του μοντέλου. R^2 = 0 μας δείχνει ότι δεν υπάρχει βελτίωση πέραν του μοντέλου βάσης. R^2 = 1 σημαίνει ένα τέλειο μοντέλο πρόβλεψης

Συμπεραίνουμε ότι υπάρχει πολύ μικρή προστιθέμενη αξία με την προσθήκη της δεύτερης ανεξάρτητης μεταβλητής. Δεν υπάρχει ιδιαίτερη βελτίωση από το πρώτο μοντέλο στο δεύτερο.