```/*****************************************************************************
* Project: RooFit                                                           *
* Package: RooFitCore                                                       *
* @(#)root/roofitcore:\$Id\$
* Authors:                                                                  *
*   WV, Wouter Verkerke, UC Santa Barbara, verkerke@slac.stanford.edu       *
*   DK, David Kirkby,    UC Irvine,         dkirkby@uci.edu                 *
*                                                                           *
* Copyright (c) 2000-2005, Regents of the University of California          *
*                                                                           *
* Redistribution and use in source and binary forms,                        *
* with or without modification, are permitted according to the terms        *
*****************************************************************************/

//////////////////////////////////////////////////////////////////////////////
//
// RooLinearVar is the most general form of a derived real-valued object that can
// be used by RooRealIntegral to integrate over. The requirements for this are
//
//          - Can be modified directly (i.e. invertible formula)
//          - Jacobian term in integral is constant (but not necessarily 1)
//
// This class implements the most general form that satisfy these requirement
//
//    RLV = (slope)*x + (offset)
//
// X is required to be a RooRealVar to meet the invertibility criterium
// (slope) and (offset) is are RooAbsReals, but may not overlap with x,
// i.e. x may not be a server of (slope) and (offset)
//
// In the context of a dataset, (slope) may not contain any real-valued dependents
// (satisfied constant Jacobian requirement). This check cannot be enforced at
// construction time, but can be performed at run time through the isJacobianOK(depList)
// member function.
//
//

#include "RooFit.h"
#include "Riostream.h"

#include <math.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
#include "TClass.h"
#include "TObjString.h"
#include "TTree.h"
#include "RooLinearVar.h"
#include "RooStreamParser.h"
#include "RooArgSet.h"
#include "RooRealVar.h"
#include "RooNumber.h"
#include "RooBinning.h"
#include "RooMsgService.h"

using namespace std;

ClassImp(RooLinearVar)

//_____________________________________________________________________________
RooLinearVar::RooLinearVar(const char *name, const char *title, RooAbsRealLValue& variable,
const RooAbsReal& slope, const RooAbsReal& offs, const char *unit) :
RooAbsRealLValue(name, title, unit),
_binning(variable.getBinning(),slope.getVal(),offs.getVal()),
_var("var","variable",this,variable,kTRUE,kTRUE),
_slope("slope","slope",this,(RooAbsReal&)slope),
_offset("offset","offset",this,(RooAbsReal&)offs)
{
// Constructor with RooAbsRealLValue variable and RooAbsReal slope and offset

// Slope and offset may not depend on variable
if (slope.dependsOnValue(variable) || offs.dependsOnValue(variable)) {
coutE(InputArguments) << "RooLinearVar::RooLinearVar(" << GetName()
<< "): ERROR, slope(" << slope.GetName() << ") and offset("
<< offs.GetName() << ") may not depend on variable("
<< variable.GetName() << ")" << endl ;
assert(0) ;
}

// Initial plot range and number of bins from dependent variable
//   setPlotRange(variable.getPlotMin()*_slope + _offset,
//                variable.getPlotMax()*_slope + _offset) ;
//   setPlotBins(variable.getPlotBins()) ;

}

//_____________________________________________________________________________
RooLinearVar::RooLinearVar(const RooLinearVar& other, const char* name) :
RooAbsRealLValue(other,name),
_binning(other._binning),
_var("var",this,other._var),
_slope("slope",this,other._slope),
_offset("offset",this,other._offset)
{
// Copy constructor
}

//_____________________________________________________________________________
RooLinearVar::~RooLinearVar()
{
// Destructor

_altBinning.Delete() ;
}

//_____________________________________________________________________________
Double_t RooLinearVar::evaluate() const
{
// Calculate current value of this object

return _offset + _var * _slope ;
}

//_____________________________________________________________________________
void RooLinearVar::setVal(Double_t value)
{
// Assign given value to linear transformation: sets input variable to (value-offset)/slope
// If slope is zerom an error message is printed and no assignment is made

//cout << "RooLinearVar::setVal(" << GetName() << "): new value = " << value << endl ;

// Prevent DIV0 problems
if (_slope == 0.) {
coutE(Eval) << "RooLinearVar::setVal(" << GetName() << "): ERROR: slope is zero, cannot invert relation" << endl ;
return ;
}

// Invert formula 'value = offset + slope*var'
((RooRealVar&)_var.arg()).setVal((value - _offset) / _slope) ;

}

//_____________________________________________________________________________
Bool_t RooLinearVar::isJacobianOK(const RooArgSet& depList) const
{
// Returns true if Jacobian term associated with current
// expression tree is indeed constant.

if (!((RooAbsRealLValue&)_var.arg()).isJacobianOK(depList)) {
return kFALSE ;
}

// Check if jacobian has no real-valued dependents
RooAbsArg* arg ;
TIterator* dIter = depList.createIterator() ;
while ((arg=(RooAbsArg*)dIter->Next())) {
if (arg->IsA()->InheritsFrom(RooAbsReal::Class())) {
if (_slope.arg().dependsOnValue(*arg)) {
// 	cout << "RooLinearVar::isJacobianOK(" << GetName() << ") return kFALSE because slope depends on value of " << arg->GetName() << endl ;
return kFALSE ;
}
}
}
delete dIter ;
//   cout << "RooLinearVar::isJacobianOK(" << GetName() << ") return kTRUE" << endl ;
return kTRUE ;
}

//_____________________________________________________________________________
Double_t RooLinearVar::jacobian() const
{
// Return value of Jacobian associated with the transformation

return _slope*((RooAbsRealLValue&)_var.arg()).jacobian() ;
}

//_____________________________________________________________________________
Bool_t RooLinearVar::readFromStream(istream& /*is*/, Bool_t /*compact*/, Bool_t /*verbose*/)
{
// Read object contents from stream
return kTRUE ;
}

//_____________________________________________________________________________
void RooLinearVar::writeToStream(ostream& os, Bool_t compact) const
{
// Write object contents to stream

if (compact) {
os << getVal() ;
} else {
os << _slope.arg().GetName() << " * " << _var.arg().GetName() << " + " << _offset.arg().GetName() ;
}
}

//_____________________________________________________________________________
RooAbsBinning& RooLinearVar::getBinning(const char* name, Bool_t verbose, Bool_t createOnTheFly)
{
// Retrieve binning of this linear transformation. A RooLinearVar does not have its own
// binnings but uses linearly transformed binnings of teh input variable. If a given
// binning exists on the input variable, it will also exists on this linear transformation
// and a binning adaptor object is created on the fly.

// Normalization binning
if (name==0) {
_binning.updateInput(((RooAbsRealLValue&)_var.arg()).getBinning(),_slope,_offset) ;
return _binning ;
}

// Alternative named range binnings, look for existing translator binning first
RooLinTransBinning* altBinning = (RooLinTransBinning*) _altBinning.FindObject(name) ;
if (altBinning) {
altBinning->updateInput(((RooAbsRealLValue&)_var.arg()).getBinning(name,verbose),_slope,_offset) ;
return *altBinning ;
}

// If binning is not found return default binning, if creation is not requested
if (!_var.arg().hasRange(name) && !createOnTheFly) {
return _binning ;
}

// Create translator binning on the fly
RooAbsBinning& sourceBinning = ((RooAbsRealLValue&)_var.arg()).getBinning(name,verbose) ;
RooLinTransBinning* transBinning = new RooLinTransBinning(sourceBinning,_slope,_offset) ;

return *transBinning ;
}

//_____________________________________________________________________________
const RooAbsBinning& RooLinearVar::getBinning(const char* name, Bool_t verbose, Bool_t createOnTheFly) const
{
// Const version of getBinning()

return const_cast<RooLinearVar*>(this)->getBinning(name,verbose,createOnTheFly) ;
}

//_____________________________________________________________________________
std::list<std::string> RooLinearVar::getBinningNames() const
{
// Get a list of all binning names. An empty name implies the default binning.
// A 0 pointer should be passed to getBinning in this case.
std::list<std::string> binningNames(1, "");

RooFIter iter = _altBinning.fwdIterator();
const RooAbsArg* binning = 0;
while((binning = iter.next())) {
const char* name = binning->GetName();
binningNames.push_back(name);
}

return binningNames;
}

//_____________________________________________________________________________
Bool_t RooLinearVar::hasBinning(const char* name) const
{
// Returns true if binning with given name exists.If a given binning
// exists on the input variable, it will also exists on this linear
// transformation.

return ((RooAbsRealLValue&)_var.arg()).hasBinning(name) ;
}
```
RooLinearVar.cxx:1
RooLinearVar.cxx:2
RooLinearVar.cxx:3
RooLinearVar.cxx:4
RooLinearVar.cxx:5
RooLinearVar.cxx:6
RooLinearVar.cxx:7
RooLinearVar.cxx:8
RooLinearVar.cxx:9
RooLinearVar.cxx:10
RooLinearVar.cxx:11
RooLinearVar.cxx:12
RooLinearVar.cxx:13
RooLinearVar.cxx:14
RooLinearVar.cxx:15
RooLinearVar.cxx:16
RooLinearVar.cxx:17
RooLinearVar.cxx:18
RooLinearVar.cxx:19
RooLinearVar.cxx:20
RooLinearVar.cxx:21
RooLinearVar.cxx:22
RooLinearVar.cxx:23
RooLinearVar.cxx:24
RooLinearVar.cxx:25
RooLinearVar.cxx:26
RooLinearVar.cxx:27
RooLinearVar.cxx:28
RooLinearVar.cxx:29
RooLinearVar.cxx:30
RooLinearVar.cxx:31
RooLinearVar.cxx:32
RooLinearVar.cxx:33
RooLinearVar.cxx:34
RooLinearVar.cxx:35
RooLinearVar.cxx:36
RooLinearVar.cxx:37
RooLinearVar.cxx:38
RooLinearVar.cxx:39
RooLinearVar.cxx:40
RooLinearVar.cxx:41
RooLinearVar.cxx:42
RooLinearVar.cxx:43
RooLinearVar.cxx:44
RooLinearVar.cxx:45
RooLinearVar.cxx:46
RooLinearVar.cxx:47
RooLinearVar.cxx:48
RooLinearVar.cxx:49
RooLinearVar.cxx:50
RooLinearVar.cxx:51
RooLinearVar.cxx:52
RooLinearVar.cxx:53
RooLinearVar.cxx:54
RooLinearVar.cxx:55
RooLinearVar.cxx:56
RooLinearVar.cxx:57
RooLinearVar.cxx:58
RooLinearVar.cxx:59
RooLinearVar.cxx:60
RooLinearVar.cxx:61
RooLinearVar.cxx:62
RooLinearVar.cxx:63
RooLinearVar.cxx:64
RooLinearVar.cxx:65
RooLinearVar.cxx:66
RooLinearVar.cxx:67
RooLinearVar.cxx:68
RooLinearVar.cxx:69
RooLinearVar.cxx:70
RooLinearVar.cxx:71
RooLinearVar.cxx:72
RooLinearVar.cxx:73
RooLinearVar.cxx:74
RooLinearVar.cxx:75
RooLinearVar.cxx:76
RooLinearVar.cxx:77
RooLinearVar.cxx:78
RooLinearVar.cxx:79
RooLinearVar.cxx:80
RooLinearVar.cxx:81
RooLinearVar.cxx:82
RooLinearVar.cxx:83
RooLinearVar.cxx:84
RooLinearVar.cxx:85
RooLinearVar.cxx:86
RooLinearVar.cxx:87
RooLinearVar.cxx:88
RooLinearVar.cxx:89
RooLinearVar.cxx:90
RooLinearVar.cxx:91
RooLinearVar.cxx:92
RooLinearVar.cxx:93
RooLinearVar.cxx:94
RooLinearVar.cxx:95
RooLinearVar.cxx:96
RooLinearVar.cxx:97
RooLinearVar.cxx:98
RooLinearVar.cxx:99
RooLinearVar.cxx:100
RooLinearVar.cxx:101
RooLinearVar.cxx:102
RooLinearVar.cxx:103
RooLinearVar.cxx:104
RooLinearVar.cxx:105
RooLinearVar.cxx:106
RooLinearVar.cxx:107
RooLinearVar.cxx:108
RooLinearVar.cxx:109
RooLinearVar.cxx:110
RooLinearVar.cxx:111
RooLinearVar.cxx:112
RooLinearVar.cxx:113
RooLinearVar.cxx:114
RooLinearVar.cxx:115
RooLinearVar.cxx:116
RooLinearVar.cxx:117
RooLinearVar.cxx:118
RooLinearVar.cxx:119
RooLinearVar.cxx:120
RooLinearVar.cxx:121
RooLinearVar.cxx:122
RooLinearVar.cxx:123
RooLinearVar.cxx:124
RooLinearVar.cxx:125
RooLinearVar.cxx:126
RooLinearVar.cxx:127
RooLinearVar.cxx:128
RooLinearVar.cxx:129
RooLinearVar.cxx:130
RooLinearVar.cxx:131
RooLinearVar.cxx:132
RooLinearVar.cxx:133
RooLinearVar.cxx:134
RooLinearVar.cxx:135
RooLinearVar.cxx:136
RooLinearVar.cxx:137
RooLinearVar.cxx:138
RooLinearVar.cxx:139
RooLinearVar.cxx:140
RooLinearVar.cxx:141
RooLinearVar.cxx:142
RooLinearVar.cxx:143
RooLinearVar.cxx:144
RooLinearVar.cxx:145
RooLinearVar.cxx:146
RooLinearVar.cxx:147
RooLinearVar.cxx:148
RooLinearVar.cxx:149
RooLinearVar.cxx:150
RooLinearVar.cxx:151
RooLinearVar.cxx:152
RooLinearVar.cxx:153
RooLinearVar.cxx:154
RooLinearVar.cxx:155
RooLinearVar.cxx:156
RooLinearVar.cxx:157
RooLinearVar.cxx:158
RooLinearVar.cxx:159
RooLinearVar.cxx:160
RooLinearVar.cxx:161
RooLinearVar.cxx:162
RooLinearVar.cxx:163
RooLinearVar.cxx:164
RooLinearVar.cxx:165
RooLinearVar.cxx:166
RooLinearVar.cxx:167
RooLinearVar.cxx:168
RooLinearVar.cxx:169
RooLinearVar.cxx:170
RooLinearVar.cxx:171
RooLinearVar.cxx:172
RooLinearVar.cxx:173
RooLinearVar.cxx:174
RooLinearVar.cxx:175
RooLinearVar.cxx:176
RooLinearVar.cxx:177
RooLinearVar.cxx:178
RooLinearVar.cxx:179
RooLinearVar.cxx:180
RooLinearVar.cxx:181
RooLinearVar.cxx:182
RooLinearVar.cxx:183
RooLinearVar.cxx:184
RooLinearVar.cxx:185
RooLinearVar.cxx:186
RooLinearVar.cxx:187
RooLinearVar.cxx:188
RooLinearVar.cxx:189
RooLinearVar.cxx:190
RooLinearVar.cxx:191
RooLinearVar.cxx:192
RooLinearVar.cxx:193
RooLinearVar.cxx:194
RooLinearVar.cxx:195
RooLinearVar.cxx:196
RooLinearVar.cxx:197
RooLinearVar.cxx:198
RooLinearVar.cxx:199
RooLinearVar.cxx:200
RooLinearVar.cxx:201
RooLinearVar.cxx:202
RooLinearVar.cxx:203
RooLinearVar.cxx:204
RooLinearVar.cxx:205
RooLinearVar.cxx:206
RooLinearVar.cxx:207
RooLinearVar.cxx:208
RooLinearVar.cxx:209
RooLinearVar.cxx:210
RooLinearVar.cxx:211
RooLinearVar.cxx:212
RooLinearVar.cxx:213
RooLinearVar.cxx:214
RooLinearVar.cxx:215
RooLinearVar.cxx:216
RooLinearVar.cxx:217
RooLinearVar.cxx:218
RooLinearVar.cxx:219
RooLinearVar.cxx:220
RooLinearVar.cxx:221
RooLinearVar.cxx:222
RooLinearVar.cxx:223
RooLinearVar.cxx:224
RooLinearVar.cxx:225
RooLinearVar.cxx:226
RooLinearVar.cxx:227
RooLinearVar.cxx:228
RooLinearVar.cxx:229
RooLinearVar.cxx:230
RooLinearVar.cxx:231
RooLinearVar.cxx:232
RooLinearVar.cxx:233
RooLinearVar.cxx:234
RooLinearVar.cxx:235
RooLinearVar.cxx:236
RooLinearVar.cxx:237
RooLinearVar.cxx:238
RooLinearVar.cxx:239
RooLinearVar.cxx:240
RooLinearVar.cxx:241
RooLinearVar.cxx:242
RooLinearVar.cxx:243
RooLinearVar.cxx:244
RooLinearVar.cxx:245
RooLinearVar.cxx:246
RooLinearVar.cxx:247
RooLinearVar.cxx:248
RooLinearVar.cxx:249
RooLinearVar.cxx:250
RooLinearVar.cxx:251
RooLinearVar.cxx:252
RooLinearVar.cxx:253
RooLinearVar.cxx:254
RooLinearVar.cxx:255
RooLinearVar.cxx:256
RooLinearVar.cxx:257
RooLinearVar.cxx:258
RooLinearVar.cxx:259
RooLinearVar.cxx:260
RooLinearVar.cxx:261
RooLinearVar.cxx:262
RooLinearVar.cxx:263
RooLinearVar.cxx:264
RooLinearVar.cxx:265
RooLinearVar.cxx:266
RooLinearVar.cxx:267
RooLinearVar.cxx:268
RooLinearVar.cxx:269
RooLinearVar.cxx:270
RooLinearVar.cxx:271
RooLinearVar.cxx:272
RooLinearVar.cxx:273
RooLinearVar.cxx:274
RooLinearVar.cxx:275
RooLinearVar.cxx:276
RooLinearVar.cxx:277