Added event cut set for MC
[u/mrichter/AliRoot.git] / PWGLF / RESONANCES / AliRsnExpression.cxx
1 //
2 // AliRsnExpresion class is used to
3 // handle operators &|!
4 // in AliRsnCut
5 //
6 // authors: Martin Vala (martin.vala@cern.ch)
7 //          Alberto Pulvirenti (alberto.pulvirenti@ct.infn.it)
8 //
9
10 #include <TString.h>
11 #include <TObjString.h>
12 #include <TObjArray.h>
13
14 #include "AliLog.h"
15
16 #include "AliRsnVariableExpression.h"
17 #include "AliRsnExpression.h"
18
19 ClassImp(AliRsnExpression)
20
21 AliRsnCutSet *AliRsnExpression::fgCutSet = 0;
22
23 //______________________________________________________________________________
24 AliRsnExpression::AliRsnExpression(TString exp) :
25    TObject(),
26    fVname(""),
27    fArg1(0x0),
28    fArg2(0x0),
29    fOperator(0)
30 {
31    // Default constructor
32    TObjArray *tokens = Tokenize(exp);
33
34    Int_t i = -1;
35    AliRsnExpression *e = Expression(*tokens, i);
36    // Copy !!!
37    fArg1 = e->fArg1; e->fArg1 = 0;
38    fArg2 = e->fArg2; e->fArg2 = 0;
39    fOperator = e->fOperator;
40    fVname = e->fVname;
41    delete e;
42    delete tokens;
43 }
44
45 //______________________________________________________________________________
46 AliRsnExpression::~AliRsnExpression()
47 {
48    if (fArg1) delete fArg1;
49    if (fArg2) delete fArg2;
50 }
51
52 AliRsnExpression::AliRsnExpression(const AliRsnExpression &exp) : TObject(exp),
53    fVname(exp.fVname),
54    fArg1(exp.fArg1),
55    fArg2(exp.fArg2),
56    fOperator(exp.fOperator)
57 {}
58
59 //______________________________________________________________________________
60 AliRsnExpression &AliRsnExpression::operator= (const AliRsnExpression &e)
61 {
62    // AliRsnExpression assignment operator.
63
64    if (this != &e) {
65       TObject::operator= (e);
66       fArg1 = e.fArg1;
67       fArg2 = e.fArg2;
68       fOperator = e.fOperator;
69       fVname = e.fVname;
70    }
71    return *this;
72 }
73
74 //______________________________________________________________________________
75 AliRsnExpression::AliRsnExpression(int op, AliRsnExpression *a, AliRsnExpression *b) :
76    TObject(),
77    fVname(""),
78    fArg1(a),
79    fArg2(b),
80    fOperator(op)
81 {
82    // Create a new expression
83 }
84
85 //______________________________________________________________________________
86 AliRsnExpression::AliRsnExpression(int op, AliRsnExpression *a) :
87    TObject(),
88    fVname(""),
89    fArg1(0),
90    fArg2(a),
91    fOperator(op)
92 {
93    // Create a unary expression.
94 }
95
96 //______________________________________________________________________________
97 Bool_t AliRsnExpression::Value(TObjArray &vars)
98 {
99    //  Evaluate the expression
100    if (fArg2 == 0 && fVname.IsNull()) {
101       AliError("Expression undefined.");
102       return kFALSE;
103    }
104    //if (fArg2 == 0) {
105    //   AliError("Needed second parameter");
106    //   return kFALSE;
107    //}
108
109 //   AliDebug(AliLog::kDebug,Form("fOperator %d",fOperator));
110
111    switch (fOperator) {
112
113       case kOpOR :
114          return fArg1->Value(vars) || fArg2->Value(vars);
115
116       case kOpAND :
117          return fArg1->Value(vars) && fArg2->Value(vars);
118
119       case kOpNOT :
120          return !(fArg2->Value(vars));
121
122       case 0 : {
123 //       Int_t indexx = fgCutSet->GetIndexByCutName ( fVname.Data() );
124          AliDebug(AliLog::kDebug, Form("Vname %s", fVname.Data()));
125 //       return fgCutSet->GetBoolValue ( indexx );
126          return fgCutSet->GetBoolValue(fVname.Atoi());
127       }
128
129       default:
130          AliError("Illegal operator in expression!");
131
132    }
133    return kFALSE;
134 }
135
136
137 //______________________________________________________________________________
138 TString AliRsnExpression::Unparse() const
139 {
140    // Unparse the expression
141
142    TString opVals[4] = { "", "&", "|", "!" };
143    if (fArg2 == 0 && fVname.IsNull()) {
144       AliError("Expression undefined.");
145       return "Error";
146    }
147
148    if (fArg2 == 0 && !fVname.IsNull()) return fVname;
149
150    if (fArg1 == 0 && fArg2) {
151       return opVals[fOperator] + fArg2->Unparse();
152    }
153    return "(" + fArg1->Unparse() + " " + opVals[fOperator] + " " + fArg2->Unparse() + ")";
154 }
155
156 //______________________________________________________________________________
157 TObjArray *AliRsnExpression::Tokenize(TString str) const
158 {
159    // tokenize the expression
160
161    // Remove spaces
162    TString str1;
163    for (Int_t i = 0; i < str.Length(); i++) {
164       if (str[i] == ' ') continue;
165       str1.Append(str[i]);
166    }
167    // get variable tokens
168    TObjArray *valtok = str1.Tokenize("!&|()");
169    // put all variables together
170    Int_t nvt = valtok->GetEntriesFast();
171    TString sumval;
172    for (Int_t i = 0; i < nvt; i++) {
173       TObjString *val = (TObjString *) valtok->At(i);
174       sumval.Append(val->String());
175    }
176    // get the operator tokens
177    TObjArray *optok = str1.Tokenize(sumval.Data());
178    // put all operator in one string
179    TString operators;
180    Int_t nopt = optok->GetEntriesFast();
181    for (Int_t i = 0; i < nopt; i++) {
182       TObjString *val1 = (TObjString *) optok->At(i);
183       operators.Append(val1->String());
184    }
185    // add more room to be safe
186    TObjString *blank = new TObjString(" ");
187    operators.Append(" ");
188    valtok->AddLast(blank);
189    // Now put var. and oper. together
190    TObjArray *tokens = new TObjArray(valtok->GetEntriesFast() + operators.Length());
191    int io = 0, iv = 0;
192    int index = 0;
193    while (1) {
194       TString so = operators[io];
195       int indexO = str1.Index(so, index);
196       TString val2 = ((TObjString *) valtok->At(iv))->String();
197       int indexV = str1.Index(val2, index);
198       if ((indexO < indexV || indexV < 0) && indexO >= 0) {
199          tokens->AddLast(new TObjString(so));
200          index += so.Length();
201          io++;
202       }
203       if ((indexV < indexO || indexO < 0) && indexV >= 0) {
204          tokens->AddLast(new TObjString(val2));
205          index += val2.Length();
206          iv++;
207       }
208       if (index >= str1.Length()) break;
209    }
210
211 // //  Debug -> Print the tokens
212 //   Int_t nt = tokens->GetEntriesFast();
213 //   for ( Int_t i=0; i<nt; i++ )
214 //   {
215 //     TObjString* val3 = ( TObjString* ) tokens->At ( i );
216 //     AliInfo ( Form ( "%d %s",i,val3->String().Data() ) );
217 //   }
218 //
219 //
220    delete valtok;
221    delete optok;
222
223    return tokens;
224 }
225
226
227 //______________________________________________________________________________
228 AliRsnExpression *AliRsnExpression::Element(TObjArray &st, Int_t &i)
229 {
230    // create an element
231
232    AliRsnExpression *result = 0;
233
234    Int_t nt = st.GetEntriesFast();
235    TString token = "@";
236    TObjString *valt;
237    // next token
238    if (i < nt - 1) {
239       i++;
240       valt = (TObjString *) st.At(i);
241       token = valt->String();
242    }
243    // token type
244    char ttok = (token[0] != '|' && token[0] != '&' &&
245                 token[0] != '!' && token[0] != '(' && token[0] != ')') ? 'w' : token[0];
246    switch (ttok) {
247       case 'w' : {
248          result = new AliRsnVariableExpression(token);
249          break;
250       }
251       case '(' :
252          result = Expression(st, i);
253          // next token
254          if (i < nt - 1) {
255             i++;
256             valt = (TObjString *) st.At(i);
257             token = valt->String();
258          }
259          if (token[0] != ')') {
260             //       i--; // push back
261             AliErrorGeneral("AliRsnExpression::Element", "Mismatched parenthesis.");
262             delete result;
263             result = new AliRsnExpression;
264          }
265          break;
266       default:
267          i--; // push back
268          AliErrorGeneral("AliRsnExpression::Element", Form("Unexpected symbol on input. %s", token.Data()));
269          //if (result) delete result;
270          result = new AliRsnExpression;
271    }
272    return result;
273 }
274
275 //______________________________________________________________________________
276 AliRsnExpression *AliRsnExpression::Primary(TObjArray &st, Int_t &i)
277 {
278    // create a primary
279
280    Int_t nt = st.GetEntriesFast();
281    TString token = "@";
282    TObjString *valt;
283    // next token
284    if (i < nt - 1) {
285       i++;
286       valt = (TObjString *) st.At(i);
287       token = valt->String();
288    }
289
290    switch (token[0]) {
291       case '!' :
292          return new AliRsnExpression(kOpNOT, Primary(st, i));
293       default:
294          i--; // push back
295          return Element(st, i);
296    }
297 }
298
299 //______________________________________________________________________________
300 AliRsnExpression *AliRsnExpression::Expression(TObjArray &st, Int_t &i)
301 {
302    // create an expression
303
304    AliRsnExpression *result = 0;
305    Bool_t done = kFALSE;
306    TString token;
307    TObjString *valt;
308
309    static int stack = 0;
310    stack++;
311    Int_t nt = st.GetEntriesFast();
312
313    result = Primary(st, i);
314 //   cout <<"i "<<i<< "Primary " << result->Unparse() << endl;
315    while (! done) {
316       // next token
317       if (i < nt - 1) i++;
318       else break;
319       valt = (TObjString *) st.At(i);
320       token = valt->String();
321       switch (token[0]) {
322          case '&' :
323             result = new AliRsnExpression(kOpAND, result, Primary(st, i));
324 //   cout <<"i "<<i<< " Expression AND " << result->Unparse() << endl;
325             break;
326          case '|' :
327             result = new AliRsnExpression(kOpOR, result, Primary(st, i));
328 //   cout <<"i "<<i<< " Expression OR " << result->Unparse() << endl;
329             break;
330          default:
331             done = kTRUE;
332             i--; // push back
333             break;
334       }
335    }
336    stack--;
337    if (stack == 0 && !token.IsNull() && token[0] == ')') {
338       AliErrorGeneral("AliRsnExpression::Expression", "To many closing parenthesis.");
339       delete result;
340       result = new AliRsnExpression;
341    } else if (stack == 0 && i < nt - 1) {
342       AliErrorGeneral("AliRsnExpression::Expression", Form("Unexpected symbol on input. %s", token.Data()));
343       delete result;
344       result = new AliRsnExpression;
345    }
346    return result;
347 }