# To fit a curve to model direct mail marketing responses. How to obtain the % of responses that are likely to occur each day

I'm trying to model the responses from a direct mail marketing campaign so that I can use it to forecast for future campaigns.

I started, in the code below, with the average number of responses by day of a historical campaign (contained in the vector: "responses"). I was then able to fit a 63-day (8-wk) smooth curve to model the data. But I now need a way to use this curve to help me with forecasting. For example, if I think I'll get x number of total responses from a campaign, I need to know when those responses are most likely to happen. In other words, I need the daily "factors" (i.e. the percentage of the total responses that is most likely to respond on each day).

p.s. if anyone has a better way of approaching this I'd love to hear!

#vector of direct mail marketing responses over 63 days
responses <- c(
24.16093706,  41.59607507,  68.20083052,  85.19109064,  100.0704403,  58.6600221,  86.08475816,  88.97439581,  65.58341418,  49.25588053,  53.63602085,  47.03620672,  29.71552264,  32.85862747,  31.29118096,  23.67961069,  19.81261675,  18.69300933,  17.25738435,  12.01161679,  12.36734071,  14.32360673,  11.02390849,  9.108021409,  9.647965622,  8.815576548,  5.67225654,  5.739220185,  6.233999138,  5.527376627,  5.024065761,  5.565266355,  4.626749364,  3.480761716,  4.621902301,  4.518554271,  4.075985188,  3.204946787,  3.174020873,  2.966915873,  2.129178828,  2.673009031,  2.410429043,  2.331287075,  2.509300578,  2.13820695,  2.53433787,  1.603934405,  1.555813592,  1.834605068,  1.842905685,  1.454045577,  2.08684322,  1.318276487,  0.807666643,  1.333167088,  1.004526525,  1.180110123,  1.078079735,  1.151394678,  1.426747942,  0.699119833,  0.583347236)

set.seed(2)
install.packages("MASS")
library("MASS")

shape_and_scale <- fitdistr(responses,'weibull')

#check the shape and scale
shape_and_scale

#plug in the shape and scale
#essentially taking the total number of respondants and for each, doing a random simulation for what day they'll respond- according to a weibull distribution
#rweibull makes it a random generation
#also need to create a variable for the total number of responses
total_responses <- 1121
day_response <- round(rweibull(total_responses,0.70730466,13.79467490)+.5)

day_response

day_response_frequency_table <- as.data.frame(table(round(rweibull(total_responses,0.70730466,13.79467490)+.5)))

day_response_frequency_table
#notice that it extends beyond our 63 day limit for modeling a campaign

#create a factor with levels so that we can limit our distribution to 63 days
day_response_with_levels <- factor(day_response, levels=0:63)
day_response_with_levels
response_frequency <- as.data.frame(table(day_response_with_levels))
response_frequency

#now use dweibull and the curve() function to create a curve
?dweibull
curve(x*dweibull(x,0.70730466,13.79467490),from=0, to=63)

• What are you asking? It's hard to tell because (1) a lot relies on people reading and understanding your code and (2) you write about "projections," a "factor," "forecasting," and "applying" something in vague ways that could mean anything from fitting a curve to predicting future values. Could you edit this post to help readers get a clearer idea of what you need to accomplish?
– whuber
Commented Apr 7, 2015 at 18:46
• @whuber I tried to make my question more clear. Does what I'm looking to do make sense now? Commented Apr 7, 2015 at 19:27
• It is much clearer, thank you. I'm not sure you are aware this is a vast subject: you can find out about many approaches by following our time-series links. Your code is rather curious though: one thinks of a "response" as a count or perhaps a monetary quantity. The values in your responses vector, given up to nine decimal places, obviously are not either one of those! Count responses often will be modeled in subtly different ways than other kinds of responses, so this could be an important detail.
– whuber
Commented Apr 7, 2015 at 19:34
• @whuber ah, I see how that could have been confusing. The responses vector was calculated as an average number of responses on a certain day of a campaign (for example, day 1 usually gets ~24.16 responses on average). Do you have any suggestions given that I've already created the weibul curve? Commented Apr 7, 2015 at 19:46
• @whuber To be clear I deseasonalized or normalized my responses to account for the variations in day-of-the-week, holidays, promotions, etc...is this what you're talking about? So in my case the responses that I averaged were free of daily seasonal variability and just represent the aging of a direct mail campaign. At a high level, I need to forecast responses for future direct mail campaigns. I have data from previous campaigns and just need to know what % should come in day 1, day 2, ... etc. not accounting for seasonality. Then I'll seasonalize the smooth response curve afterward. Commented Apr 8, 2015 at 14:48

