
Image by Author | ChatGPT
Market basket analysis uses three key metrics to identify shopping patterns: support, confidence, and lift. These measures show you which product combinations happen often enough to matter, how strongly items connect, and whether relationships exist beyond random chance.
Support shows how popular an item or combination is. It is the percentage of transactions that contain those items. If bread shows up in 6 out of 10 transactions, its support is 60%.
Confidence measures conditional probability. If someone buys bread, what’s the chance they’ll also buy milk? It answers “Given that X happened, how likely is Y?” This helps predict what customers will do based on what’s already in their cart.
Lift compares what actually happens versus what you’d expect by chance alone. A lift above 1 means items really do go together; below 1 suggests they might be substitutes or bought separately.
These metrics turn raw transaction data into business insights. This guide shows you how to calculate each one using Python’s mlxtend library, which has specialized tools for market basket analysis.
Setting Up Transaction Data
Before calculating any metrics, prepare your transaction data in the right format. The mlxtend library wants data as a one-hot encoded DataFrame where each row is a transaction and each column is a product.
import pandas as pd import numpy as np from mlxtend.preprocessing import TransactionEncoder # Create sample transaction data transactions = [ ['bread', 'milk', 'eggs'], ['bread', 'butter', 'jam'], ['milk', 'eggs', 'cheese'], ['bread', 'milk'], ['butter', 'jam'], ['bread', 'eggs', 'cheese'], ['milk', 'cheese'], ['bread', 'butter', 'milk'] ] # Convert to one-hot encoded format encoder = TransactionEncoder() onehot_array = encoder.fit_transform(transactions) onehot = pd.DataFrame(onehot_array, columns=encoder.columns_) print(onehot.head())
Output:
bread butter cheese eggs jam milk 0 True False False True False True 1 True True False False True False 2 False False True True False True 3 True False False False False True 4 False True False False True False
This creates a DataFrame where True means an item was bought in that transaction, and False means it wasn’t. The output shows the first 5 transactions with bread, milk, and eggs appearing in the first transaction, while bread, butter, and jam appear together in the second.
Calculating Support Values
Support answers “How popular is this item or combination?” It basically counts how often things appear. If you’re deciding whether to stock items together on a shelf, you want combinations that appear often enough to justify the space. For individual items, support equals the proportion of transactions containing that item. For combinations, it shows how often those items appear together.
# Calculate support for individual items
item_support = onehot.mean()
print("Individual item support:")
print(item_support)
# Calculate support for bread and milk combination
bread_milk_together = onehot['bread'] & onehot['milk']
bread_milk_support = bread_milk_together.mean()
print(f"\nBread and milk together support: {bread_milk_support:.3f}")
Output:
Individual item support: bread 0.625 butter 0.375 cheese 0.375 eggs 0.375 jam 0.250 milk 0.625 dtype: float64 Bread and milk together support: 0.375
Bread and milk are the most popular individual items, each appearing in 62.5% of transactions. Bread and milk together appear in 37.5% of transactions, which is a moderately frequent combination. Items with support below 0.5 like jam (25%) might be specialty purchases rather than staple goods.
Calculating Confidence Scores
Now for conditional probability. Confidence answers “If someone already has item A in their cart, what’s the probability they’ll add item B?” This metric is directional. The confidence of bread→butter differs in meaning from butter→bread.
Think of confidence as your crystal ball for cross-selling. If confidence for bread→butter is high, bread buyers are good targets for butter promotions.
# Calculate confidence for bread → butter rule
bread_butter_together = onehot['bread'] & onehot['butter']
bread_transactions = onehot['bread'].sum()
bread_and_butter_transactions = bread_butter_together.sum()
confidence_bread_to_butter = bread_and_butter_transactions / bread_transactions
print(f"Confidence (bread → butter): {confidence_bread_to_butter:.3f}")
# Calculate reverse confidence butter → bread
butter_transactions = onehot['butter'].sum()
confidence_butter_to_bread = bread_and_butter_transactions / butter_transactions
print(f"Confidence (butter → bread): {confidence_butter_to_bread:.3f}")
# Let's also check the support values to understand why they differ
print(f"\nSupport comparison:")
print(f"Bread support: {onehot['bread'].mean():.3f}")
print(f"Butter support: {onehot['butter'].mean():.3f}")
print(f"Bread and butter together support: {bread_butter_together.mean():.3f}")
Output:
Confidence (bread → butter): 0.400 Confidence (butter → bread): 0.667 Support comparison: Bread support: 0.625 Butter support: 0.375 Bread and butter together support: 0.250
This example demonstrates the directional nature of confidence clearly. Bread buyers have a 40% chance of also buying butter, while butter buyers have a 67% chance of also buying bread. This asymmetry reveals important customer behavior patterns that would be missed if you only looked at one direction.
The difference occurs because bread is more popular overall (62.5% support) than butter (37.5% support). When someone buys the less popular item (butter), they’re more likely to also buy the popular staple (bread). But bread buyers, who represent a broader customer base, are less likely to also purchase the more specialized butter.
Calculating Lift and Interpreting Results
Lift is your reality check. It tells you whether what looks like a relationship is actually just coincidence. Lift compares what you observe versus what you’d expect if items were completely independent.
Here’s the math: if bread appears in 62.5% of transactions and milk appears in 62.5%, chance alone would put them together in 62.5% × 62.5% = 39.1% of transactions. Lift compares this expected rate with what actually happens.
# Define the combination of interest
bread_milk_together = onehot['bread'] & onehot['milk']
bread_milk_support = bread_milk_together.mean()
# Calculate confidence for bread → milk rule
bread_transactions = onehot['bread'].sum()
bread_and_milk_transactions = bread_milk_together.sum()
confidence_bread_to_milk = bread_and_milk_transactions / bread_transactions
# Calculate lift for bread → milk rule
milk_support = onehot['milk'].mean()
lift_bread_to_milk = confidence_bread_to_milk / milk_support
# Display all metrics together
print("Market Basket Analysis Results:")
print(f"Support (bread, milk): {bread_milk_support:.3f}")
print(f"Confidence (bread → milk): {confidence_bread_to_milk:.3f}")
print(f"Lift (bread → milk): {lift_bread_to_milk:.3f}")
# Interpret lift value
if lift_bread_to_milk > 1:
print("Positive association: Items are bought together more than expected")
elif lift_bread_to_milk < 1:
print("Negative association: Items are bought together less than expected")
else:
print("No association: Items are independent")
Output:
Market Basket Analysis Results: Support (bread, milk): 0.375 Confidence (bread → milk): 0.600 Lift (bread → milk): 0.960 Negative association: Items are bought together less than expected
The surprising result shows a lift of 0.960, indicating a slight negative association. Even though bread and milk appear together frequently and have decent confidence scores, they actually occur together less often than chance would predict given their individual popularity.
Understanding the Counter-Intuitive Results
This example shows why all three metrics matter. Looking at support (37.5%) and confidence (60%) alone, you might think bread and milk make a great pair for bundling or cross-promotions. But lift reveals they’re actually slightly negatively associated.
This happens because both items are individually popular (62.5% support each). When items are this popular on their own, chance alone would put them together quite often. Since they only appear together 37.5% of the time versus the expected 39.1%, customers might actually be choosing one OR the other rather than both.
For business decisions, this suggests bread and milk might serve as substitute items in some shopping contexts, or customers might buy them on different shopping trips rather than together. You wouldn’t want to create a bread-and-milk bundle based on these numbers.
The mlxtend library automates these calculations for large datasets and includes additional functions for generating association rules. These three metrics together give you complete insight into customer purchasing behavior and help with decisions about product placement, promotions, and inventory management.
