DEEPPRICE Procedure
A Demand-Price Example When the Price Is Not Endogenous
This example illustrates how the DEEPPRICE procedure enables you to estimate the parameters of interest and perform policy evaluation and policy comparison when the treatment variable is not endogenous. In this case, the instrumental variable is not needed. This example also demonstrates how you can save the model information and use it later to score other new data.
A simulated data set is generated, based on the following assumptions:
The treatment variable, scaled flight price (denoted by p), is continuous, and its value ranges from 0.01 to 75, inclusive.
The outcome variable, demand (denoted by y), is continuous and nonnegative.
-
There are two covariates:
The customer type (denoted by s), is discrete, and its value ranges from 1 to 10, inclusive.
The time (denoted by t) is continuous, and its value ranges from 0 to 12, exclusive.
The disturbance in the treatment model is independent of the disturbance in the outcome model; this implies that the treatment variable is not endogenous.
The treatment model is given as
where describes the seasonality.
The outcome model is given as
Note that and
are uncorrelated, which implies that the scaled flight price is not endogenous.
The following statements simulate samples that are based on the treatment and outcome models that were just presented:
%macro deepPriceGenerateData(n,rho,seed);
data deepPriceDGP;
call streaminit('pcg', &seed.);
rho = &rho.;
do i = 1 to &n.;
s = floor(rand('Uniform')*10+1);
t = rand('Uniform')*12;
z = rand('Normal',0,1);
eta = rand('Normal',0,1);
psi = 2*((t-6)/12*(t-6)/12*(t-6)/12*(t-6)/12*50/3
+exp(-400*(t-6)/12*(t-6)/12)+t/12-41/20);
eta0 = 5+0.3*psi;
eta1 = 0.1*psi;
if(rho ^= 0) then p = eta0 + eta1*z + eta;
else p = eta0 + eta;
plb = 0.01;
pub = 75;
if(p<plb) then p=plb;
if(p>pub) then p=pub;
eps = rand('Normal',rho*eta,0.25);
alpha = 30 + 0.1*s*psi;
beta = 0.1*s*psi - 0.2;
if(beta>0) then beta=0;
y0 = alpha + beta*p;
y = y0 + eps;
if(y<0) then y = 0;
* the realized revenue;
R = y * p;
R0 = y0 * p;
* the best price to maximize the revenue,
which cannot be obtained without knowing DGP;
if(beta<0) then pstar = -alpha/beta/2;
else pstar = pub;
ystar = alpha + beta * pstar;
* the maximized expected revenue;
Rstar = ystar * pstar;
output;
end;
run;
%mend;
%let n=12500;
%let rho = 0;
%let seed=12346;
%deepPriceGenerateData(&n.,&rho.,&seed.);
The following DATA steps load the first observations of the data set
deepPriceDGP into the data table simPrice_train and the next observations into the data table
simPrice_test in your session that is associated with the mylib libref. The DATA steps assume that your libref is named mylib, but you can substitute any appropriately defined libref.
data mylib.simPrice_train;
set deepPriceDGP(obs=10000 keep=i s t p y R pstar);
run;
data mylib.simPrice_test;
set deepPriceDGP(firstobs=10001 keep=i s t p y R pstar);
run;
The unknown functions ,
, and
are estimated through two DNNs by using the data set
simPrice_train. The parameters of interest are then estimated, and policy evaluation and policy comparison are performed. The following statements use PROC DEEPPRICE to perform these tasks and store the model information and parameter learning results:
proc deepprice data=mylib.simPrice_train;
id i;
tmodel p=s t / dnn=(nodes=(32 32 32 32)
train=(optimizer=(miniBatchSize=2000 regL1=0.001 maxEpochs=2000
algorithm=adam) nthreads=5 seed=12346 recordseed=12346));
model y=s t / dnn=(nodes=(32 32 32 32)
train=(optimizer=(miniBatchSize=2000 regL1=0.001 maxEpochs=4000
algorithm=adam) nthreads=5 seed=12346 recordseed=12346));
infer policy=(pstar) policyComparison=(base=(p) compare=(pstar))
out=mylib.oest outdetails=mylib.odetails;
score outt=mylib.outtdata outa=mylib.outadata outb=mylib.outbdata;
run;
Note that specifying the SEED= and RECORDSEED= option values does not guarantee that you get identical results each time you run the DEEPPRICE procedure in single-machine or distributed computing mode. This is because the execution environment is the combination of the operating environment and the number of threads (single-machine mode) or the number of worker nodes, together with the number of threads that are used for execution on each worker node (distributed computing mode).
The OUTT= option writes the treatment model information to the data table outtdata, the OUTA= option writes the estimation information to the data table
outadata, and the OUTB= option writes the estimation information to the data table
outbdata. The number of observations is shown in Figure 1.
Figure 1: Number of Observations
| Number of Observations | 10000 |
|---|---|
| Observations with Missing Covariates | 0 |
| Observations with Missing Covariates for Treatment Model | 0 |
| Observations with Missing Covariates for Outcome Model | 0 |
| Observations with Missing Outcome | 0 |
| Observations with Missing Treatment | 0 |
The estimates of parameters of interest are shown in Figure 2.
Figure 2: Parameters of Interest
| Parameter Estimates | ||||||
|---|---|---|---|---|---|---|
| Parameter | Estimate | Standard Error | 95% Confidence Limits | Z | Pr > |Z| | |
| Average Intercept | 28.442737 | 0.032558 | 28.378925 | 28.506549 | 873.61 | <.0001 |
| Average Slope | -1.515271 | 0.011544 | -1.537896 | -1.492646 | -131.27 | <.0001 |
The policy evaluation estimates the expected demand of a policy. The policy evaluation results are shown in Figure 3.
Figure 3: Policy Evaluation
| Policy Evaluation | ||||||
|---|---|---|---|---|---|---|
| Policy | Estimate | Standard Error | 95% Confidence Limits | Z | Pr > |Z| | |
| pstar | 14.671826 | 0.107646 | 14.460845 | 14.882808 | 136.30 | <.0001 |
The policy comparison estimates the difference in expected demand of two policies. The policy comparison results are shown in Figure 4.
Figure 4: Policy Comparison
| Policy Comparison | |||||||
|---|---|---|---|---|---|---|---|
| Comparison Policy | Base Policy | Estimate | Standard Error | 95% Confidence Limits | Z | Pr > |Z| | |
| pstar | p | -7.273572 | 0.111963 | -7.493016 | -7.054129 | -64.96 | <.0001 |
According to the comparison of the two policies, the policy p in the observed data generates more demand on average than the policy pstar; however, this does not mean that p generates more revenue than pstar! In fact, in the real world, although pstar is theoretically the best policy to maximize revenue, it cannot be available because it requires the unknown functions and
. Because of the availability of the true data generating process (DGP), the revenue that the optimized policies generate that is suggested by the plug-in estimator and influence-function estimator can be compared to that of the best-in-theory infeasible policy pstar. The following statements compare the actual function values in the true DGP to the estimates of
,
, and
, which are
_that_, _alpha_, and _beta_, respectively, in the oDetails data table in your session; compare the revenues that are generated through different policies; and use PROC MEANS to get the bias and variance of each estimator:
proc sort data=mylib.odetails out=odetails_tmp;
by i;
run;
data odetails;
merge odetails_tmp(in=a) deepPriceDGP(in=b where=(i<=10000));
by i;
diff_eta0 = _that_ - eta0;
diff_alpha = _alpha_-alpha;
diff_beta = _beta_ -beta;
* revenue difference between observed policy and best policy;
diff_R = R0 - Rstar;
* pipstar, the optimized policy suggested by plug-in estimator;
if(_beta_<0) then pipstar = -_alpha_/_beta_/2;
else pipstar = pub;
if(pipstar>pub) then pipstar = pub;
if(pipstar<plb) then pipstar = plb;
piystar = alpha + beta * pipstar;
if(piystar<0) then piystar=0;
piRstar = piystar * pipstar;
* revenue difference between plug-in optimized policy and best policy;
diff_piR = piRstar - Rstar;
* ifpstar, the optimized policy suggested by influence-function
estimator;
if(_if_beta_<0) then ifpstar = -_if_alpha_/_if_beta_/2;
else ifpstar = pub;
if(ifpstar>pub) then ifpstar = pub;
if(ifpstar<plb) then ifpstar = plb;
ifystar = alpha + beta * ifpstar;
if(ifystar<0) then ifystar=0;
ifRstar = ifystar * ifpstar;
* revenue difference between influence-function optimized policy and
best policy;
diff_ifR = ifRstar - Rstar;
run;
proc means data=odetails;
var diff_eta0 diff_alpha diff_beta diff_R diff_ifR diff_piR;
run;
The results are displayed in Figure 5, which shows that all three estimated functions are unbiased.
Figure 5: Summary Statistics of Difference between Actual Value and Estimate
| Variable | N | Mean | Std Dev | Minimum | Maximum | ||||||||||||||||||||||||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|
|
|
|
|
|
You can apply the previously saved treatment model, the estimation information, and the
estimation information to a new data set by specifying the INT=, INA=, and INB= options, respectively, in the SCORE statement. The following statements use the
outtdata, outadata, and outbdata data tables as input data tables and then estimate the parameters of interest and perform the policy evaluation and comparison by using the simPrice_test data table:
proc deepprice data=mylib.simPrice_test;
id i;
infer policy=(pstar) policyComparison=(base=(p) compare=(pstar))
out=mylib.oest2 outdetails=mylib.odetails2;
score int=mylib.outtdata ina=mylib.outadata inb=mylib.outbdata;
run;
When you specify the INT=, INA=, and INB= options in the SCORE statement, you do not need to specify the TMODEL or MODEL statement. The estimates of the parameters of interest and the results of the policy evaluation and policy comparison are shown in Figure 6.
Figure 6: Parameters of Interest, Policy Evaluation, and Policy Comparison
| Parameter Estimates | ||||||
|---|---|---|---|---|---|---|
| Parameter | Estimate | Standard Error | 95% Confidence Limits | Z | Pr > |Z| | |
| Average Intercept | 28.348928 | 0.071672 | 28.208453 | 28.489403 | 395.53 | <.0001 |
| Average Slope | -1.507769 | 0.024143 | -1.555090 | -1.460449 | -62.45 | <.0001 |
| Policy Evaluation | ||||||
|---|---|---|---|---|---|---|
| Policy | Estimate | Standard Error | 95% Confidence Limits | Z | Pr > |Z| | |
| pstar | 14.662468 | 0.166886 | 14.335377 | 14.989560 | 87.86 | <.0001 |
| Policy Comparison | |||||||
|---|---|---|---|---|---|---|---|
| Comparison Policy | Base Policy | Estimate | Standard Error | 95% Confidence Limits | Z | Pr > |Z| | |
| pstar | p | -7.222689 | 0.178589 | -7.572718 | -6.872660 | -40.44 | <.0001 |
For more information about the estimates of parameters of interest, policy evaluation, and policy comparison, see the sections Average Intercept and Slope Parameters and Policy Evaluation and Comparison.