The data, responses, that you have can be modeled more generally than a probability distribution. A probability distribution is always normalized to 1 while your data contains more information, it also has a magnitude. I think that a more general type of function would also be better since in that case (if the function stems from good arguments well) the model seems to link closer to a physical interpretation (which is more intuitive) rather than using a phenomenological model

(Note: The Weibull distribution does have a physical interpretation when applied to processes that generate size distributions, e.g. a process that randomly breaks bigger pieces into smaller pieces, but in the case of the application here, the shape of a response impulse in a time series, it has no clear meaning)

### Modelling with simple exponential function.

Your data can be reasonably described by using a series of exponential functions.

$$Y(day)_{response} = 286*e^{-\frac{day}{3}}-269*e^{-\frac{day}{7}}$$

more precise coefficients are 286.254*exp(-0.1536516*day)-268.6887*exp(-0.3326013*day)

For your information the Weibull function in the graph is a = 163.7235 k= 1.4914 l=0.1098 weibull <-a*(time*l)^(k-1)*exp(-(time*l)^k) found by using the nls function

### Physical interpretation

These kind of exponential expressions may be interpreted in terms of a differential equation with two parameters (https://en.wikipedia.org/wiki/Multi-compartment_model). E.g. you can imagine a (auxiliary/not measured) variable $X$ which is the amount of people that do not know about the campaign which slowly decreases once the campaign advances.

$$\dot X = -c_1 X$$

and the variable $Y$ is the amount of people that create a response. Which gets filled up by a fraction $f$ from the people from $X$ that get to know the campaign but decreases because people loose interest:

$$\dot Y = fc_1 X -c_2 Y$$

these have the solution:

$$\begin{bmatrix} Y(t) \\ X(t) \end{bmatrix} = \begin{bmatrix} Y(0)-Q \\ 0 \end{bmatrix} e^{-c_2 t} + \begin{bmatrix} Q \\ X(0) \end{bmatrix} e^{-c_1 t}$$

with $Q = f X(0) \frac{c_1}{c_2-c_1}$.

Note: you may, of course, argue for different models as well based on other (better) ideas about the change of $Y$. E.g. the decay of $X$ is not necessarily exponential as prescribed by the equations here, or other factors than this $X$ as the pool of people that do not know about the advertisement might be included (I just came up with this model after making the exponential fit and as a possible physical explanation).

### Temporal effect

In the above figure I have marked every sixth day of the week in the color red. This is to emphasize that on top of the exponential model there seems to be some weekly pattern. You can see this by the red marked dot being the relatively low point in a weekly (7 day period) pattern that moves around the trend which is the modeled function.

It could be possibly to incorporate this pattern or temporal variation into the model as well (I do not think it is possible with some simple auto correlation and moving average model, although I might be mistaken, and I would model it with some additional correction function on top of the exponential function or by fitting some computational model, ie. solving the differential equations with $c_1$ and $c_2$ being time varying parameters).

You should be more clear about the data for this to work out. For instance is the average done on time sequences that always start on the same day? Or if it is corrected then how is this done. Describe more exactly the data, and make some plots or show some descriptions (possibly it is out of the scope of a Q&A to get to the bottom of this).

### Splitting the data

The analysis would greatly improve when you fit to the individual curves instead of the average. In that way you can see better

1. the validity of the model
2. increase the complexity of the model (currently the degrees of freedom is low since the large amount of data is reduced to only a single time series)
3. obtain information about the variation/distribution of the parameters and the error distribution (which provides more insight than the variation of the output, and this is what you can use to make predictions with estimates for error)
4. and also you might group the data and investigate how the model parameters may be a function of other variables, for instance the type of campaign.