139 const Int_t nrStocks = 10;
 
  140 static const Char_t *stocks[] =
 
  141      {
"GE",
"SUNW",
"QCOM",
"BRCM",
"TYC",
"IBM",
"AMAT",
"C",
"PFE",
"HD"};
 
  154      fDate = fVol = fOpen = fHigh = fLow = fClose = fCloseAdj = 0;
 
  156   virtual ~TStockDaily() {}
 
  158   ClassDef(TStockDaily,1)
 
  162 Double_t RiskProfile(Double_t *x, Double_t *par) {
 
  163   Double_t riskFactor = par[0];
 
  164   return 1-TMath::Exp(-riskFactor*x[0]);
 
  168 TArrayF &StockReturn(TFile *f,
const TString &name,Int_t sDay,Int_t eDay)
 
  170   TTree *tDaily = (TTree*)f->Get(name);
 
  171   TStockDaily *data = 0;
 
  172   tDaily->SetBranchAddress(
"daily",&data);
 
  173   TBranch *b_closeAdj = tDaily->GetBranch(
"fCloseAdj");
 
  174   TBranch *b_date     = tDaily->GetBranch(
"fDate");
 
  177   const Int_t nrEntries = (Int_t)tDaily->GetEntries();
 
  178   TArrayF closeAdj(nrEntries);
 
  179   for (Int_t i = 0; i < nrEntries; i++) {
 
  181     b_closeAdj->GetEntry(i);
 
  182     if (data->fDate >= sDay && data->fDate <= eDay)
 
  183       closeAdj[i] = data->fCloseAdj/100.;
 
  186   TArrayF *r = 
new TArrayF(nrEntries-1);
 
  187   for (Int_t i = 1; i < nrEntries; i++)
 
  189     (*r)[i-1] = closeAdj[i]/closeAdj[i-1];
 
  196 TVectorD OptimalInvest(Double_t riskFactor,TVectorD r,TMatrixDSym Covar)
 
  214   const Int_t nrVar     = nrStocks;
 
  215   const Int_t nrEqual   = 1;
 
  216   const Int_t nrInEqual = 0;
 
  220   TMatrixDSym Q = riskFactor*Covar;
 
  223   TMatrixD A(nrEqual,nrVar); A = 1;
 
  224   TVectorD b(nrEqual); b = 1;
 
  233   TMatrixD C   (nrInEqual,nrVar);
 
  234   TVectorD clo (nrInEqual);
 
  235   TVectorD cup (nrInEqual);
 
  236   TVectorD iclo(nrInEqual);
 
  237   TVectorD icup(nrInEqual);
 
  244   TVectorD xlo (nrVar); xlo  = 0;
 
  245   TVectorD xup (nrVar); xup  = 0;
 
  246   TVectorD ixlo(nrVar); ixlo = 1;
 
  247   TVectorD ixup(nrVar); ixup = 0;
 
  254   TQpProbDens *qp = 
new TQpProbDens(nrVar,nrEqual,nrInEqual);
 
  258   TQpDataDens *prob = (TQpDataDens *)qp->MakeData(c,Q,xlo,ixlo,xup,ixup,A,b,C,clo,iclo,cup,icup);
 
  262   TQpVar      *vars  = qp->MakeVariables(prob);
 
  263   TQpResidual *resid = qp->MakeResiduals(prob);
 
  269   TGondzioSolver *s = 
new TGondzioSolver(qp,prob);
 
  270   const Int_t status = s->Solve(prob,vars,resid);
 
  272   const TVectorD weight = vars->fX;
 
  274   delete qp; 
delete prob; 
delete vars; 
delete resid; 
delete s;
 
  276     cout << 
"Could not solve this problem." <<endl;
 
  277     return TVectorD(nrStocks);
 
  287    const Int_t sDay = 20000809;
 
  288    const Int_t eDay = 20040602;
 
  290    const char *fname = 
"stock.root";
 
  292    if (!gSystem->AccessPathName(fname)) {
 
  293       f = TFile::Open(fname);
 
  294    } 
else if (!gSystem->AccessPathName(Form(
"%s/quadp/%s", TROOT::GetTutorialDir().Data(), fname))) {
 
  295       f = TFile::Open(Form(
"%s/quadp/%s", TROOT::GetTutorialDir().Data(), fname));
 
  297       printf(
"accessing %s file from http://root.cern.ch/files\n",fname);
 
  298       f = TFile::Open(Form(
"http://root.cern.ch/files/%s",fname));
 
  302    TArrayF *data = 
new TArrayF[nrStocks];
 
  303    for (Int_t i = 0; i < nrStocks; i++) {
 
  304       const TString symbol = stocks[i];
 
  305       data[i] = StockReturn(f,symbol,sDay,eDay);
 
  308    const Int_t nrData = data[0].GetSize();
 
  310    TVectorD r(nrStocks);
 
  311    for (Int_t i = 0; i < nrStocks; i++)
 
  312       r[i] = data[i].GetSum()/nrData;
 
  314    TMatrixDSym Covar(nrStocks);
 
  315    for (Int_t i = 0; i < nrStocks; i++) {
 
  316       for (Int_t j = 0; j <= i; j++) {
 
  318          for (Int_t k = 0; k < nrData; k++) {
 
  319             sum += (data[i][k] - r[i]) * (data[j][k] - r[j]);
 
  321          Covar(i,j) = Covar(j,i) = sum/nrData;
 
  325    const TVectorD weight1 = OptimalInvest(2.0,r,Covar);
 
  326    const TVectorD weight2 = OptimalInvest(10.,r,Covar);
 
  328    cout << 
"stock     daily  daily   w1     w2" <<endl;
 
  329    cout << 
"symb      return sdv              " <<endl;
 
  330    for (Int_t i = 0; i < nrStocks; i++)
 
  331       printf(
"%s\t: %.3f  %.3f  %.3f  %.3f\n",stocks[i],r[i],TMath::Sqrt(Covar[i][i]),weight1[i],weight2[i]);
 
  333    TCanvas *c1 = 
new TCanvas(
"c1",
"Portfolio Optimizations",10,10,800,900);
 
  342    TF1 *f1 = 
new TF1(
"f1",RiskProfile,0,2.5,1);
 
  343    f1->SetParameter(0,2.0);
 
  344    f1->SetLineColor(49);
 
  346    f1->GetHistogram()->SetXTitle(
"dollar");
 
  347    f1->GetHistogram()->SetYTitle(
"utility");
 
  348    f1->GetHistogram()->SetMinimum(0.0);
 
  349    f1->GetHistogram()->SetMaximum(1.0);
 
  350    TF1 *f2 = 
new TF1(
"f2",RiskProfile,0,2.5,1);
 
  351    f2->SetParameter(0,10.);
 
  352    f2->SetLineColor(50);
 
  355    TLegend *legend1 = 
new TLegend(0.50,0.65,0.70,0.82);
 
  356    legend1->AddEntry(f1,
"1-exp(-2.0*x)",
"l");
 
  357    legend1->AddEntry(f2,
"1-exp(-10.*x)",
"l");
 
  363    TH1F *h1 = 
new TH1F(
"h1",
"Portfolio Distribution",nrStocks,0,0);
 
  364    TH1F *h2 = 
new TH1F(
"h2",
"Portfolio Distribution",nrStocks,0,0);
 
  366    h1->SetFillColor(49);
 
  367    h2->SetFillColor(50);
 
  368    h1->SetBarWidth(0.45);
 
  369    h1->SetBarOffset(0.1);
 
  370    h2->SetBarWidth(0.4);
 
  371    h2->SetBarOffset(0.55);
 
  372    for (Int_t i = 0; i < nrStocks; i++) {
 
  373       h1->Fill(stocks[i],weight1[i]);
 
  374       h2->Fill(stocks[i],weight2[i]);
 
  377    h1->Draw(
"BAR2 HIST");
 
  378    h2->Draw(
"BAR2SAME HIST");
 
  380    TLegend *legend2 = 
new TLegend(0.50,0.65,0.70,0.82);
 
  381    legend2->AddEntry(h1,
"high risk",
"f");
 
  382    legend2->AddEntry(h2,
"low  risk",
"f");