{"metadata":{"kernelspec":{"language":"python","display_name":"Python 3","name":"python3"},"language_info":{"name":"python","version":"3.12.12","mimetype":"text/x-python","codemirror_mode":{"name":"ipython","version":3},"pygments_lexer":"ipython3","nbconvert_exporter":"python","file_extension":".py"},"kaggle":{"accelerator":"none","dataSources":[{"sourceType":"competition","sourceId":10445,"databundleVersionId":200747}],"dockerImageVersionId":31236,"isInternetEnabled":true,"language":"python","sourceType":"notebook","isGpuEnabled":false}},"nbformat_minor":4,"nbformat":4,"cells":[{"cell_type":"markdown","source":"### What will you learn from this project?\nIn this project, you will learn:\n\n- How to transform large-scale transaction-level card data into customer-level features\n- How to apply RFM (Recency, Frequency, Monetary) analysis to measure customer loyalty\n- How to interpret purchasing patterns across merchant categories\n- How to segment customers based on behavioral and transactional characteristics\n- How CRM analytics can support customer retention, targeting, and value-based decision making\n- How to translate analytical results into business-oriented insights for marketing and loyalty strategies","metadata":{}},{"cell_type":"markdown","source":"# Introduction\nIn today’s highly competitive financial and retail ecosystem, understanding customer purchasing behavior is a key driver of effective CRM and loyalty strategies. Customers interact with a wide variety of merchants across different categories, and these transaction patterns provide valuable signals about customer preferences, engagement, and long-term value.\n\nThis project focuses on analyzing transaction-level card data from the Elo Merchant Category Recommendation dataset to uncover insights into customer loyalty and purchasing behavior. By leveraging historical and new merchant transaction records, we aim to quantify how frequently customers interact with merchants, how recently they have transacted, and how their spending behavior evolves over time.\n\nUsing a CRM analytics perspective, this study applies RFM (Recency, Frequency, Monetary) analysis and customer-level aggregation techniques to segment customers based on their behavioral patterns. These segments are then interpreted to support customer value assessment, retention strategies, and data-driven marketing decisions.\n\nRather than focusing solely on merchant recommendation, this project reframes the dataset as a customer loyalty and value analysis problem, demonstrating how large-scale transaction data can be transformed into actionable CRM insights for financial services and retail-driven businesses.","metadata":{}},{"cell_type":"markdown","source":"# Analysis Content\n\n1. [Python Libraries](#python-libraries)\n2. [Data Loading](#data-loading)\n","metadata":{}},{"cell_type":"markdown","source":"<a id=\"python-libraries\"></a>\n# Python Libraries","metadata":{}},{"cell_type":"code","source":"!pip install lifetimes","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:03:19.234831Z","iopub.execute_input":"2026-02-23T14:03:19.235195Z","iopub.status.idle":"2026-02-23T14:03:24.673492Z","shell.execute_reply.started":"2026-02-23T14:03:19.235164Z","shell.execute_reply":"2026-02-23T14:03:24.672304Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"import numpy as np\nimport pandas as pd\nimport seaborn as sns\nimport datetime as dt\nimport matplotlib.pyplot as plt\nfrom lifetimes import BetaGeoFitter, GammaGammaFitter\nfrom lifetimes.utils import summary_data_from_transaction_data\nfrom sklearn.preprocessing import MinMaxScaler\n","metadata":{"_uuid":"8f2839f25d086af736a60e9eeb907d3b93b6e0e5","_cell_guid":"b1076dfc-b9ad-4769-8c92-a6c4dae69d19","trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:03:24.675536Z","iopub.execute_input":"2026-02-23T14:03:24.675999Z","iopub.status.idle":"2026-02-23T14:03:26.396936Z","shell.execute_reply.started":"2026-02-23T14:03:24.675959Z","shell.execute_reply":"2026-02-23T14:03:26.396048Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"# Dataset Columns Description\n\n| Column | Description |\n|--------|-------------|\n| authorized_flag | Indicates whether the transaction was authorized or not. |\n| card_id | Unique identifier for each customer card. |\n| city_id | Identifier of the city where the transaction took place. |\n| category_1 | Binary categorical feature representing a transaction type. |\n| installments | Number of installments for the transaction. |\n| category_3 | Categorical feature indicating merchant-related characteristics. |\n| merchant_category_id | Identifier of the merchant's category. |\n| merchant_id | Unique identifier for the merchant. |\n| month_lag | Number of months before or after the reference month when the transaction occurred. |\n| purchase_amount | Transaction amount normalized by Elo. |\n| purchase_date | Date and time when the transaction occurred. |\n| category_2 | Categorical feature related to merchant or transaction type. |\n| state_id | Identifier of the state where the transaction occurred. |\n| subsector_id | Identifier of the merchant’s business subsector. |","metadata":{}},{"cell_type":"markdown","source":"<a id=\"data-loading\"></a>\n# Data Loading","metadata":{}},{"cell_type":"code","source":"hist = pd.read_csv(\"/kaggle/input/elo-merchant-category-recommendation/historical_transactions.csv\")\nnew = pd.read_csv(\"/kaggle/input/elo-merchant-category-recommendation/new_merchant_transactions.csv\")\ntrain = pd.read_csv(\"/kaggle/input/elo-merchant-category-recommendation/train.csv\")\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:03:26.398069Z","iopub.execute_input":"2026-02-23T14:03:26.398608Z","iopub.status.idle":"2026-02-23T14:04:46.126260Z","shell.execute_reply.started":"2026-02-23T14:03:26.398557Z","shell.execute_reply":"2026-02-23T14:04:46.125387Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"print(\"Historical:\", hist.shape)\nprint(\"New:\", new.shape)\nprint(\"Train:\", train.shape)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:04:46.127957Z","iopub.execute_input":"2026-02-23T14:04:46.128264Z","iopub.status.idle":"2026-02-23T14:04:46.133302Z","shell.execute_reply.started":"2026-02-23T14:04:46.128238Z","shell.execute_reply":"2026-02-23T14:04:46.132508Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"Looking at the dataset sizes, the first thing that stands out is how heavily transaction-driven this data is. While the `train` dataset contains around 200K customers, the historical transactions table alone has more than 29 million rows. This clearly shows that customer behavior is recorded at a very granular, transaction level.\n\nThis structure means that we cannot directly analyze customers using the raw transaction data. To make sense of loyalty, engagement, and value, we need to summarize these millions of transactions at the customer level. This is exactly why customer-level aggregation becomes a necessary step before applying RFM or moving toward CLTV analysis.\n\nThe new merchant transactions dataset, although smaller, still provides important signals about how customer behavior continues and evolves over time. Overall, this initial size comparison helps clarify why the project focuses on transforming transaction-level data into customer-level insights from a CRM perspective.\n","metadata":{}},{"cell_type":"code","source":"hist.columns","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:04:46.134428Z","iopub.execute_input":"2026-02-23T14:04:46.134794Z","iopub.status.idle":"2026-02-23T14:04:46.149673Z","shell.execute_reply.started":"2026-02-23T14:04:46.134750Z","shell.execute_reply":"2026-02-23T14:04:46.148720Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"hist.head()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:04:46.150716Z","iopub.execute_input":"2026-02-23T14:04:46.151123Z","iopub.status.idle":"2026-02-23T14:04:46.183206Z","shell.execute_reply.started":"2026-02-23T14:04:46.151088Z","shell.execute_reply":"2026-02-23T14:04:46.182437Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"After inspecting the columns and a few sample rows, it’s clear that this dataset is transaction-oriented: each row represents a single purchase linked to a customer (`card_id`), not a pre-aggregated customer record.\n\nFor CRM-focused analysis, transaction timing (`purchase_date`, `month_lag`) is critical for recency metrics, while `purchase_amount` reflects spending behavior. The `authorized_flag` variable is typically used as a data-quality filter to keep only approved transactions. In our initial check on the historical transactions data, the records appear to be overwhelmingly (or entirely) authorized, but validating this step is still a good practice.\n\nOverall, the key takeaway is that the dataset must be aggregated to the customer level before applying RFM segmentation and later CLTV modeling.\n\n","metadata":{}},{"cell_type":"code","source":"use_cols = [\n    \"card_id\",\n    \"purchase_date\",\n    \"purchase_amount\",\n    \"authorized_flag\"]\n\nhist = pd.read_csv(\n    \"/kaggle/input/elo-merchant-category-recommendation/historical_transactions.csv\",\n    usecols=use_cols)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:04:46.184103Z","iopub.execute_input":"2026-02-23T14:04:46.184345Z","iopub.status.idle":"2026-02-23T14:05:26.155658Z","shell.execute_reply.started":"2026-02-23T14:04:46.184306Z","shell.execute_reply":"2026-02-23T14:05:26.154628Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"df=hist.copy()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:05:26.156834Z","iopub.execute_input":"2026-02-23T14:05:26.157169Z","iopub.status.idle":"2026-02-23T14:05:26.781151Z","shell.execute_reply.started":"2026-02-23T14:05:26.157134Z","shell.execute_reply":"2026-02-23T14:05:26.780254Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"df.head()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:05:26.782146Z","iopub.execute_input":"2026-02-23T14:05:26.782432Z","iopub.status.idle":"2026-02-23T14:05:26.793108Z","shell.execute_reply.started":"2026-02-23T14:05:26.782406Z","shell.execute_reply":"2026-02-23T14:05:26.792224Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"df.tail()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:05:26.796201Z","iopub.execute_input":"2026-02-23T14:05:26.796545Z","iopub.status.idle":"2026-02-23T14:05:26.813824Z","shell.execute_reply.started":"2026-02-23T14:05:26.796518Z","shell.execute_reply":"2026-02-23T14:05:26.812946Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"df.shape","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:05:26.815158Z","iopub.execute_input":"2026-02-23T14:05:26.815827Z","iopub.status.idle":"2026-02-23T14:05:26.829088Z","shell.execute_reply.started":"2026-02-23T14:05:26.815798Z","shell.execute_reply":"2026-02-23T14:05:26.828233Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"df.info()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:05:26.830250Z","iopub.execute_input":"2026-02-23T14:05:26.831005Z","iopub.status.idle":"2026-02-23T14:05:26.855411Z","shell.execute_reply.started":"2026-02-23T14:05:26.830971Z","shell.execute_reply":"2026-02-23T14:05:26.854497Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"df.describe().T","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:05:26.856582Z","iopub.execute_input":"2026-02-23T14:05:26.857223Z","iopub.status.idle":"2026-02-23T14:05:27.893870Z","shell.execute_reply.started":"2026-02-23T14:05:26.857196Z","shell.execute_reply":"2026-02-23T14:05:27.892939Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"Looking at the distribution of `purchase_amount`, we observe that although the mean is very small (0.036), the maximum value exceeds 6 million. This indicates the presence of extreme outliers in the dataset.This indicates the presence of extreme outliers in the dataset. \nThe large gap between the median (-0.688) and the maximum value, along with the extremely high standard deviation (1123), suggests that the distribution is heavily skewed.\nBefore performing RFM analysis, especially when calculating the Monetary metric, it is essential to handle these outliers using techniques such as clipping or winsorization. Otherwise, a small number of extreme transactions may disproportionately influence customer segmentation results.","metadata":{}},{"cell_type":"code","source":"df.isnull().sum()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:05:27.895081Z","iopub.execute_input":"2026-02-23T14:05:27.895738Z","iopub.status.idle":"2026-02-23T14:05:32.179390Z","shell.execute_reply.started":"2026-02-23T14:05:27.895697Z","shell.execute_reply":"2026-02-23T14:05:32.178635Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"# Data Preprocessing","metadata":{}},{"cell_type":"code","source":"df = df[df[\"authorized_flag\"] == \"Y\"]","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:05:32.180294Z","iopub.execute_input":"2026-02-23T14:05:32.180590Z","iopub.status.idle":"2026-02-23T14:05:35.432262Z","shell.execute_reply.started":"2026-02-23T14:05:32.180567Z","shell.execute_reply":"2026-02-23T14:05:35.431090Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"df.head()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:05:35.433457Z","iopub.execute_input":"2026-02-23T14:05:35.433871Z","iopub.status.idle":"2026-02-23T14:05:35.444139Z","shell.execute_reply.started":"2026-02-23T14:05:35.433844Z","shell.execute_reply":"2026-02-23T14:05:35.443316Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"At this stage, we filtered the dataset to keep only authorized transactions. \nAlthough the historical dataset appears to contain only authorized records, \nthis step ensures data quality and prevents potential invalid transactions \nfrom affecting the analysis.","metadata":{}},{"cell_type":"code","source":"df[\"purchase_date\"] = pd.to_datetime(df[\"purchase_date\"])","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:05:35.445419Z","iopub.execute_input":"2026-02-23T14:05:35.445716Z","iopub.status.idle":"2026-02-23T14:05:42.987032Z","shell.execute_reply.started":"2026-02-23T14:05:35.445692Z","shell.execute_reply":"2026-02-23T14:05:42.985621Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"df[\"purchase_amount_new\"] = df[\"purchase_amount\"] + 1","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:05:42.988589Z","iopub.execute_input":"2026-02-23T14:05:42.988974Z","iopub.status.idle":"2026-02-23T14:05:43.066565Z","shell.execute_reply.started":"2026-02-23T14:05:42.988939Z","shell.execute_reply":"2026-02-23T14:05:43.065654Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"df[[\"purchase_amount\", \"purchase_amount_new\"]].head()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:05:43.067587Z","iopub.execute_input":"2026-02-23T14:05:43.067851Z","iopub.status.idle":"2026-02-23T14:05:43.262159Z","shell.execute_reply.started":"2026-02-23T14:05:43.067827Z","shell.execute_reply":"2026-02-23T14:05:43.261181Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"At this stage, two important preprocessing steps were performed.\n\nFirst, the `purchase_date` column was converted into datetime format to enable time-based calculations such as recency measurement and customer lifetime estimation.\n\nSecond, since the `purchase_amount` variable in the Elo dataset is normalized and contains negative values, a +1 transformation was applied to create a strictly positive monetary variable (`purchase_amount_new`). This adjustment is necessary for probabilistic CLTV modeling approaches such as the Gamma-Gamma model, which require positive monetary inputs.","metadata":{}},{"cell_type":"code","source":"df.head()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:05:43.263298Z","iopub.execute_input":"2026-02-23T14:05:43.263700Z","iopub.status.idle":"2026-02-23T14:05:43.276534Z","shell.execute_reply.started":"2026-02-23T14:05:43.263671Z","shell.execute_reply":"2026-02-23T14:05:43.275670Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"df[\"authorized_flag\"].value_counts()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:05:43.277938Z","iopub.execute_input":"2026-02-23T14:05:43.278270Z","iopub.status.idle":"2026-02-23T14:05:44.652697Z","shell.execute_reply.started":"2026-02-23T14:05:43.278244Z","shell.execute_reply":"2026-02-23T14:05:44.651758Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"df.drop(\"authorized_flag\", axis=1, inplace=True)\ndf.drop(\"purchase_amount\",axis=1, inplace=True)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:05:44.653970Z","iopub.execute_input":"2026-02-23T14:05:44.654316Z","iopub.status.idle":"2026-02-23T14:05:46.018954Z","shell.execute_reply.started":"2026-02-23T14:05:44.654282Z","shell.execute_reply":"2026-02-23T14:05:46.017828Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"df.head()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:05:46.020037Z","iopub.execute_input":"2026-02-23T14:05:46.020352Z","iopub.status.idle":"2026-02-23T14:05:46.029981Z","shell.execute_reply.started":"2026-02-23T14:05:46.020307Z","shell.execute_reply":"2026-02-23T14:05:46.029138Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"# RFM","metadata":{}},{"cell_type":"markdown","source":"# Calculating RFM Metrics","metadata":{}},{"cell_type":"markdown","source":"**Recency:** Analysis date - customer's last purchase date (in days)\n\n**Frequency:** Total number of transactions per customer\n\n**Monetary:** Total spending per customer (using purchase_amount_new)","metadata":{}},{"cell_type":"markdown","source":"## 1. Define Analysis Date\nTo calculate the Recency metric, we define an analysis date. \nThe analysis date is set to one day after the last transaction date in the dataset. \nThis ensures that the most recent customer does not have a recency value of zero and \nallows consistent time-based comparisons across customers.\n","metadata":{}},{"cell_type":"code","source":"analysis_date = df[\"purchase_date\"].max() + pd.Timedelta(days=1)\n\nprint(\"Last transaction date in the dataset:\", df[\"purchase_date\"].max())\nprint(\"Analysis date:\", analysis_date)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:05:46.031251Z","iopub.execute_input":"2026-02-23T14:05:46.032099Z","iopub.status.idle":"2026-02-23T14:05:46.166309Z","shell.execute_reply.started":"2026-02-23T14:05:46.032067Z","shell.execute_reply":"2026-02-23T14:05:46.165579Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"## 2. Customer-level RFM aggregation","metadata":{}},{"cell_type":"code","source":"rfm = df.groupby(\"card_id\").agg({\n    \"purchase_date\": [lambda x: (analysis_date - x.max()).days, \"count\"],\n    \"purchase_amount_new\": \"sum\"\n})\n\nrfm.columns = [\"recency\", \"frequency\", \"monetary\"]\nrfm.head()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:05:46.167515Z","iopub.execute_input":"2026-02-23T14:05:46.167819Z","iopub.status.idle":"2026-02-23T14:06:16.526893Z","shell.execute_reply.started":"2026-02-23T14:05:46.167794Z","shell.execute_reply":"2026-02-23T14:06:16.525818Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"## 3. Summary statistics","metadata":{}},{"cell_type":"code","source":"rfm.describe().T","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:16.527966Z","iopub.execute_input":"2026-02-23T14:06:16.528208Z","iopub.status.idle":"2026-02-23T14:06:16.578558Z","shell.execute_reply.started":"2026-02-23T14:06:16.528188Z","shell.execute_reply":"2026-02-23T14:06:16.577593Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"rfm = rfm[rfm[\"monetary\"] > 0]","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:16.579597Z","iopub.execute_input":"2026-02-23T14:06:16.579912Z","iopub.status.idle":"2026-02-23T14:06:16.667683Z","shell.execute_reply.started":"2026-02-23T14:06:16.579886Z","shell.execute_reply":"2026-02-23T14:06:16.666645Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"rfm.shape","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:16.673141Z","iopub.execute_input":"2026-02-23T14:06:16.673498Z","iopub.status.idle":"2026-02-23T14:06:16.685514Z","shell.execute_reply.started":"2026-02-23T14:06:16.673469Z","shell.execute_reply":"2026-02-23T14:06:16.684586Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"# Calculating RFM Scores","metadata":{}},{"cell_type":"markdown","source":"## 1. Recency score\nlow recency = recent customer = higher score","metadata":{}},{"cell_type":"code","source":"rfm[\"recency_score\"] = pd.qcut(\n    rfm[\"recency\"],\n    5,\n    labels=[5, 4, 3, 2, 1]\n)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:16.686665Z","iopub.execute_input":"2026-02-23T14:06:16.686966Z","iopub.status.idle":"2026-02-23T14:06:16.725798Z","shell.execute_reply.started":"2026-02-23T14:06:16.686940Z","shell.execute_reply":"2026-02-23T14:06:16.724730Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"## 2. Frequency score\nhigh frequency = higher score\nrank(method=\"first\") prevents qcut errors when many customers share the same frequency value","metadata":{}},{"cell_type":"code","source":"rfm[\"frequency_score\"] = pd.qcut(\n    rfm[\"frequency\"].rank(method=\"first\"),\n    5,\n    labels=[1, 2, 3, 4, 5]\n)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:16.726985Z","iopub.execute_input":"2026-02-23T14:06:16.727299Z","iopub.status.idle":"2026-02-23T14:06:16.793531Z","shell.execute_reply.started":"2026-02-23T14:06:16.727265Z","shell.execute_reply":"2026-02-23T14:06:16.792589Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"## 3. Monetary score\nhigh monetary = higher score","metadata":{}},{"cell_type":"code","source":"rfm[\"monetary_score\"] = pd.qcut(\n    rfm[\"monetary\"],\n    5,\n    labels=[1, 2, 3, 4, 5]\n)\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:16.794631Z","iopub.execute_input":"2026-02-23T14:06:16.795011Z","iopub.status.idle":"2026-02-23T14:06:16.824092Z","shell.execute_reply.started":"2026-02-23T14:06:16.794977Z","shell.execute_reply":"2026-02-23T14:06:16.823180Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"## 4. Create combined RF score","metadata":{}},{"cell_type":"code","source":"rfm[\"RFM_SCORE\"] = (\n    rfm[\"recency_score\"].astype(str) +\n    rfm[\"frequency_score\"].astype(str)\n)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:16.825146Z","iopub.execute_input":"2026-02-23T14:06:16.825440Z","iopub.status.idle":"2026-02-23T14:06:16.933079Z","shell.execute_reply.started":"2026-02-23T14:06:16.825415Z","shell.execute_reply":"2026-02-23T14:06:16.932034Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"rfm.head()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:16.934122Z","iopub.execute_input":"2026-02-23T14:06:16.934410Z","iopub.status.idle":"2026-02-23T14:06:16.945965Z","shell.execute_reply.started":"2026-02-23T14:06:16.934384Z","shell.execute_reply":"2026-02-23T14:06:16.944943Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"rfm[\"RFM_SCORE\"].value_counts().sort_index()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:16.947191Z","iopub.execute_input":"2026-02-23T14:06:16.947916Z","iopub.status.idle":"2026-02-23T14:06:16.993146Z","shell.execute_reply.started":"2026-02-23T14:06:16.947886Z","shell.execute_reply":"2026-02-23T14:06:16.992253Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"rfm[rfm[\"RFM_SCORE\"] == \"55\"].head()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:16.994225Z","iopub.execute_input":"2026-02-23T14:06:16.994514Z","iopub.status.idle":"2026-02-23T14:06:17.048121Z","shell.execute_reply.started":"2026-02-23T14:06:16.994482Z","shell.execute_reply":"2026-02-23T14:06:17.047305Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"rfm[rfm[\"RFM_SCORE\"] == \"11\"].head()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:17.049307Z","iopub.execute_input":"2026-02-23T14:06:17.049965Z","iopub.status.idle":"2026-02-23T14:06:17.092134Z","shell.execute_reply.started":"2026-02-23T14:06:17.049935Z","shell.execute_reply":"2026-02-23T14:06:17.091246Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"# Creating & Analysing RFM Segments","metadata":{}},{"cell_type":"code","source":"# Segment mapping based on RF score (RFM_SCORE = recency_score + frequency_score)\nseg_map = {\n    r'[1-2][1-2]': 'hibernating',\n    r'[1-2][3-4]': 'at_risk',\n    r'[1-2]5': 'cant_loose',\n    r'3[1-2]': 'about_to_sleep',\n    r'33': 'need_attention',\n    r'[3-4][4-5]': 'loyal_customers',\n    r'41': 'promising',\n    r'51': 'new_customers',\n    r'[4-5][2-3]': 'potential_loyalists',\n    r'5[4-5]': 'champions'\n}\n\n# Assign segment labels using regex mapping\nrfm[\"segment\"] = rfm[\"RFM_SCORE\"].replace(seg_map, regex=True)\n\n# Segment summary (mean + count)\nsegment_summary = (\n    rfm.groupby(\"segment\")[[\"recency\", \"frequency\", \"monetary\"]]\n       .agg([\"mean\", \"count\"])\n       .sort_values((\"recency\", \"mean\"))\n)\n\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:17.093197Z","iopub.execute_input":"2026-02-23T14:06:17.093546Z","iopub.status.idle":"2026-02-23T14:06:19.679221Z","shell.execute_reply.started":"2026-02-23T14:06:17.093514Z","shell.execute_reply":"2026-02-23T14:06:19.678284Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"segment_summary","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:19.680263Z","iopub.execute_input":"2026-02-23T14:06:19.680644Z","iopub.status.idle":"2026-02-23T14:06:19.693643Z","shell.execute_reply.started":"2026-02-23T14:06:19.680615Z","shell.execute_reply":"2026-02-23T14:06:19.692692Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"#### Champions\n**What We Observe:**\n- Very low recency\n- Extremely high frequency\n- High monetary value\n\n**Interpretation:**\nChampions represent the most valuable customer segment. They are highly active and generate significant revenue. Retention strategies such as exclusive rewards, VIP programs, and personalized offers should be prioritized to maintain their engagement.\n\n---\n\n#### New Customers\n**What We Observe:**\n- Very low recency\n- Low frequency\n- Low monetary value\n\n**Interpretation:**\nNew customers are recently acquired and still in the early stage of the customer lifecycle. Although their current value is limited, they have strong growth potential. Effective onboarding and engagement campaigns may convert them into loyal customers.\n\n---\n\n#### Loyal Customers\n**What We Observe:**\n- Low recency\n- High frequency\n- High monetary value\n\n**Interpretation:**\nLoyal customers consistently generate revenue and form the stable core of the customer base. Strengthening relationships with this segment can help transition them into Champions.\n\n---\n\n#### Cant_Loose\n**What We Observe:**\n- Very high frequency\n- Very high monetary value\n- High recency (long time since last transaction)\n\n**Interpretation:**\nThis is one of the most critical segments. These customers were historically very valuable but have recently become inactive. They present a high churn risk and should be targeted with urgent retention campaigns.\n\n---\n\n####  At Risk\n**What We Observe:**\n- High recency\n- Moderate frequency\n- Moderate monetary value\n\n**Interpretation:**\nAt-risk customers show declining engagement. Targeted win-back campaigns and personalized incentives may help re-engage this group.\n\n---\n\n#### Hibernating\n**What We Observe:**\n- Very high recency\n- Low frequency\n- Low monetary value\n\n**Interpretation:**\nHibernating customers are inactive and generate low value. They represent low strategic priority compared to other segments.\n\n---\n\n####  Need Attention\n**What We Observe:**\n- Moderate recency\n- Moderate frequency\n- Moderate monetary value\n\n**Interpretation:**\nCustomers in this segment are active but not highly engaged. With proper marketing strategies, they may transition into higher-value segments.\n\n---\n\n#### About to Sleep\n**What We Observe:**\n- Increasing recency\n- Moderate frequency\n- Moderate monetary value\n\n**Interpretation:**\nAbout-to-sleep customers show early signs of disengagement. Preventive engagement strategies are necessary to avoid potential churn.\n\n---\n\n#### Promising\n**What We Observe:**\n- Low recency\n- Low frequency\n- Low monetary value\n\n**Interpretation:**\nPromising customers are recently active but currently generate limited revenue. With the right engagement strategy, they may evolve into loyal or high-value customers.\n\n---\n\n### 📌 Overall Conclusion\n\nThe RFM segmentation successfully differentiates customers based on purchasing behavior. High-value segments such as Champions and Loyal Customers drive revenue, while Cant_Loose and At Risk segments require proactive retention strategies. Lower-value segments such as Hibernating represent minimal strategic importance. Overall, the segmentation provides actionable insights for customer lifecycle management and targeted marketing decisions.\n","metadata":{}},{"cell_type":"code","source":"rfm[rfm[\"segment\"] == \"cant_loose\"].head()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:19.694773Z","iopub.execute_input":"2026-02-23T14:06:19.695117Z","iopub.status.idle":"2026-02-23T14:06:19.749240Z","shell.execute_reply.started":"2026-02-23T14:06:19.695080Z","shell.execute_reply":"2026-02-23T14:06:19.748408Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"The sample customers in the \"cant_loose\" segment show extremely high frequency and monetary values, indicating strong historical contribution. However, their high recency values suggest that they have not made purchases recently. This segment represents high-value customers with strong churn risk and should be prioritized in retention campaigns.\n","metadata":{}},{"cell_type":"code","source":"cant_loose_ids = rfm[rfm[\"segment\"] == \"cant_loose\"].index\ncant_loose_ids[:10]   # first 10","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:19.750258Z","iopub.execute_input":"2026-02-23T14:06:19.750582Z","iopub.status.idle":"2026-02-23T14:06:19.786650Z","shell.execute_reply.started":"2026-02-23T14:06:19.750549Z","shell.execute_reply":"2026-02-23T14:06:19.785744Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"Extracting the card_ids of the \"cant_loose\" segment enables targeted marketing actions. These customers can be directly integrated into CRM systems for personalized retention campaigns, special discounts, or reactivation strategies.\n","metadata":{}},{"cell_type":"code","source":"new_df = pd.DataFrame()\nnew_df[\"new_customer_id\"] = rfm[rfm[\"segment\"] == \"new_customers\"].index\n\nnew_df.head()\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:19.787678Z","iopub.execute_input":"2026-02-23T14:06:19.788011Z","iopub.status.idle":"2026-02-23T14:06:19.825406Z","shell.execute_reply.started":"2026-02-23T14:06:19.787986Z","shell.execute_reply":"2026-02-23T14:06:19.824421Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"new_df.to_csv(\"new_customers.csv\", index=False)\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:19.826827Z","iopub.execute_input":"2026-02-23T14:06:19.827155Z","iopub.status.idle":"2026-02-23T14:06:19.849990Z","shell.execute_reply.started":"2026-02-23T14:06:19.827121Z","shell.execute_reply":"2026-02-23T14:06:19.849002Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"Exporting the new customer segment into a CSV file enables operational usage. This allows marketing teams to directly use the segmented customer list for onboarding campaigns and personalized engagement strategies.\n","metadata":{}},{"cell_type":"code","source":"rfm[\"segment\"].value_counts()\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:19.851148Z","iopub.execute_input":"2026-02-23T14:06:19.851530Z","iopub.status.idle":"2026-02-23T14:06:19.878552Z","shell.execute_reply.started":"2026-02-23T14:06:19.851491Z","shell.execute_reply":"2026-02-23T14:06:19.877780Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"The segment distribution reveals that a large portion of customers are classified as hibernating, indicating low engagement. High-value segments such as Champions, Loyal Customers, and Potential Loyalists form a significant share of the customer base and represent the main revenue drivers.\n\nAdditionally, the substantial size of the At Risk segment highlights potential churn threats. Immediate retention strategies should be considered to prevent revenue loss.\n","metadata":{}},{"cell_type":"code","source":"rfm[\"segment\"].value_counts().plot(kind=\"bar\")\nplt.title(\"Customer Segment Distribution\")\nplt.xticks(rotation=45)\nplt.show()\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:19.879633Z","iopub.execute_input":"2026-02-23T14:06:19.879957Z","iopub.status.idle":"2026-02-23T14:06:20.203593Z","shell.execute_reply.started":"2026-02-23T14:06:19.879924Z","shell.execute_reply":"2026-02-23T14:06:20.202731Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"rfm.groupby(\"segment\")[[\"recency\",\"frequency\",\"monetary\"]].mean()\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:20.204598Z","iopub.execute_input":"2026-02-23T14:06:20.204866Z","iopub.status.idle":"2026-02-23T14:06:20.249545Z","shell.execute_reply.started":"2026-02-23T14:06:20.204841Z","shell.execute_reply":"2026-02-23T14:06:20.248716Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"# Segment Revenue Contribution","metadata":{}},{"cell_type":"code","source":"segment_revenue = rfm.groupby(\"segment\")[\"monetary\"].sum().sort_values(ascending=False)\n\nsegment_revenue_ratio = segment_revenue / segment_revenue.sum() * 100\n\nsegment_revenue_ratio\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:20.250587Z","iopub.execute_input":"2026-02-23T14:06:20.250864Z","iopub.status.idle":"2026-02-23T14:06:20.286223Z","shell.execute_reply.started":"2026-02-23T14:06:20.250838Z","shell.execute_reply":"2026-02-23T14:06:20.285507Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"segment_colors = {\n    \"champions\": \"gold\",\n    \"loyal_customers\": \"green\",\n    \"cant_loose\": \"darkred\",\n    \"at_risk\": \"orange\",\n    \"hibernating\": \"gray\",\n    \"new_customers\": \"blue\",\n    \"promising\": \"lightgreen\",\n    \"about_to_sleep\": \"purple\",\n    \"need_attention\": \"pink\",\n    \"potential_loyalists\": \"teal\"\n}\n\n# Create a color list according to segment order.\ncolors = [segment_colors[seg] for seg in segment_revenue_ratio.index]\n\nplt.figure()\nax = segment_revenue_ratio.plot(kind=\"bar\", color=colors)\n\nplt.title(\"Revenue Contribution (%) by Segment\")\nplt.xlabel(\"Segment\")\nplt.ylabel(\"Revenue Percentage\")\nplt.xticks(rotation=45)\n\n# Write the percentage values ​​above the bars.\nfor i, v in enumerate(segment_revenue_ratio):\n    ax.text(i, v + 0.5, f\"{v:.1f}%\", ha='center')\n\nplt.show()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:20.287298Z","iopub.execute_input":"2026-02-23T14:06:20.287650Z","iopub.status.idle":"2026-02-23T14:06:20.481195Z","shell.execute_reply.started":"2026-02-23T14:06:20.287615Z","shell.execute_reply":"2026-02-23T14:06:20.480156Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"### `Champions (34.3%)`:\n\nChampions generate the highest share of total revenue. They are highly active, purchase frequently, and spend significantly. This segment represents the core revenue engine of the business. Retention strategies such as VIP programs, exclusive rewards, and personalized offers should be prioritized to maintain their loyalty.\n\n---\n\n### `Loyal Customers (23.3%)`:\n\nLoyal Customers contribute a substantial portion of total revenue and show consistent purchasing behavior. They are highly valuable but slightly less active than Champions. Upselling and cross-selling strategies can help move them into the Champions segment.\n\n---\n\n### `Cant_Loose (11.5%)`:\n\nCant_Loose customers were historically high spenders with frequent transactions, but their recent inactivity signals churn risk. Losing this segment would result in a significant revenue loss. Immediate win-back campaigns and personalized incentives are strongly recommended.\n\n---\n\n### `At Risk (11.4%)`:\n\nAt Risk customers are gradually disengaging. Although their contribution is still meaningful, declining recency indicates potential churn. Preventive engagement strategies and targeted discounts may help retain this segment.\n\n---\n\n### `Potential Loyalists (7.8%)`:\n\nPotential Loyalists show promising behavior with moderate frequency and monetary value. With proper engagement and nurturing strategies, they can evolve into Loyal Customers or Champions.\n\n---\n\n### `Hibernating (5.6%)`:\n\nHibernating customers have low engagement and limited revenue contribution. They have been inactive for a long period and represent low immediate strategic value. Low-cost reactivation campaigns may be applied.\n\n---\n\n### `About to Sleep (2.6%)`:\n\nAbout-to-Sleep customers show early signs of disengagement. Although their revenue contribution is limited, proactive communication strategies may prevent them from becoming fully inactive.\n\n---\n\n### `Need Attention (2.6%)`:\n\nThis segment consists of moderately active customers who require engagement reinforcement. Without targeted strategies, they may shift toward the At Risk segment.\n\n---\n\n### `Promising (0.5%)`:\n\nPromising customers are recently active but currently generate low revenue. They represent growth potential rather than immediate revenue drivers.\n\n---\n\n### `New Customers (0.3%)`:\n\nNew Customers have recently joined and contribute minimally to current revenue. However, they represent long-term growth opportunities. Effective onboarding and engagement strategies are essential to increase their lifetime value.\n\n---\n\n### Overall Strategic Insight\n\nRevenue is highly concentrated in the top four segments (Champions, Loyal Customers, Cant_Loose, and At Risk), which together generate nearly 80% of total revenue. This highlights the importance of retention and risk management strategies in sustaining overall business performance.\n","metadata":{}},{"cell_type":"markdown","source":"# RFM Validation & Business Insights","metadata":{}},{"cell_type":"markdown","source":"## 1. Segment behavioral comparison\n\nIn this section, we compare key behavioral metrics across RFM segments\nto validate whether the segmentation meaningfully differentiates customers.\n\nWe analyze:\n- Average Recency\n- Average Frequency\n- Average Monetary\n- Revenue per customer\n- Order behavior\n\nThis helps us confirm that each segment represents distinct purchasing behavior.","metadata":{}},{"cell_type":"code","source":"rfm.columns","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:20.482181Z","iopub.execute_input":"2026-02-23T14:06:20.482515Z","iopub.status.idle":"2026-02-23T14:06:20.488802Z","shell.execute_reply.started":"2026-02-23T14:06:20.482488Z","shell.execute_reply":"2026-02-23T14:06:20.487844Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"segment_summary = rfm.groupby(\"segment\").agg({\n    \"recency\": \"mean\",\n    \"frequency\": \"mean\",\n    \"monetary\": \"mean\"\n})\n\nsegment_summary[\"CustomerCount\"] = rfm.groupby(\"segment\").size()\n\nsegment_summary.sort_values(\"monetary\", ascending=False)\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:20.489814Z","iopub.execute_input":"2026-02-23T14:06:20.490059Z","iopub.status.idle":"2026-02-23T14:06:20.571698Z","shell.execute_reply.started":"2026-02-23T14:06:20.490037Z","shell.execute_reply":"2026-02-23T14:06:20.570801Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"\nsegments = {\n    \"Champions\": (5, 78),\n    \"Loyal Customers\": (12, 56),\n    \"Potential Loyalists\": (8, 18),\n    \"Need Attention\": (18, 22),\n    \"About to Sleep\": (20, 12),\n    \"New Customers\": (3, 6),\n    \"Cant Lose\": (95, 82),\n    \"At Risk\": (108, 27),\n    \"Hibernating\": (112, 9),\n}\n\n\ncolor_palette = {\n    \"Champions\": \"#1f77b4\",       \n    \"Loyal Customers\": \"#2ca02c\",  \n    \"Potential Loyalists\": \"#17becf\",\n    \"Need Attention\": \"#ff7f0e\",\n    \"About to Sleep\": \"#9467bd\",\n    \"New Customers\": \"#8c564b\",\n    \"Cant Lose\": \"#d62728\",\n    \"At Risk\": \"#e377c2\",\n    \"Hibernating\": \"#7f7f7f\",\n}\n\nplt.figure(figsize=(10, 6))\n\nfor segment, (recency, monetary) in segments.items():\n    plt.scatter(\n        recency,\n        monetary,\n        color=color_palette[segment],\n        s=120,\n        alpha=0.85\n    )\n    plt.text(\n        recency + 1,\n        monetary + 1,\n        segment,\n        fontsize=9\n    )\n\nplt.title(\"Segment Behavioral Map\", fontsize=13)\nplt.xlabel(\"Recency\", fontsize=11)\nplt.ylabel(\"Monetary\", fontsize=11)\n\nplt.grid(alpha=0.2)\nplt.tight_layout()\nplt.show()\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:20.572764Z","iopub.execute_input":"2026-02-23T14:06:20.573086Z","iopub.status.idle":"2026-02-23T14:06:20.972460Z","shell.execute_reply.started":"2026-02-23T14:06:20.573059Z","shell.execute_reply":"2026-02-23T14:06:20.971683Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"The segment-level averages confirm that the RFM segmentation successfully differentiates customer behavior.\n\n`Cant_Loose` customers show the highest historical frequency and monetary values but high recency, indicating significant churn risk. \n\n`Champions` remain highly active and generate substantial revenue, making them the core revenue drivers.\n\n`Hibernating` customers form the largest segment in terms of customer count but contribute relatively low monetary value, suggesting limited short-term strategic importance.\n\n`Potential Loyalists` represent a key growth opportunity, as they show active engagement with moderate purchasing behavior.\n","metadata":{}},{"cell_type":"markdown","source":"## 2. Revenue Concentration Analysis","metadata":{}},{"cell_type":"code","source":"segment_revenue = (\n    rfm.groupby(\"segment\")[\"monetary\"]\n    .sum()\n    .sort_values(ascending=False)\n    .to_frame(name=\"TotalRevenue\")\n)\n\nsegment_revenue","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:20.973510Z","iopub.execute_input":"2026-02-23T14:06:20.973821Z","iopub.status.idle":"2026-02-23T14:06:21.011742Z","shell.execute_reply.started":"2026-02-23T14:06:20.973788Z","shell.execute_reply":"2026-02-23T14:06:21.010876Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"The revenue distribution shows that the Champions segment generates the highest total revenue, followed by Loyal Customers. This indicates that a relatively smaller portion of customers is responsible for a significant share of overall revenue.\n\nThe Cant Lose and At Risk segments also contribute substantially, despite their high recency values. This signals potential revenue loss risk if no retention strategy is applied.","metadata":{}},{"cell_type":"code","source":"segment_revenue[\"RevenueShare%\"] = (\n    segment_revenue[\"TotalRevenue\"] /\n    segment_revenue[\"TotalRevenue\"].sum()\n) * 100\n\nsegment_revenue","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:21.012874Z","iopub.execute_input":"2026-02-23T14:06:21.013197Z","iopub.status.idle":"2026-02-23T14:06:21.025870Z","shell.execute_reply.started":"2026-02-23T14:06:21.013159Z","shell.execute_reply":"2026-02-23T14:06:21.024742Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"Champions alone generate approximately 34% of total revenue. Together with Loyal Customers (23%), the top two segments account for nearly 57% of overall revenue.\n\nThis confirms a strong revenue concentration effect, similar to the Pareto principle.","metadata":{}},{"cell_type":"code","source":"plt.figure()\nsegment_revenue[\"RevenueShare%\"].plot(kind=\"bar\")\n\nplt.title(\"Revenue Share (%) by Segment\")\nplt.xlabel(\"Segment\")\nplt.ylabel(\"Revenue Share (%)\")\nplt.xticks(rotation=45)\n\nplt.show()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:21.027427Z","iopub.execute_input":"2026-02-23T14:06:21.027773Z","iopub.status.idle":"2026-02-23T14:06:21.217923Z","shell.execute_reply.started":"2026-02-23T14:06:21.027744Z","shell.execute_reply":"2026-02-23T14:06:21.216864Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"The visual clearly highlights that revenue is highly concentrated in the Champions and Loyal Customers segments. Lower-value segments such as Promising and New Customers contribute less than 1% individually.\n\nThis suggests that growth potential lies in nurturing mid-level segments rather than relying solely on top-tier customers.","metadata":{}},{"cell_type":"code","source":"segment_revenue[\"Cumulative_%\"] = (\n    segment_revenue[\"RevenueShare%\"].cumsum()\n)\n\nplt.figure()\n\nsegment_revenue[\"Cumulative_%\"].plot(marker=\"o\")\n\nplt.title(\"Cumulative Revenue Contribution (%)\")\nplt.xlabel(\"Segment\")\nplt.ylabel(\"Cumulative Revenue (%)\")\nplt.xticks(rotation=45)\n\nplt.show()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:21.218976Z","iopub.execute_input":"2026-02-23T14:06:21.219236Z","iopub.status.idle":"2026-02-23T14:06:21.364568Z","shell.execute_reply.started":"2026-02-23T14:06:21.219213Z","shell.execute_reply":"2026-02-23T14:06:21.363785Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"The cumulative revenue curve shows that the first three segments already account for nearly 70% of total revenue. The first four segments reach approximately 80%.\n\nThis confirms a classic revenue concentration structure and highlights the strategic importance of top segments.","metadata":{}},{"cell_type":"code","source":"segment_revenue[\"CustomerCount\"] = rfm[\"segment\"].value_counts()\n\nsegment_revenue[\"RevenuePerCustomer\"] = (\n    segment_revenue[\"TotalRevenue\"] /\n    segment_revenue[\"CustomerCount\"]\n)\n\nsegment_revenue","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:21.365615Z","iopub.execute_input":"2026-02-23T14:06:21.365870Z","iopub.status.idle":"2026-02-23T14:06:21.398363Z","shell.execute_reply.started":"2026-02-23T14:06:21.365846Z","shell.execute_reply":"2026-02-23T14:06:21.397530Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"Cant Lose customers have the highest revenue per customer (82), even higher than Champions (78). This is extremely critical, as losing this segment would significantly impact revenue.\n\nChampions are both high-volume and high-value, making them the core revenue drivers.\n\nLower segments (Hibernating, New Customers) generate minimal revenue per customer, requiring cost-efficient marketing strategies.","metadata":{}},{"cell_type":"markdown","source":"### General Revenue Concentration Result\nThe revenue analysis reveals a highly concentrated revenue structure where top-performing segments dominate overall financial performance. While `Champions` and `Loyal Customers` drive the majority of revenue, high-value but high-risk segments such as `Cant Lose` require urgent retention strategies to prevent potential revenue loss.\n\nThis segmentation provides a strong foundation for value-based marketing and future CLTV modeling.","metadata":{}},{"cell_type":"markdown","source":"## 3. Risk & Opportunity Assessment","metadata":{}},{"cell_type":"markdown","source":"### Segment Risk Matrix Table","metadata":{}},{"cell_type":"code","source":"risk_table = rfm.groupby(\"segment\")[[\"recency\", \"frequency\", \"monetary\"]].mean()\n\nrisk_table.sort_values(\"recency\", ascending=False)\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:21.399480Z","iopub.execute_input":"2026-02-23T14:06:21.399788Z","iopub.status.idle":"2026-02-23T14:06:21.458471Z","shell.execute_reply.started":"2026-02-23T14:06:21.399762Z","shell.execute_reply":"2026-02-23T14:06:21.457664Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"### Revenue at Risk Calculation","metadata":{}},{"cell_type":"code","source":"risk_segments = [\"cant_loose\", \"at_risk\"]\n\nrevenue_at_risk = segment_revenue.loc[risk_segments, \"TotalRevenue\"].sum()\n\ntotal_revenue = segment_revenue[\"TotalRevenue\"].sum()\n\nrevenue_at_risk_ratio = (revenue_at_risk / total_revenue) * 100\n\nrevenue_at_risk_ratio\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:21.459558Z","iopub.execute_input":"2026-02-23T14:06:21.459885Z","iopub.status.idle":"2026-02-23T14:06:21.467863Z","shell.execute_reply.started":"2026-02-23T14:06:21.459852Z","shell.execute_reply":"2026-02-23T14:06:21.466866Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"The analysis reveals that approximately 22.9% of total revenue is concentrated in high-risk segments (Cant Lose and At Risk).\n\nCant Lose customers have extremely high monetary value but elevated recency, indicating that they were previously high-value customers who have recently reduced activity.\n\nIf no retention strategy is implemented, nearly one-quarter of total revenue may be exposed to churn risk.\n\nHibernating customers, while high in recency, generate minimal revenue and therefore represent lower financial risk.","metadata":{}},{"cell_type":"markdown","source":"### Revenue Risk Matrix","metadata":{}},{"cell_type":"code","source":"# Segment averages\nrisk_table = rfm.groupby(\"segment\")[[\"recency\", \"frequency\", \"monetary\"]].mean()\n\n\ncolor_map = {\n    \"champions\": \"#1f77b4\",\n    \"loyal_customers\": \"#2ca02c\",\n    \"cant_loose\": \"#d62728\",\n    \"at_risk\": \"#ff7f0e\",\n    \"hibernating\": \"#7f7f7f\",\n    \"potential_loyalists\": \"#17becf\",\n    \"about_to_sleep\": \"#9467bd\",\n    \"need_attention\": \"#8c564b\",\n    \"promising\": \"#e377c2\",\n    \"new_customers\": \"#bcbd22\"\n}\n\nplt.figure(figsize=(10,7))\n\nfor segment in risk_table.index:\n    plt.scatter(\n        risk_table.loc[segment, \"recency\"],\n        risk_table.loc[segment, \"monetary\"],\n        s=risk_table.loc[segment, \"frequency\"] * 2,\n        color=color_map[segment],\n        alpha=0.8\n    )\n    \n    # yazı offset\n    plt.text(\n        risk_table.loc[segment, \"recency\"] + 2,\n        risk_table.loc[segment, \"monetary\"] + 2,\n        segment.replace(\"_\",\" \"),\n        fontsize=9\n    )\n\n\nplt.axvline(risk_table[\"recency\"].mean(), color=\"black\", linestyle=\"--\", alpha=0.5)\nplt.axhline(risk_table[\"monetary\"].mean(), color=\"black\", linestyle=\"--\", alpha=0.5)\n\nplt.title(\"Revenue Risk Matrix\", fontsize=14)\nplt.xlabel(\"Recency (Risk Level)\", fontsize=12)\nplt.ylabel(\"Monetary (Customer Value)\", fontsize=12)\n\nplt.grid(alpha=0.2)\nplt.tight_layout()\nplt.show()\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:21.468901Z","iopub.execute_input":"2026-02-23T14:06:21.469229Z","iopub.status.idle":"2026-02-23T14:06:21.815099Z","shell.execute_reply.started":"2026-02-23T14:06:21.469194Z","shell.execute_reply":"2026-02-23T14:06:21.814290Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"The Revenue Risk Matrix clearly illustrates the structural distribution of customer value and churn risk across segments.\n\nThe horizontal axis (Recency) represents churn risk, while the vertical axis (Monetary) represents customer value. The size of each bubble reflects purchase frequency.\n\n---\n\nThe visualization reveals a clear separation between high-value active customers and high-value at-risk customers.\n\n`Champions` are positioned in the low-recency, high-monetary quadrant, confirming that they are both active and highly profitable. They represent the core revenue base.\n\n`Cant Lose` customers appear in the high-recency, high-monetary quadrant, indicating a critical risk zone. These customers were previously very valuable but have not transacted recently. This segment poses a direct revenue threat if no retention action is implemented.\n\n`At Risk` customers also show elevated recency levels, although their monetary contribution is moderate. They require timely intervention to prevent further decline.\n\n`Hibernating` customers are located in the high-recency, low-monetary area. While churn probability is high, their financial impact is limited.\n\n`Potential Loyalists` and `Loyal Customers` are positioned in lower-risk zones and present growth opportunities through engagement and cross-selling strategies.\n\nOverall, the matrix highlights that a substantial portion of high-value revenue is exposed to churn risk, emphasizing the need for targeted retention strategies focused on high-value segments.","metadata":{}},{"cell_type":"markdown","source":"## 4. Marketing Strategy Recommendations\n(Elo Transaction-Based RFM Framework)","metadata":{}},{"cell_type":"markdown","source":"### 1. Champions\n*(High Monetary – High Frequency – Very Low Recency)*\n\n**Behavioral Insight:**\nChampions are the most engaged card users. They transact frequently, spend consistently, and show very recent activity. They represent the strongest contributors to the payment ecosystem.\n\n**Risk Level:** Very Low\n\n**Strategic Focus:** Retention and ecosystem value maximization.\n\n**Recommended Actions:**\n* Introduce tier-based card usage rewards\n* Offer merchant-specific premium cashback campaigns\n* Provide early access to partner merchant promotions\n* Encourage cross-category spending expansion\n* Launch referral-based incentives to leverage advocacy\n\n**Strategic Objective:** Increase Customer Lifetime Value (CLTV) while maintaining profitability and engagement within the payment ecosystem.\n","metadata":{}},{"cell_type":"markdown","source":"### 2. Loyal Customers\n\n*(High Frequency – Moderate to High Monetary – Low Recency)*\n\n**Behavioral Insight:**\nThese customers are consistently active but slightly below Champions in monetary value. They are stable revenue contributors.\n\n**Risk Level:** Low\n\n**Strategic Focus:**\nUpselling and frequency enhancement.\n\n**Recommended Actions:**\n\n* Introduce spending threshold-based rewards\n\n* Offer multi-category cashback bundles\n\n* Promote seasonal merchant campaigns\n\n* Encourage incremental spending through milestone rewards\n\n**Strategic Objective:**\nConvert Loyal Customers into Champions by increasing average transaction value and card usage depth.","metadata":{}},{"cell_type":"markdown","source":"### 3. Cant Lose\n\n*(Very High Monetary – High Frequency – High Recency)*\n\n**Behavioral Insight:**\nThese customers historically generated very high revenue per customer but show increasing inactivity. This is a critical revenue-risk segment.\n\n**Risk Level:** Extremely High\n\n**Recommended Actions:**\n\n* Launch reactivation cashback campaigns\n\n* Offer limited-time high-value merchant incentives\n\n* Send inactivity-triggered promotional offers\n\n* Analyze previous merchant categories to personalize offers\n\n**Strategic Objective:**\nPrevent revenue loss by reactivating high-value card users before churn occurs","metadata":{}},{"cell_type":"markdown","source":"### 4. At Risk\n\n*(Moderate Monetary – Medium Frequency – High Recency)*\n\n**Behavioral Insight:**\nThese customers are gradually reducing card usage. Revenue contribution is moderate but declining.\n\n**Risk Level:** High\n\n**Recommended Actions:**\n\n* Implement time-based reminder campaigns\n\n* Offer category-specific discounts\n\n* Deploy automated inactivity monitoring triggers\n\n* Provide short-term bonus reward multipliers\n\n**Strategic Objective:**\nReduce churn probability and stabilize card usage behavior.","metadata":{}},{"cell_type":"markdown","source":"### 5. Potential Loyalists\n\n*(Moderate Frequency – Low to Moderate Monetary – Low Recency)*\n\n**Behavioral Insight:**\nThese customers are relatively active but have not yet reached high spending levels.\n\n**Risk Level:** Low to Medium\n\n**Recommended Actions:**\n\n* Offer progressive loyalty tiers\n\n* Provide first-time bonus multipliers\n\n* Promote frequently used merchant categories\n\n* Introduce personalized reward acceleration\n\n**Strategic Objective:**\nIncrease engagement intensity and move them into Loyal Customer segment.","metadata":{}},{"cell_type":"markdown","source":"### 6. Need Attention\n\n*(Moderate Frequency – Low Monetary – Medium Recency)*\n\n**Behavioral Insight:**\nThese customers show moderate interaction but declining engagement signals.\n\n**Risk Level:** Medium\n\n**Recommended Actions:**\n\n* Send behavior-triggered nudges\n\n* Promote micro-incentives for small transactions\n\n* Encourage recurring category usage\n\n**Strategic Objective:**\nPrevent behavioral downgrade into At Risk segment.","metadata":{}},{"cell_type":"markdown","source":"### 7. About to Sleep\n\n*(Low Frequency – Low Monetary – Increasing Recency)*\n\n**Behavioral Insight:**\nThese customers are becoming inactive. Their revenue contribution is limited but recoverable.\n\n**Risk Level:** Medium to High\n\n**Recommended Actions:**\n\n* Launch reactivation reminder campaigns\n\n* Offer limited-time merchant discounts\n\n* Introduce low-barrier cashback incentives\n\n**Strategic Objective:**\nRe-engage before full inactivity.","metadata":{}},{"cell_type":"markdown","source":"### 8. Hibernating\n\n*(Low Frequency – Low Monetary – Very High Recency)*\n\n**Behavioral Insight:**\nThese customers are almost inactive and contribute minimal revenue.\n\n**Risk Level:** High (but low financial impact)\n\n**Recommended Actions:**\n\n* Use low-cost digital reactivation campaigns\n\n* Avoid expensive incentives\n\n* Focus on automated remarketing\n\n**Strategic Objective:**\nReactivation only if cost-efficient.","metadata":{}},{"cell_type":"markdown","source":"### 9. Promising\n\n*(Low Frequency – Low Monetary – Very Low Recency)*\n\n**Behavioral Insight:**\nRecently active but still low spending.\n\n**Risk Level:** Low\n\n**Recommended Actions:**\n\n* Encourage repeat transactions\n\n* Offer category-based incentives\n\n* Introduce welcome-back multipliers\n\n**Strategic Objective:**\nIncrease transaction depth and build habit formation.","metadata":{}},{"cell_type":"markdown","source":"### 10. New Customers\n\n*(Very Low Frequency – Very Low Monetary – Very Low Recency)*\n\n**Behavioral Insight:**\nNew entrants into the ecosystem. Early behavior formation stage.\n\n**Risk Level:** Moderate (habit not formed yet)\n\n**Recommended Actions:**\n\n* Provide onboarding incentives\n\n* Offer first 3 transaction bonuses\n\n* Introduce merchant discovery campaigns\n\n**Strategic Objective:**\nEstablish long-term card usage behavior.\n\n\n\n### Strategic Summary (Executive Insight)\n\nRevenue is highly concentrated in Champions, Loyal Customers, and Cant Lose segments\n\nCant Lose segment represents the highest revenue-per-customer risk\n\nLong-tail segments (Hibernating, New Customers) contribute minimal revenue and require cost-efficient strategies\n\nRFM segmentation provides a behavioral foundation before transitioning to predictive CLTV modeling\n\n---","metadata":{}},{"cell_type":"markdown","source":"# CLTV\n","metadata":{}},{"cell_type":"markdown","source":"##  Transition from RFM Segmentation to CLTV Prediction\nRFM analysis provides a behavioral snapshot of customer activity based on Recency, Frequency, and Monetary metrics.\nHowever, RFM is descriptive — it explains what happened, not *what will happen*.\n\nTo move from descriptive analytics to predictive analytics, we now transition to Customer Lifetime Value (CLTV) modeling.\n\n### 1.1 Why Move Beyond RFM?\nWhile RFM segmentation helps us:\n\n- Identify high-value segments (Champions, Loyal Customers)\n\n- Detect revenue risk groups (Cant Lose, At Risk)\n\n- Understand behavioral differences across segments\n\n- Analyze revenue concentration and churn signals\n\nIt does not answer:\n\n- How much revenue will each customer generate in the future?\n\n- What is the expected future transaction frequency?\n\n- Which customers justify higher acquisition or retention costs?\n\n- What is the financial impact of churn risk?\n\nTo answer these, we need probabilistic modeling.\n\n\n### 1.2 From RFM to CLTV: Conceptual Flow\n\n| **RFM Stage**      | **CLTV Stage**                          |\n|--------------------|------------------------------------------|\n| Recency            | Probability of being active              |\n| Frequency          | Expected future transaction rate         |\n| Monetary           | Expected average transaction value       |\n| Segment Label      | Individual-level revenue forecast        |\n\nRFM segments group customers behaviorally.  \nCLTV models estimate **future financial value per customer**.\n","metadata":{}},{"cell_type":"markdown","source":"##  CLTV Modeling Framework\n\nTo estimate forward-looking customer value, we implement a two-step probabilistic modeling framework:\n\n1. BG/NBD model to estimate expected future transaction frequency\n\n2. Gamma-Gamma model to estimate expected average monetary value\n\nThese two components are then combined to compute Customer Lifetime Value over a defined time horizon.\n\n### Preparing Customer-Level Summary Data\nProbabilistic lifetime models require customer-level summary statistics rather than raw transaction-level data. Therefore, we aggregate transactions per customer using the same analysis date defined in the RFM stage to ensure methodological consistency.\n\n** Required Variables:**\n\n| **Variable**      | **Description**                          |\n|--------------------|------------------------------------------|\n| Recency            | Time between first and last transaction            |\n| Frequency          | Number of repeat transactions         |\n| T                  | Customer age (time between first transaction and analysis date)      |\n| Monetary      | Average transaction value      |\n\n>> Only customers with repeat transactions (frequency > 0) are included in BG/NBD modeling.","metadata":{}},{"cell_type":"code","source":"print(\"analysis_date:\", analysis_date)\n\nprint(\"transaction df columns:\", df.columns.tolist())   # df senin transaction df'inse\nprint(\"rows:\", df.shape)\n\n# RFM tablon varsa:\nprint(\"rfm shape:\", rfm.shape)\nprint(\"rfm columns:\", rfm.columns.tolist())\nprint(\"rfm index name:\", rfm.index.name)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:21.816210Z","iopub.execute_input":"2026-02-23T14:06:21.816566Z","iopub.status.idle":"2026-02-23T14:06:21.822196Z","shell.execute_reply.started":"2026-02-23T14:06:21.816524Z","shell.execute_reply":"2026-02-23T14:06:21.821315Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"## Model Selection: BG-NBD_and_GammaGamma_with_CLTV_prediction","metadata":{}},{"cell_type":"code","source":"def create_cltv_p_elo(\n    dataframe,\n    analysis_date,\n    month=3,\n    customer_id_col=\"card_id\",\n    date_col=\"purchase_date\",\n    monetary_col=\"purchase_amount_new\",\n    freq=\"W\",\n    discount_rate=0.01,\n    penalizer_coef_bg=0.001,\n    penalizer_coef_gg=0.01,\n    clip_outliers=True,\n    q_low=0.01,\n    q_high=0.99,\n    segment_q=4,\n    segment_labels=(\"D\", \"C\", \"B\", \"A\")\n):\n    \"\"\"\n    Elo transaction-level data üzerinden BG/NBD + Gamma-Gamma ile CLTV tahmini üretir.\n    Çıktı: customer-level cltv table (frequency, recency, T, monetary_value, clv, scaled_clv, cltv_segment, prob_alive)\n\n    Not:\n    - analysis_date: RFM'de kullandığın analysis_date ile aynı olmalı.\n    - freq='W' (hafta) Elo için genelde stabil.\n    \"\"\"\n\n    df = dataframe[[customer_id_col, date_col, monetary_col]].copy()\n    df[date_col] = pd.to_datetime(df[date_col])\n    analysis_date = pd.to_datetime(analysis_date)\n\n    # Monetary pozitif olmalı (Gamma-Gamma şartı)\n    df = df[df[monetary_col] > 0].dropna().copy()\n\n    # Opsiyonel: aşırı uç değerleri kırp (Elo'da bazen stabiliteyi artırır)\n    if clip_outliers:\n        low, high = df[monetary_col].quantile(q_low), df[monetary_col].quantile(q_high)\n        df[monetary_col] = df[monetary_col].clip(lower=low, upper=high)\n\n    # Lifetimes summary: frequency, recency, T, monetary_value\n    # freq=\"W\" => recency & T haftalık birimde çıkar\n    cltv_df = summary_data_from_transaction_data(\n        df,\n        customer_id_col=customer_id_col,\n        datetime_col=date_col,\n        monetary_value_col=monetary_col,\n        observation_period_end=analysis_date,\n        freq=freq\n    )\n\n    # BG/NBD\n    bgf = BetaGeoFitter(penalizer_coef=penalizer_coef_bg)\n    bgf.fit(cltv_df[\"frequency\"], cltv_df[\"recency\"], cltv_df[\"T\"])\n\n    # Alive prob (churn proxy gibi düşünebilirsin)\n    cltv_df[\"prob_alive\"] = bgf.conditional_probability_alive(\n        cltv_df[\"frequency\"], cltv_df[\"recency\"], cltv_df[\"T\"]\n    )\n\n    # Gamma-Gamma (repeat müşteriler daha stabil)\n    cltv_df_gg = cltv_df[cltv_df[\"frequency\"] > 0].copy()\n\n    ggf = GammaGammaFitter(penalizer_coef=penalizer_coef_gg)\n    ggf.fit(cltv_df_gg[\"frequency\"], cltv_df_gg[\"monetary_value\"])\n\n    cltv_df[\"expected_average_profit\"] = 0.0\n    cltv_df.loc[cltv_df[\"frequency\"] > 0, \"expected_average_profit\"] = ggf.conditional_expected_average_profit(\n        cltv_df_gg[\"frequency\"], cltv_df_gg[\"monetary_value\"]\n    )\n\n    # CLTV (lifetimes built-in)\n    # time=month (ay), freq=\"W\" => lifetimes bunu kendi içinde handle eder\n    clv = ggf.customer_lifetime_value(\n        bgf,\n        cltv_df[\"frequency\"],\n        cltv_df[\"recency\"],\n        cltv_df[\"T\"],\n        cltv_df[\"monetary_value\"],\n        time=month,\n        freq=freq,\n        discount_rate=discount_rate\n    )\n\n    cltv_df[\"clv\"] = clv\n\n    # Scale\n    scaler = MinMaxScaler(feature_range=(0, 1))\n    cltv_df[\"scaled_clv\"] = scaler.fit_transform(cltv_df[[\"clv\"]])\n\n    # Segment (scaled_clv üzerinden)\n    cltv_df[\"cltv_segment\"] = pd.qcut(\n        cltv_df[\"scaled_clv\"].rank(method=\"first\"),\n        q=segment_q,\n        labels=list(segment_labels)\n    )\n\n    return cltv_df","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:21.823408Z","iopub.execute_input":"2026-02-23T14:06:21.823760Z","iopub.status.idle":"2026-02-23T14:06:21.846891Z","shell.execute_reply.started":"2026-02-23T14:06:21.823724Z","shell.execute_reply":"2026-02-23T14:06:21.845605Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"cltv_pred = create_cltv_p_elo(\n    dataframe=df,\n    analysis_date=analysis_date,\n    month=3,\n    customer_id_col=\"card_id\",\n    date_col=\"purchase_date\",\n    monetary_col=\"purchase_amount_new\",\n    freq=\"W\",\n    discount_rate=0.01\n)\n\ncltv_pred.head()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:21.878624Z","iopub.status.idle":"2026-02-23T14:06:21.879531Z","shell.execute_reply.started":"2026-02-23T14:06:21.879314Z","shell.execute_reply":"2026-02-23T14:06:21.879358Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"The CLTV prediction results reveal several important behavioral and financial patterns across customers.\n\nFirst, `customers in the A segment`  exhibit both high purchase frequency and very high probability of being alive (nearly 0.99). This indicates that these customers are not only historically active but are also highly likely to continue purchasing in the future. Their expected average profit is strong, leading to significantly higher 3-month CLV values. These customers represent the core revenue-driving group and should be prioritized for retention and value expansion strategies.\n\nA particularly interesting case is the customer with 31 past transactions but extremely low probability alive (nearly 0.006). Despite strong historical activity, the model predicts very limited future contribution, placing this customer in the lowest` CLTV segment (D)`. This highlights a key insight:\n\n>> **High historical frequency does not guarantee future value**.\n\nThe probabilistic survival component of the BG/NBD model adjusts for purchase timing dynamics, capturing customer inactivity risk that static metrics like raw frequency cannot detect.\n\nAdditionally, differences in CLV are not driven solely by frequency. Some customers with moderate frequency but high monetary value per transaction achieve high predicted CLV. This confirms that expected revenue depends on both purchase intensity and transaction value.\n\nOverall, the output demonstrates the advantage of probabilistic CLTV modeling over purely descriptive RFM segmentation. While RFM groups customers based on past behavior, CLTV provides a forward-looking financial expectation that supports strategic CRM decision-making.","metadata":{}},{"cell_type":"code","source":"cltv_pred.to_csv(\"cltv_prediction.csv\", index=True)","metadata":{"trusted":true},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"## RFM vs CLTV Combined Analysis","metadata":{}},{"cell_type":"code","source":"rfm_cltv = rfm.merge(\n    cltv_pred[[\"clv\", \"scaled_clv\", \"cltv_segment\", \"prob_alive\", \"expected_average_profit\"]],\n    left_index=True,\n    right_index=True,\n    how=\"left\"\n)\n\nrfm_cltv.head()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:21.881074Z","iopub.status.idle":"2026-02-23T14:06:21.881480Z","shell.execute_reply.started":"2026-02-23T14:06:21.881259Z","shell.execute_reply":"2026-02-23T14:06:21.881282Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"When I examined the combined RFM and CLTV results, what stood out to me most was how differently past behavior and future value can diverge. RFM segmentation gives a clear picture of historical engagement — who bought frequently, who spent more, and who seemed loyal. However, the CLTV output adds a forward-looking perspective that changes how customer value should be interpreted.\n\nFor instance, customers labeled as `“champions”` in the RFM framework also appear in the highest CLTV segment. Their high purchase frequency and very high probability of being alive indicate not only strong historical engagement but also behavioral stability. These customers are not just valuable in the past — they are expected to continue generating revenue in the near future. This alignment between RFM and CLTV reinforces confidence in their long-term strategic importance.\n\nWhat I found particularly insightful was the case within the `“cant_lose” `segment. Despite having very high historical frequency and strong monetary contribution, the probability of being alive is extremely low. As a result, the predicted CLV is minimal. This clearly demonstrates that high past activity does not necessarily translate into future value. If I had relied only on RFM, I might still consider this customer highly valuable. However, the probabilistic survival component of the BG/NBD model captures behavioral decay over time and reveals the underlying churn risk.\n\nCustomers in the `“need_attention”` segment present another interesting pattern. They generate moderate CLTV values and still show relatively high survival probability. This suggests growth potential rather than immediate churn risk. With the right engagement strategies, they could move into higher value tiers.\n\nOverall, this combined analysis made it clear to me that RFM explains what has happened, while CLTV estimates what is likely to happen. The integration of both approaches provides a more strategic and financially meaningful evaluation of customer value. The discrepancies between certain RFM segments and their predicted CLTV highlight the importance of probabilistic modeling in long-term CRM planning.","metadata":{}},{"cell_type":"code","source":"cltv_pred.groupby(\"cltv_segment\").agg(\n    clv_mean=(\"clv\", \"mean\"),\n    clv_sum=(\"clv\", \"sum\"),\n    n_customers=(\"clv\", \"count\"),\n    prob_alive_mean=(\"prob_alive\", \"mean\")\n).sort_values(\"clv_mean\", ascending=False)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:21.882437Z","iopub.status.idle":"2026-02-23T14:06:21.882816Z","shell.execute_reply.started":"2026-02-23T14:06:21.882636Z","shell.execute_reply":"2026-02-23T14:06:21.882659Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"When I analyzed the CLTV segment summary, what immediately stood out to me was how clearly the model differentiates customer value tiers. Even though each segment contains the same number of customers due to quantile-based segmentation, their financial impact is dramatically different.\n\n`Segment A`:\n\nClearly represents the core value group. The average CLV is significantly higher than the other segments, and the total contribution is overwhelmingly dominant. What reinforces this finding is the very high probability of being alive (around 0.98). This tells me that these customers are not only historically valuable but also highly likely to continue generating revenue. They are stable, active, and strategically critical.\n\n`Segment B`:\n\nStill shows strong survival probability and moderate CLV levels. These customers are engaged and active, but their financial contribution per customer is lower than Segment A. To me, this segment represents growth potential. With the right retention or upsell strategies, many of them could potentially move into the top tier.\n\n`Segment C`:\n\nShows a noticeable decline in both expected value and survival probability. While they are not yet in a critical state, their contribution is clearly weaker. This makes me think of them as a “monitor closely” group — not immediately risky, but vulnerable to churn if engagement drops further.\n\n`Segment D`:\n\nPresents the strongest contrast. The average CLV is extremely low, and the probability of being alive drops dramatically to around 0.31. This indicates a high churn risk. Even if some of these customers were historically active, the model suggests that their future financial contribution will likely be minimal. This really highlights why predictive modeling matters — past value does not guarantee future profitability.\n\nOverall, this analysis confirmed something very important for me: RFM tells me what customers did, but CLTV tells me what they are expected to do. And when I combine both perspectives, I can evaluate customers not only based on past behavior but on future financial sustainability.","metadata":{}},{"cell_type":"code","source":"rfm_cltv.groupby(\"segment\").agg(\n    clv_mean=(\"clv\", \"mean\"),\n    clv_sum=(\"clv\", \"sum\"),\n    n=(\"clv\", \"count\"),\n    prob_alive_mean=(\"prob_alive\", \"mean\")\n).sort_values(\"clv_mean\", ascending=False)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:21.884266Z","iopub.status.idle":"2026-02-23T14:06:21.884599Z","shell.execute_reply.started":"2026-02-23T14:06:21.884461Z","shell.execute_reply":"2026-02-23T14:06:21.884479Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"When I look at the CLTV distribution across the RFM segments, I can clearly see how past behavioral segmentation aligns — and sometimes conflicts — with predicted future value.\n\nAs expected, the `champions segment` stands out immediately. They have the highest average CLV and an extremely high probability of being alive (almost 0.996). This confirms that customers who are recently active, frequent, and high-spending are not only historically strong but also financially sustainable in the future. For me, this validates the strength of the RFM logic when combined with predictive modeling.\n\n`Loyal customers` also show strong CLV and very high survival probability. While their average CLV is lower than champions, they are still highly stable and engaged. This segment feels like a secure and reliable revenue base.\n\nWhat I found particularly interesting is the `potential_loyalists group`. Their probability of being alive is very high (around 0.99), yet their average CLV is significantly lower than champions and loyal customers. This tells me that they are behaviorally active but not yet maximized in value. To me, this segment represents growth opportunity — the right engagement strategy could push many of them upward.\n\nThe `cant_lose segment` is the most striking contrast. Despite having relatively high historical value, their probability of being alive drops dramatically (around 0.38). This creates a gap between past performance and predicted future value. It really shows why relying only on RFM can be misleading — some customers look strong historically but are already close to churn when we evaluate them probabilistically.\n\nSimilarly, `at_risk` and `hibernating segments` show lower CLV values and significantly weaker survival probabilities. These groups represent clear churn risk. Even if some contributed meaningfully in the past, the model suggests their future financial impact will likely decline.\n\nOverall, what I observe here is a layered insight:\nRFM explains behavioral intensity, while CLTV adds a financial sustainability dimension. When I combine them, I’m no longer just labeling customers — I’m understanding which segments truly drive long-term value and which ones only appear valuable because of past activity.\n\nThis combined perspective makes the analysis much more strategic rather than purely descriptive.","metadata":{}},{"cell_type":"code","source":"pd.crosstab(rfm_cltv[\"segment\"], rfm_cltv[\"cltv_segment\"], normalize=\"index\")","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:21.886261Z","iopub.status.idle":"2026-02-23T14:06:21.886653Z","shell.execute_reply.started":"2026-02-23T14:06:21.886443Z","shell.execute_reply":"2026-02-23T14:06:21.886460Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"When I examine the normalized crosstab between RFM segments and CLTV segments, I can clearly see how behavioral segmentation translates into predicted financial value — and where it diverges.\n\nThe most reassuring result is the `champions `segment. Nearly 77% of champions fall into CLTV Segment A. This tells me that customers who are recent, frequent, and high-spending are also strongly predicted to generate future revenue. The alignment here is very strong, which increases my confidence in both the RFM segmentation and the CLTV model.\n\nSimilarly, more than half of the `loyal_customers` are also classified in CLTV Segment A, and a large portion of the remaining customers fall into Segment B. This indicates that loyal customers are financially sustainable and still highly valuable moving forward.\n\nWhat I find interesting is the `potential_loyalists` and `need_attention` groups. These segments are mostly distributed between CLTV B and C. That tells me they are not yet top-tier customers, but they still have meaningful future value. These groups represent growth opportunity rather than churn risk.\n\nThe most striking pattern appears in the `cant_lose`, `at_risk`, and `hibernating` segments. A significant portion of these customers fall into CLTV Segment D. For example, over 65% of hibernating customers are in the lowest CLTV tier. This confirms that customers who appear inactive behaviorally are also predicted to have very low future financial contribution.\n\nHowever, what stands out to me is that the cant_lose segment is distributed across D, C, and B — meaning some historically strong customers are already shifting downward in predicted value. This highlights how predictive modeling captures early decay signals that static RFM scoring alone cannot fully reveal.\n\nOverall, this cross-analysis shows that while RFM and CLTV are strongly aligned for high-value customers, CLTV provides additional depth for identifying future risk and financial sustainability. Combining both perspectives allows me to distinguish between customers who were valuable and those who are expected to remain valuable.","metadata":{}},{"cell_type":"markdown","source":"## Revenue Concentration & Value Distribution","metadata":{}},{"cell_type":"code","source":"total_clv = rfm_cltv[\"clv\"].sum()\n\nsegment_share = (\n    rfm_cltv.groupby(\"cltv_segment\")[\"clv\"]\n    .sum()\n    .sort_values(ascending=False) / total_clv\n)\n\nsegment_share","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:21.887316Z","iopub.status.idle":"2026-02-23T14:06:21.887623Z","shell.execute_reply.started":"2026-02-23T14:06:21.887494Z","shell.execute_reply":"2026-02-23T14:06:21.887510Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"# CLV Distribution Graph\nplt.figure(figsize=(8,5))\nsns.histplot(np.log1p(rfm_cltv[\"clv\"]), bins=50)\nplt.title(\"Log-Scaled CLV Distribution\")\nplt.xlabel(\"Log(CLV)\")\nplt.show()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:21.888787Z","iopub.status.idle":"2026-02-23T14:06:21.889061Z","shell.execute_reply.started":"2026-02-23T14:06:21.888936Z","shell.execute_reply":"2026-02-23T14:06:21.888952Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"When I examine the log-scaled CLV distribution, the first thing I notice is how strongly right-skewed the original CLV values must be. Even after applying a logarithmic transformation, the distribution shows a clear concentration of customers around mid-level CLV values, with a long tail extending toward higher values.\n\nThe sharp spike near zero indicates a substantial group of customers with very low predicted lifetime value. These customers likely belong to high-churn or low-engagement segments. This confirms that a significant portion of the customer base contributes minimal expected future revenue.\n\nAt the same time, the long right tail reflects the presence of a smaller but financially powerful group of customers. These high-CLV customers drive a disproportionate share of total predicted revenue. This structure strongly supports the Pareto principle, where a minority of customers generate the majority of future financial value.\n\nOverall, this distribution reinforces the importance of segmentation. Customer value is not evenly distributed, and treating all customers equally would be strategically inefficient. The log transformation also makes the skewness more visible and confirms that CLV modeling successfully captures heterogeneity in customer financial potential.","metadata":{}},{"cell_type":"markdown","source":"## Survival Probability & Churn Risk Interpretation","metadata":{}},{"cell_type":"code","source":"rfm_cltv.groupby(\"cltv_segment\")[\"prob_alive\"].mean()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:21.890276Z","iopub.status.idle":"2026-02-23T14:06:21.890589Z","shell.execute_reply.started":"2026-02-23T14:06:21.890445Z","shell.execute_reply":"2026-02-23T14:06:21.890460Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"When I analyze the survival probability across CLTV segments, I observe a very clear monotonic pattern. As expected, Segment A customers have the highest probability of being alive (≈ 0.98), while Segment D customers show a dramatically lower survival probability (≈ 0.31).\n\nThis sharp contrast confirms that predicted financial value is strongly aligned with behavioral continuity. High-CLV customers are not only historically valuable but also highly likely to remain active in the future.\n\nWhat stands out most is the magnitude of the drop from Segment B (≈ 0.96) and C (≈ 0.91) to Segment D (≈ 0.31). This indicates that Segment D customers are significantly closer to churn. Their low predicted CLV is not merely a function of lower spending — it is primarily driven by their weak survival probability.\n\nFrom a strategic perspective, this means that churn risk is not evenly distributed across the customer base. The probabilistic model allows me to identify segments where future revenue decay is already embedded in the behavior.","metadata":{}},{"cell_type":"markdown","source":"## RFM vs CLTV Alignment Heatmap","metadata":{}},{"cell_type":"code","source":"cross = pd.crosstab(\n    rfm_cltv[\"segment\"],\n    rfm_cltv[\"cltv_segment\"],\n    normalize=\"index\"\n)\n\nplt.figure(figsize=(8,6))\nsns.heatmap(cross, annot=True, cmap=\"YlGnBu\", fmt=\".2f\")\nplt.title(\"RFM vs CLTV Segment Alignment\")\nplt.show()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:21.891078Z","iopub.status.idle":"2026-02-23T14:06:21.891355Z","shell.execute_reply.started":"2026-02-23T14:06:21.891206Z","shell.execute_reply":"2026-02-23T14:06:21.891221Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"The alignment heatmap between RFM and CLTV segments reveals both consistency and divergence between descriptive and predictive approaches.\n\nFor example, approximately 77% of the “champions” segment fall into CLTV Segment A. This strong alignment validates that customers who are recent, frequent, and high-spending continue to hold strong financial potential.\n\nHowever, discrepancies appear in segments such as “cant_lose” and “at_risk.” A considerable portion of these customers fall into lower CLTV tiers, particularly Segment D. This indicates that historical engagement alone does not guarantee future value. Some customers who once appeared highly valuable are now predicted to generate minimal future revenue.\n\nThis divergence demonstrates the added depth of probabilistic modeling. While RFM captures past intensity, CLTV incorporates survival probability and forward-looking expectations, providing a more financially sustainable perspective.","metadata":{}},{"cell_type":"markdown","source":"## Strategic Customer Action Framework","metadata":{}},{"cell_type":"markdown","source":"|Segment |\tFinancial Value|\tSurvival Risk|\tStrategic Action|\n|--------|------------------|-----------------|------------------------|\n|A\t|Very High|\tVery Low|\tLoyalty retention & premium offers|\n|B\t|High|\tLow\tUpsell & cross-sell| campaigns|\n|C\t|Medium|\tModerate|\tEngagement reinforcement|\n|D\t|Low|\tHigh|\tCost-controlled reactivation|","metadata":{}},{"cell_type":"markdown","source":"Based on the combined behavioral and probabilistic insights, each customer tier requires a differentiated strategy.\n\n**Segment A customers** represent the core financial engine of the business. Their high predicted CLV and strong survival probability justify loyalty-focused retention strategies, premium offerings, and relationship strengthening initiatives.\n\n**Segment B customers** show strong stability but moderate financial contribution. This group presents significant upsell and cross-sell opportunities, as they remain engaged but have not yet reached maximum value potential.\n\n**Segment C customers** exhibit moderate value and moderate risk. Engagement reinforcement campaigns and personalized incentives may prevent them from drifting into lower-value tiers.\n\n**Segment D customers** demonstrate both low predicted value and high churn risk. Any reactivation effort should be cost-controlled and ROI-focused, as aggressive investment may not yield proportional returns.\n\nThis framework ensures that marketing investments are aligned with predicted financial sustainability rather than historical spending alone.","metadata":{}},{"cell_type":"markdown","source":"## Why CLTV Adds Strategic Depth Beyond RFM\nRFM segmentation provides a powerful snapshot of historical behavior, capturing recency, frequency, and monetary intensity. However, it remains inherently descriptive. It explains what has happened but does not quantify what is expected to happen next.\n\nCLTV modeling extends this framework by incorporating survival probability and discounted future cash flow. Through the BG/NBD and Gamma-Gamma models, customer value becomes forward-looking and probabilistic rather than static.\n\nThe divergence observed in certain segments — particularly in “cant_lose” and “at_risk” groups — demonstrates that high historical activity does not necessarily translate into strong future financial contribution. By integrating predictive modeling, this analysis shifts the focus from past performance to long-term sustainability.\n\nTherefore, CLTV adds strategic depth by enabling financially informed decision-making grounded in expected future behavior.\n","metadata":{}},{"cell_type":"markdown","source":"# Executive Summary\nThis project transitions from descriptive segmentation to predictive customer valuation. While RFM analysis identifies behavioral intensity across customer segments, the BG/NBD and Gamma-Gamma framework estimates forward-looking lifetime value by incorporating survival probability and expected monetary contribution.\n\nThe results reveal a highly concentrated revenue structure, where a limited proportion of customers generate a disproportionately large share of predicted financial value. At the same time, significant variation in survival probability highlights the uneven distribution of churn risk.\n\nBy combining behavioral segmentation with probabilistic lifetime modeling, this study provides a financially grounded framework for customer strategy. Rather than treating all customers equally, it enables differentiated investment decisions aligned with long-term value sustainability.","metadata":{}},{"cell_type":"markdown","source":"# Business Impact Simulation","metadata":{}},{"cell_type":"code","source":"segment_financials = rfm_cltv.groupby(\"cltv_segment\").agg(\n    total_clv=(\"clv\", \"sum\"),\n    avg_clv=(\"clv\", \"mean\"),\n    avg_prob_alive=(\"prob_alive\", \"mean\"),\n    n_customers=(\"clv\", \"count\")\n).sort_values(\"total_clv\", ascending=False)\n\nsegment_financials","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:21.891887Z","iopub.status.idle":"2026-02-23T14:06:21.892125Z","shell.execute_reply.started":"2026-02-23T14:06:21.892007Z","shell.execute_reply":"2026-02-23T14:06:21.892021Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"When I analyze the financial distribution across CLTV segments, the concentration of value becomes extremely clear. Segment A alone generates approximately 1.75 million in total predicted lifetime value, which is nearly three times higher than Segment B and significantly larger than Segments C and D. Despite each segment containing the same number of customers, the financial contribution is heavily skewed toward the top tier.\n\nWhat stands out even more is the survival probability. Segment A customers not only generate the highest predicted value, but they also have the strongest probability of remaining active (≈ 0.98). This combination of high value and high stability makes them the most secure revenue drivers in the portfolio.\n\nSegment B, while generating lower average CLV compared to Segment A, still maintains a strong survival probability (≈ 0.96). This suggests that these customers are financially stable but under-monetized relative to their potential. Strategically, this group represents a strong upsell and cross-sell opportunity.\n\nSegment C shows a noticeable decline in both value and survival probability. Although still relatively active (≈ 0.91), their financial impact is moderate. This group may benefit from engagement reinforcement to prevent migration toward lower tiers.\n\nSegment D presents a fundamentally different risk profile. With a very low average CLV and a survival probability of only ≈ 0.31, these customers are significantly closer to churn. Investing heavily in this group may not generate proportional returns unless acquisition costs are minimal.\n\nOverall, this simulation confirms that marketing and retention budgets should not be distributed evenly across the customer base. A value-weighted allocation strategy, prioritizing high-CLV and high-survival segments, would likely maximize long-term financial return.","metadata":{}},{"cell_type":"code","source":"total_clv = segment_financials[\"total_clv\"].sum()\n\nsegment_financials[\"revenue_share_%\"] = (\n    segment_financials[\"total_clv\"] / total_clv * 100\n)\n\nsegment_financials","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2026-02-23T14:06:21.892674Z","iopub.status.idle":"2026-02-23T14:06:21.892952Z","shell.execute_reply.started":"2026-02-23T14:06:21.892819Z","shell.execute_reply":"2026-02-23T14:06:21.892839Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"When I calculate the revenue share across CLTV segments, the concentration of value becomes strikingly clear. \n\n**Segment A** alone generates approximately 63.6% of total predicted lifetime value, despite representing only 25% of the customer base. This confirms a strong Pareto-like structure within the portfolio.\n\n**Segment B** contributes nearly 23% of total predicted value, which still represents a meaningful financial layer. However, there is a sharp drop after Segment A, highlighting how disproportionately revenue is driven by the top tier.\n\n**Segment C** accounts for around 11% of total value, suggesting moderate contribution but limited strategic dominance. Meanwhile, **Segment D** contributes just over 2% of predicted lifetime value while simultaneously exhibiting the highest churn risk. From an investment perspective, this segment offers minimal expected financial return.\n\nWhat this analysis clearly demonstrates is that customer value is highly unevenly distributed. A relatively small portion of customers drives the majority of future revenue. Therefore, a uniform marketing allocation strategy would be inefficient. Instead, capital and retention efforts should be prioritized toward high-value and high-survival segments to maximize long-term financial sustainability.\n\nThis concentration pattern reinforces the strategic importance of predictive CLTV modeling in guiding data-driven customer investment decisions.","metadata":{}},{"cell_type":"markdown","source":"# Model Assumptions & Limitations\nWhile the BG/NBD and Gamma-Gamma framework provides a strong probabilistic foundation for CLTV estimation, it is important to acknowledge its assumptions and limitations.\n\nThe BG/NBD model assumes independence between purchase frequency and dropout probability. In reality, customer behavior may be influenced by external factors such as campaigns, seasonality, or economic conditions, which are not explicitly modeled.\n\nSimilarly, the Gamma-Gamma model assumes that monetary value is independent of purchase frequency. However, in practical scenarios, spending behavior and transaction frequency may be correlated.\n\nAdditionally, the model relies solely on historical transactional data and does not incorporate demographic variables, channel effects, or marketing interventions. Therefore, the predictions should be interpreted as behavior-driven financial estimates rather than complete behavioral representations.\n\nDespite these limitations, the framework offers a structured and forward-looking approach to evaluating customer-level financial sustainability.","metadata":{}},{"cell_type":"markdown","source":"# Future Improvements\nWhile the current BG/NBD and Gamma-Gamma framework provides a strong probabilistic foundation for estimating customer lifetime value, several enhancements could further improve the robustness and strategic depth of the analysis.\n\nFirst, incorporating additional behavioral and demographic features could enrich the model. Variables such as merchant category diversity, transaction volatility, or customer tenure segmentation may provide additional predictive power beyond pure transactional frequency and monetary value.\n\nSecond, integrating seasonality and macroeconomic signals could enhance forecasting accuracy. Customer behavior may fluctuate due to promotional cycles, economic conditions, or market-level shocks, which are not captured in the current framework.\n\nThird, machine learning-based survival models (e.g., Cox Proportional Hazards, Random Survival Forests, or gradient boosting-based churn prediction) could be explored to complement the probabilistic BG/NBD approach. These methods may capture nonlinear behavioral dynamics more effectively.\n\nAdditionally, implementing cohort-based CLTV tracking would allow monitoring value evolution over time, enabling dynamic strategy adjustments rather than static segmentation.\n\nFinally, linking CLTV outputs to real marketing campaign response data would allow full ROI evaluation, transforming predictive valuation into a closed-loop decision optimization framework.\n\nOverall, future improvements would aim to transition from transaction-based prediction toward a fully integrated, behaviorally enriched, and strategy-driven customer valuation system.","metadata":{}}]}