1 /**************************************************************************
2 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
4 * Author: The ALICE Off-line Project. *
5 * Contributors are mentioned in the code where appropriate. *
7 * Permission to use, copy, modify and distribute this software and its *
8 * documentation strictly for non-commercial purposes is hereby granted *
9 * without fee, provided that the above copyright notice appears in all *
10 * copies and that both the copyright notice and this permission notice *
11 * appear in the supporting documentation. The authors make no claims *
12 * about the suitability of this software for any purpose. It is *
13 * provided "as is" without express or implied warranty. *
14 **************************************************************************/
18 ///////////////////////////////////////////////////////////////////////////////
20 // AliExpression Class // //
22 // Helper class to evaluate the condition expressions in //
23 // AliTriggerCondition //
24 // Implements a simple recursive-descent parser //
26 ///////////////////////////////////////////////////////////////////////////////
28 //#include <Riostream.h>
30 #include <TObjString.h>
31 #include <TObjArray.h>
34 #include "AliExpression.h"
35 #include "AliTriggerInput.h"
37 ClassImp( AliExpression )
39 //______________________________________________________________________________
40 AliExpression::AliExpression( TString exp )
42 // Default constructor
43 TObjArray* tokens = Tokenize( exp );
46 AliExpression* e = Expression( *tokens, i );
48 fArg1 = e->fArg1; e->fArg1 = 0;
49 fArg2 = e->fArg2; e->fArg2 = 0;
50 fOperator = e->fOperator;
55 //______________________________________________________________________________
56 AliExpression::~AliExpression()
58 if( fArg1 ) delete fArg1;
59 if( fArg2 ) delete fArg2;
62 //______________________________________________________________________________
63 AliExpression& AliExpression::operator=(const AliExpression& e)
65 // AliExpression assignment operator.
68 TObject::operator=(e);
71 fOperator = e.fOperator;
76 //______________________________________________________________________________
77 AliExpression::AliExpression( int op, AliExpression* a, AliExpression* b )
79 // Create a new expression
85 //______________________________________________________________________________
86 AliExpression::AliExpression( int op, AliExpression* a )
88 // Create a unary expression.
94 //______________________________________________________________________________
95 Bool_t AliExpression::Value( TObjArray &vars )
97 // Evaluate the expression
99 AliError( "Expression undefined." );
106 return fArg1->Value(vars) || fArg2->Value(vars);
109 return fArg1->Value(vars) && fArg2->Value(vars);
112 return !(fArg2->Value(vars));
115 AliError( "Illegal operator in expression!");
122 //______________________________________________________________________________
123 TString AliExpression::Unparse() const
125 // Unparse the expression
127 TString opVals[4] = { "&", "|","!" };
129 AliError( "Expression undefined." );
133 if (fArg1 == 0 && fArg2) {
134 return opVals[fOperator]+fArg2->Unparse();
136 return "("+fArg1->Unparse()+" "+opVals[fOperator]+" "+fArg2->Unparse()+")";
139 //______________________________________________________________________________
140 TObjArray* AliExpression::Tokenize( TString str ) const
142 // tokenize the expression
146 for( Int_t i=0; i<str.Length(); i++ ) {
147 if( str[i] == ' ' ) continue;
148 str1.Append( str[i] );
150 // get variable tokens
151 TObjArray* valtok = str1.Tokenize( "!&|()" );
152 // put all variables together
153 Int_t nvt = valtok->GetEntriesFast();
155 for( Int_t i=0; i<nvt; i++ ) {
156 TObjString* val = (TObjString*)valtok->At( i );
157 sumval.Append( val->String() );
159 // get the operator tokens
160 TObjArray* optok = str1.Tokenize( sumval.Data() );
161 // put all operator in one string
163 Int_t nopt = optok->GetEntriesFast();
164 for( Int_t i=0; i<nopt; i++ ) {
165 TObjString* val1 = (TObjString*)optok->At( i );
166 operators.Append( val1->String() );
168 // add more room to be safe
169 TObjString* blank = new TObjString(" ");
170 operators.Append( " " );
171 valtok->AddLast( blank );
172 // Now put var. and oper. together
173 TObjArray* tokens = new TObjArray( valtok->GetEntriesFast() + operators.Length() );
177 TString so = operators[io];
178 int indexO = str1.Index( so, index );
179 TString val2 = ((TObjString*)valtok->At( iv ))->String();
180 int indexV = str1.Index( val2, index );
181 if( (indexO < indexV || indexV < 0) && indexO >=0 ) {
182 tokens->AddLast( new TObjString( so ) );
183 index += so.Length();
186 if( (indexV < indexO || indexO < 0) && indexV >=0 ) {
187 tokens->AddLast( new TObjString( val2 ) );
188 index += val2.Length();
191 if( index >= str1.Length() ) break;
194 // Debug -> Print the tokens
195 // Int_t nt = tokens->GetEntriesFast();
196 // for( Int_t i=0; i<nt; i++ ) {
197 // TObjString* val3 = (TObjString*)tokens->At( i );
198 // cout << i << " " << val3->String() << endl;
207 //______________________________________________________________________________
208 AliExpression* AliExpression::Element( TObjArray &st, Int_t &i )
212 AliExpression* result = 0;
214 Int_t nt = st.GetEntriesFast();
220 valt = (TObjString*)st.At( i );
221 token = valt->String();
224 char ttok = ( token[0]!='|' && token[0]!='&' &&
225 token[0]!='!' && token[0]!='('&& token[0]!=')') ? 'w' : token[0];
228 result = new AliVariableExpression( token );
231 result = Expression(st, i);
235 valt = (TObjString*)st.At( i );
236 token = valt->String();
238 if( token[0] != ')' ) {
240 AliErrorGeneral( "AliExpression::Element", "Mismatched parenthesis." );
242 result = new AliExpression;
247 AliErrorGeneral( "AliExpression::Element", Form("Unexpected symbol on input. %s", token.Data()) );
248 if( result ) delete result;
249 result = new AliExpression;
254 //______________________________________________________________________________
255 AliExpression* AliExpression::Primary( TObjArray &st, Int_t &i )
259 Int_t nt = st.GetEntriesFast();
265 valt = (TObjString*)st.At( i );
266 token = valt->String();
271 return new AliExpression( kOpNOT, Primary( st, i ) );
274 return Element( st, i );
278 //______________________________________________________________________________
279 AliExpression* AliExpression::Expression( TObjArray &st,Int_t &i )
281 // create an expression
283 AliExpression* result = 0;
284 Bool_t done = kFALSE;
288 static int stack = 0;
290 Int_t nt = st.GetEntriesFast();
292 result = Primary( st, i );
293 // cout <<"i "<<i<< "Primary " << result->Unparse() << endl;
298 valt = (TObjString*)st.At( i );
299 token = valt->String();
302 result = new AliExpression( kOpAND, result, Primary( st, i ) );
303 // cout <<"i "<<i<< " Expression AND " << result->Unparse() << endl;
306 result = new AliExpression( kOpOR, result, Primary( st, i ) );
307 // cout <<"i "<<i<< " Expression OR " << result->Unparse() << endl;
316 if( stack == 0 && !token.IsNull() && token[0] == ')' ) {
317 AliErrorGeneral( "AliExpression::Expression", "To many closing parenthesis." );
319 result = new AliExpression;
321 if( stack == 0 && i< nt-1 ) {
322 AliErrorGeneral( "AliExpression::Expression", Form( "Unexpected symbol on input. %s", token.Data() ) );
324 result = new AliExpression;
329 ////////////////////////////////////////////////////////////////////////////////
331 ClassImp( AliVariableExpression )
333 //______________________________________________________________________________
334 Bool_t AliVariableExpression::Value( TObjArray& pgm )
337 TObject* dd = pgm.FindObject( fVname.Data() );
339 AliError( fVname + " is undefined" );
342 return ((AliTriggerInput*)dd)->GetValue();