Slice in plotOn() picking only the last category

Hi there,

I have a 2D simultaneous extended PDF and I am trying to plot a 1D projection of each slice, along with the data slice that it was successfully fitted to. I’ve tried to adapt the rf501 tutorial (see some sections of my code below) however something strange is happening. The data is plotted correctly onto each frame, but the “LL” PDF is plotted onto both frames with the normalisation for the LL data. The INFO messages for the plotting definitely show that the LL is used for both plots

Interestingly, if I reverse the order that the types are defined in the RooCategory, then the DD PDF is plotted in both cases. So it seems that the last entered type in the category is being used.

Does anyone know what could be happening here?
Dave

......

    // Setup a splitting typeKs for the LL and DD datasets
    RooCategory typeKs("KS","KS type");
    typeKs.defineType("DD");
    typeKs.defineType("LL");

    wspace_Fit.import(typeKs);

    // Create a combined dataset of both KS types with the category as an index
    RooDataSet* data_LL = dynamic_cast<RooDataSet*>(wspace_Fit.data( "LL_Data" ) );
    data_LL->Print();
    RooDataSet* data_DD = dynamic_cast<RooDataSet*>(wspace_Fit.data( "DD_Data" ) );
    data_DD->Print();
    RooDataSet combData( "combData","combined data", obs, Index(typeKs), Import("DD",*data_DD), Import("LL",*data_LL), CutRange("fit") );
    combData.Print();

    // Begin the process of building a simultanous fit from the default pdfs
    RooSimWSTool wst(wspace_Fit);
    RooSimultaneous* sim = wst.build("sim","model",SplitParam("sigma_B,Yield","KS"));

    RooFitResult* result = sim->fitTo( combData, Optimize(0), Save(kTRUE), Optimize(0), Extended(kTRUE), Range("fit") );

    // Do some plotting
    Int_t nBins = 50;

    // Make a frame for the LL sample
    RooPlot* frameLL = Bmass->frame( Bins(nBins), Range("fit"), Title("LL sample") );
    // Plot all data tagged as LL
    combData.plotOn( frameLL, Cut("KS==KS::LL") ) ;
    sim->plotOn( frameLL, Slice(typeKs,"LL"), ProjWData(typeKs,combData), Range("fit"), NormRange("fit"), ProjectionRange("fit") );

    // Make a frame for the DD sample
    RooPlot* frameDD = Bmass->frame( Bins(nBins), Range("fit"), Title("DD sample") );
    // Plot all data tagged as DD
    combData.plotOn( frameDD, Cut("KS==KS::DD") );
    sim->plotOn( frameDD, Slice(typeKs,"DD"), ProjWData(typeKs,combData), Range("fit"), NormRange("fit"), ProjectionRange("fit") );

.....

I’ve done some checking and this error still seems to be there when using versions 5.32.00 and 5.34.05.

I’ve also found an topic on this forum from 2011 [url]Wrong PDF projection when using plotOn with RooSimultaneous which seems to be about the same problem but when using either the RooSimPDFBuilder or the RooSimWSTool that I used. So it looks like either I’m making the same mistake, or somehow the plotOn() function doesn’t work correctly when called on simultaneous PDFs created by these tools. I’ve confirmed that the simultaneous PDF and the subsequent PDFs and parameters are definitely in the RooWorkspace before fitting/plotting.

Hi Dave,

I’m having the same error as you. I’ve built a RooSimultaneous pdf using RooSimWSTool, and when I try to plot slices of the pdf I always get the last state/slice*. I tried to fix this by adding superfluous RooCategory::setIndex commands, but to no avail. I’m including my code, which is structurally very similar to yours, and the output I get.

Have you had any luck with this problem?


// Above this, the code defines a RooAddPdf named "model"
// and a RooCategory* named "cat"

  RooWorkspace space ("workspace","workspace");
  space.import(*cat);
  space.import(model);
  RooSimWSTool wst(space);
  // variable list replaced with ... for brevity
  RooSimultaneous* sim_model = wst.build("sim_model","model",SplitParam("...","cat"));

  sim_model->fitTo(data,Strategy(2),Verbose(false),PrintLevel(-1));

  const char title_total[60] = "Resolution in all bins w/ simultaneous fit";
  RooPlot* frame_total = error->frame(Title(title_total));
  data.plotOn(frame_total);
  sim_model->plotOn(frame_total,ProjWData(*cat,data));

  // num_bins is the number of bins in the RooCategory cat
  RooPlot* bin_frames[num_bins];
  for (int i = 0; i < num_bins; i++) {
    cat->setIndex(i);
    char title[50]; sprintf(title,"Resolution in bin %d",i);
    bin_frames[i] = error->frame(Title(title));
    char cut[50]; sprintf(cut,"cat==cat::%d",i);
    data.plotOn(bin_frames[i],Cut(cut));
    char comp1[5]; sprintf(comp1,"g1_%d",i);
    char comp2[5]; sprintf(comp2,"g2_%d",i);
    char comp3[5]; sprintf(comp3,"g3_%d",i);
    char bin[2]; sprintf(bin,"%d",i);
    sim_model->plotOn(bin_frames[i],ProjWData(*cat,data),Slice(*cat,bin));
    sim_model->plotOn(bin_frames[i],ProjWData(*cat,data),Slice(*cat,bin),
Components(comp1),LineColor(kRed),LineStyle(kDashed));
    sim_model->plotOn(bin_frames[i],ProjWData(*cat,data),Slice(*cat,bin),
Components(comp2),LineColor(kGreen),LineStyle(kDashed));
    sim_model->plotOn(bin_frames[i],ProjWData(*cat,data),Slice(*cat,bin),
Components(comp3),LineColor(kCyan),LineStyle(kDashed));
  }

Output:


  • which is numbered 4 out of 0-5, but this is because I created the RooCategory using a RooThresholdCategory with 5 as the default bin, making the ordering 5,0,1,2,3,4.

I also tried replacing RooSimWSTool with RooSimPDFBuilder. Now it’s another slice that gets plotted each time …

// This replaces the RoomSimWSTool part
  RooSimPdfBuilder rspb(model);
  RooArgSet* config = rspb.createProtoBuildConfig();
  config->setStringValue("physModels","model");
  config->setStringValue("splitCats","mm2cat");
  config->setStringValue("model", "cat : mean "
                                  "cat : sigma "
                                  ...);
  RooSimultaneous* sim_model = rspb.buildPdf(*config,&data);


Hi again,

I think I solved this, using RooSimPDFBuilder. I replaced the line

RooSimultaneous* model = rspb.build(*config,&data);
RooArgSet deps(*error,*cat);
RooSimultaneous* model = rspb.build(*config,deps);

Now, the output looks like this:


Plotting the components isn’t working yet, but that should be easier to fix now.

On an unrelated note, ProjWData doesn’t seem to do anything. I replaced

ProjWData(*cat,data)

everywhere with

ProjWData(RooArgSet(),data)

and the output is unchanged. Removing ProjWData completely, on the other hand, effectively makes the normalization of the pdf null (it doesn’t show up at all). Consequently, I have absolutely no idea what purpose ProjWData is serving.

Hi Jack, the solution you found is indeed the only one I tested that works. Thanks!!
I managed to make the plot split by multiple categories as well.

There is only a typo in your line, the correct one is

RooSimultaneous* model = rspb.buildPdf(*config,deps); (the “build” method doesn’t exist in the version of RooFit 3.60 I am using)