def test_customer_lifetime_value_with_known_values(fitted_bg): """ >>> print fitted_bg <lifetimes.BetaGeoFitter: fitted with 5000 subjects, r: 0.16, alpha: 1.86, a: 1.85, b: 3.18> >>> t = fitted_bg.data.head() >>> t frequency recency T 0 0 0 298 1 0 0 224 2 6 142 292 3 0 0 147 4 2 9 183 >>> print fitted_bg.predict(30, t['frequency'], t['recency'], t['T']) 0 0.016053 1 0.021171 2 0.030461 3 0.031686 4 0.001607 dtype: float64 """ t = fitted_bg.data.head() expected = np.array([0.016053, 0.021171, 0.030461, 0.031686, 0.001607]) # discount_rate=0 means the clv will be the same as the predicted clv_d0 = utils.customer_lifetime_value(fitted_bg, t['frequency'], t['recency'], t['T'], monetary_value=pd.Series([1,1,1,1,1]), time=1, discount_rate=0.) assert_almost_equal(clv_d0.values, expected, decimal=5) # discount_rate=1 means the clv will halve over a period clv_d1 = utils.customer_lifetime_value(fitted_bg, t['frequency'], t['recency'], t['T'], monetary_value=pd.Series([1,1,1,1,1]), time=1, discount_rate=1.) assert_almost_equal(clv_d1.values, expected/2., decimal=5) # time=2, discount_rate=0 means the clv will be twice the initial clv_t2_d0 = utils.customer_lifetime_value(fitted_bg, t['frequency'], t['recency'], t['T'], monetary_value=pd.Series([1,1,1,1,1]), time=2, discount_rate=0) assert_allclose(clv_t2_d0.values, expected*2., rtol=0.1) # time=2, discount_rate=1 means the clv will be twice the initial clv_t2_d1 = utils.customer_lifetime_value(fitted_bg, t['frequency'], t['recency'], t['T'], monetary_value=pd.Series([1,1,1,1,1]), time=2, discount_rate=1.) assert_allclose(clv_t2_d1.values, expected/2. + expected/4., rtol=0.1)
def customer_lifetime_value(self, transaction_prediction_model, frequency, recency, T, monetary_value, time=12, discount_rate=0.01): """ This method computes the average lifetime value for a group of one or more customers. Parameters: transaction_prediction_model: the model to predict future transactions, literature uses pareto/ndb but we can also use a different model like bg frequency: the frequency vector of customers' purchases (denoted x in literature). recency: the recency vector of customers' purchases (denoted t_x in literature). T: the vector of customers' age (time since first purchase) monetary_value: the monetary value vector of customer's purchases (denoted m in literature). time: the lifetime expected for the user in months. Default: 12 discount_rate: the monthly adjusted discount rate. Default: 0.01 Returns: Series object with customer ids as index and the estimated customer lifetime values as values """ # use the Gamma-Gamma estimates for the monetary_values adjusted_monetary_value = self.conditional_expected_average_profit( frequency, monetary_value) return customer_lifetime_value(transaction_prediction_model, frequency, recency, T, adjusted_monetary_value, time, discount_rate)
def test_customer_lifetime_value_with_bgf(self): from collections import OrderedDict ggf = estimation.GammaGammaFitter() ggf.params_ = OrderedDict({'p': 6.25, 'q': 3.74, 'v': 15.44}) bgf = estimation.BetaGeoFitter() bgf.fit(cdnow_customers_with_monetary_value['frequency'], cdnow_customers_with_monetary_value['recency'], cdnow_customers_with_monetary_value['T'], iterative_fitting=3) ggf_clv = ggf.customer_lifetime_value( bgf, cdnow_customers_with_monetary_value['frequency'], cdnow_customers_with_monetary_value['recency'], cdnow_customers_with_monetary_value['T'], cdnow_customers_with_monetary_value['monetary_value']) utils_clv = utils.customer_lifetime_value( bgf, cdnow_customers_with_monetary_value['frequency'], cdnow_customers_with_monetary_value['recency'], cdnow_customers_with_monetary_value['T'], ggf.conditional_expected_average_profit( cdnow_customers_with_monetary_value['frequency'], cdnow_customers_with_monetary_value['monetary_value'])) npt.assert_equal(ggf_clv.values, utils_clv.values)
def test_customer_lifetime_value_with_bgf(self): from collections import OrderedDict ggf = estimation.GammaGammaFitter() ggf.params_ = OrderedDict({'p':6.25, 'q':3.74, 'v':15.44}) bgf = estimation.BetaGeoFitter() bgf.fit(cdnow_customers_with_monetary_value['frequency'], cdnow_customers_with_monetary_value['recency'], cdnow_customers_with_monetary_value['T'], iterative_fitting=3) ggf_clv = ggf.customer_lifetime_value( bgf, cdnow_customers_with_monetary_value['frequency'], cdnow_customers_with_monetary_value['recency'], cdnow_customers_with_monetary_value['T'], cdnow_customers_with_monetary_value['monetary_value'] ) utils_clv = utils.customer_lifetime_value( bgf, cdnow_customers_with_monetary_value['frequency'], cdnow_customers_with_monetary_value['recency'], cdnow_customers_with_monetary_value['T'], ggf.conditional_expected_average_profit(cdnow_customers_with_monetary_value['frequency'],cdnow_customers_with_monetary_value['monetary_value']) ) npt.assert_equal(ggf_clv.values, utils_clv.values)
def customer_lifetime_value(self, transaction_prediction_model, frequency, recency, T, monetary_value, time=12, discount_rate=1): """ This method computes the average lifetime value for a group of one or more customers. transaction_prediction_model: the model to predict future transactions, literature uses pareto/ndb but we can also use a different model like bg frequency: the frequency vector of customers' purchases (denoted x in literature). recency: the recency vector of customers' purchases (denoted t_x in literature). T: the vector of customers' age (time since first purchase) monetary_value: the monetary value vector of customer's purchases (denoted m in literature). time: the lifetime expected for the user in months. Default: 12 discount_rate: the monthly adjusted discount rate. Default: 1 Returns: Series object with customer ids as index and the estimated customer lifetime values as values """ adjusted_monetary_value = self.conditional_expected_average_profit(frequency, monetary_value) # use the Gamma-Gamma estimates for the monetary_values return customer_lifetime_value(transaction_prediction_model, frequency, recency, T, adjusted_monetary_value, time, discount_rate)