exprtk.hpp 1.3 MB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843184418451846184718481849185018511852185318541855185618571858185918601861186218631864186518661867186818691870187118721873187418751876187718781879188018811882188318841885188618871888188918901891189218931894189518961897189818991900190119021903190419051906190719081909191019111912191319141915191619171918191919201921192219231924192519261927192819291930193119321933193419351936193719381939194019411942194319441945194619471948194919501951195219531954195519561957195819591960196119621963196419651966196719681969197019711972197319741975197619771978197919801981198219831984198519861987198819891990199119921993199419951996199719981999200020012002200320042005200620072008200920102011201220132014201520162017201820192020202120222023202420252026202720282029203020312032203320342035203620372038203920402041204220432044204520462047204820492050205120522053205420552056205720582059206020612062206320642065206620672068206920702071207220732074207520762077207820792080208120822083208420852086208720882089209020912092209320942095209620972098209921002101210221032104210521062107210821092110211121122113211421152116211721182119212021212122212321242125212621272128212921302131213221332134213521362137213821392140214121422143214421452146214721482149215021512152215321542155215621572158215921602161216221632164216521662167216821692170217121722173217421752176217721782179218021812182218321842185218621872188218921902191219221932194219521962197219821992200220122022203220422052206220722082209221022112212221322142215221622172218221922202221222222232224222522262227222822292230223122322233223422352236223722382239224022412242224322442245224622472248224922502251225222532254225522562257225822592260226122622263226422652266226722682269227022712272227322742275227622772278227922802281228222832284228522862287228822892290229122922293229422952296229722982299230023012302230323042305230623072308230923102311231223132314231523162317231823192320232123222323232423252326232723282329233023312332233323342335233623372338233923402341234223432344234523462347234823492350235123522353235423552356235723582359236023612362236323642365236623672368236923702371237223732374237523762377237823792380238123822383238423852386238723882389239023912392239323942395239623972398239924002401240224032404240524062407240824092410241124122413241424152416241724182419242024212422242324242425242624272428242924302431243224332434243524362437243824392440244124422443244424452446244724482449245024512452245324542455245624572458245924602461246224632464246524662467246824692470247124722473247424752476247724782479248024812482248324842485248624872488248924902491249224932494249524962497249824992500250125022503250425052506250725082509251025112512251325142515251625172518251925202521252225232524252525262527252825292530253125322533253425352536253725382539254025412542254325442545254625472548254925502551255225532554255525562557255825592560256125622563256425652566256725682569257025712572257325742575257625772578257925802581258225832584258525862587258825892590259125922593259425952596259725982599260026012602260326042605260626072608260926102611261226132614261526162617261826192620262126222623262426252626262726282629263026312632263326342635263626372638263926402641264226432644264526462647264826492650265126522653265426552656265726582659266026612662266326642665266626672668266926702671267226732674267526762677267826792680268126822683268426852686268726882689269026912692269326942695269626972698269927002701270227032704270527062707270827092710271127122713271427152716271727182719272027212722272327242725272627272728272927302731273227332734273527362737273827392740274127422743274427452746274727482749275027512752275327542755275627572758275927602761276227632764276527662767276827692770277127722773277427752776277727782779278027812782278327842785278627872788278927902791279227932794279527962797279827992800280128022803280428052806280728082809281028112812281328142815281628172818281928202821282228232824282528262827282828292830283128322833283428352836283728382839284028412842284328442845284628472848284928502851285228532854285528562857285828592860286128622863286428652866286728682869287028712872287328742875287628772878287928802881288228832884288528862887288828892890289128922893289428952896289728982899290029012902290329042905290629072908290929102911291229132914291529162917291829192920292129222923292429252926292729282929293029312932293329342935293629372938293929402941294229432944294529462947294829492950295129522953295429552956295729582959296029612962296329642965296629672968296929702971297229732974297529762977297829792980298129822983298429852986298729882989299029912992299329942995299629972998299930003001300230033004300530063007300830093010301130123013301430153016301730183019302030213022302330243025302630273028302930303031303230333034303530363037303830393040304130423043304430453046304730483049305030513052305330543055305630573058305930603061306230633064306530663067306830693070307130723073307430753076307730783079308030813082308330843085308630873088308930903091309230933094309530963097309830993100310131023103310431053106310731083109311031113112311331143115311631173118311931203121312231233124312531263127312831293130313131323133313431353136313731383139314031413142314331443145314631473148314931503151315231533154315531563157315831593160316131623163316431653166316731683169317031713172317331743175317631773178317931803181318231833184318531863187318831893190319131923193319431953196319731983199320032013202320332043205320632073208320932103211321232133214321532163217321832193220322132223223322432253226322732283229323032313232323332343235323632373238323932403241324232433244324532463247324832493250325132523253325432553256325732583259326032613262326332643265326632673268326932703271327232733274327532763277327832793280328132823283328432853286328732883289329032913292329332943295329632973298329933003301330233033304330533063307330833093310331133123313331433153316331733183319332033213322332333243325332633273328332933303331333233333334333533363337333833393340334133423343334433453346334733483349335033513352335333543355335633573358335933603361336233633364336533663367336833693370337133723373337433753376337733783379338033813382338333843385338633873388338933903391339233933394339533963397339833993400340134023403340434053406340734083409341034113412341334143415341634173418341934203421342234233424342534263427342834293430343134323433343434353436343734383439344034413442344334443445344634473448344934503451345234533454345534563457345834593460346134623463346434653466346734683469347034713472347334743475347634773478347934803481348234833484348534863487348834893490349134923493349434953496349734983499350035013502350335043505350635073508350935103511351235133514351535163517351835193520352135223523352435253526352735283529353035313532353335343535353635373538353935403541354235433544354535463547354835493550355135523553355435553556355735583559356035613562356335643565356635673568356935703571357235733574357535763577357835793580358135823583358435853586358735883589359035913592359335943595359635973598359936003601360236033604360536063607360836093610361136123613361436153616361736183619362036213622362336243625362636273628362936303631363236333634363536363637363836393640364136423643364436453646364736483649365036513652365336543655365636573658365936603661366236633664366536663667366836693670367136723673367436753676367736783679368036813682368336843685368636873688368936903691369236933694369536963697369836993700370137023703370437053706370737083709371037113712371337143715371637173718371937203721372237233724372537263727372837293730373137323733373437353736373737383739374037413742374337443745374637473748374937503751375237533754375537563757375837593760376137623763376437653766376737683769377037713772377337743775377637773778377937803781378237833784378537863787378837893790379137923793379437953796379737983799380038013802380338043805380638073808380938103811381238133814381538163817381838193820382138223823382438253826382738283829383038313832383338343835383638373838383938403841384238433844384538463847384838493850385138523853385438553856385738583859386038613862386338643865386638673868386938703871387238733874387538763877387838793880388138823883388438853886388738883889389038913892389338943895389638973898389939003901390239033904390539063907390839093910391139123913391439153916391739183919392039213922392339243925392639273928392939303931393239333934393539363937393839393940394139423943394439453946394739483949395039513952395339543955395639573958395939603961396239633964396539663967396839693970397139723973397439753976397739783979398039813982398339843985398639873988398939903991399239933994399539963997399839994000400140024003400440054006400740084009401040114012401340144015401640174018401940204021402240234024402540264027402840294030403140324033403440354036403740384039404040414042404340444045404640474048404940504051405240534054405540564057405840594060406140624063406440654066406740684069407040714072407340744075407640774078407940804081408240834084408540864087408840894090409140924093409440954096409740984099410041014102410341044105410641074108410941104111411241134114411541164117411841194120412141224123412441254126412741284129413041314132413341344135413641374138413941404141414241434144414541464147414841494150415141524153415441554156415741584159416041614162416341644165416641674168416941704171417241734174417541764177417841794180418141824183418441854186418741884189419041914192419341944195419641974198419942004201420242034204420542064207420842094210421142124213421442154216421742184219422042214222422342244225422642274228422942304231423242334234423542364237423842394240424142424243424442454246424742484249425042514252425342544255425642574258425942604261426242634264426542664267426842694270427142724273427442754276427742784279428042814282428342844285428642874288428942904291429242934294429542964297429842994300430143024303430443054306430743084309431043114312431343144315431643174318431943204321432243234324432543264327432843294330433143324333433443354336433743384339434043414342434343444345434643474348434943504351435243534354435543564357435843594360436143624363436443654366436743684369437043714372437343744375437643774378437943804381438243834384438543864387438843894390439143924393439443954396439743984399440044014402440344044405440644074408440944104411441244134414441544164417441844194420442144224423442444254426442744284429443044314432443344344435443644374438443944404441444244434444444544464447444844494450445144524453445444554456445744584459446044614462446344644465446644674468446944704471447244734474447544764477447844794480448144824483448444854486448744884489449044914492449344944495449644974498449945004501450245034504450545064507450845094510451145124513451445154516451745184519452045214522452345244525452645274528452945304531453245334534453545364537453845394540454145424543454445454546454745484549455045514552455345544555455645574558455945604561456245634564456545664567456845694570457145724573457445754576457745784579458045814582458345844585458645874588458945904591459245934594459545964597459845994600460146024603460446054606460746084609461046114612461346144615461646174618461946204621462246234624462546264627462846294630463146324633463446354636463746384639464046414642464346444645464646474648464946504651465246534654465546564657465846594660466146624663466446654666466746684669467046714672467346744675467646774678467946804681468246834684468546864687468846894690469146924693469446954696469746984699470047014702470347044705470647074708470947104711471247134714471547164717471847194720472147224723472447254726472747284729473047314732473347344735473647374738473947404741474247434744474547464747474847494750475147524753475447554756475747584759476047614762476347644765476647674768476947704771477247734774477547764777477847794780478147824783478447854786478747884789479047914792479347944795479647974798479948004801480248034804480548064807480848094810481148124813481448154816481748184819482048214822482348244825482648274828482948304831483248334834483548364837483848394840484148424843484448454846484748484849485048514852485348544855485648574858485948604861486248634864486548664867486848694870487148724873487448754876487748784879488048814882488348844885488648874888488948904891489248934894489548964897489848994900490149024903490449054906490749084909491049114912491349144915491649174918491949204921492249234924492549264927492849294930493149324933493449354936493749384939494049414942494349444945494649474948494949504951495249534954495549564957495849594960496149624963496449654966496749684969497049714972497349744975497649774978497949804981498249834984498549864987498849894990499149924993499449954996499749984999500050015002500350045005500650075008500950105011501250135014501550165017501850195020502150225023502450255026502750285029503050315032503350345035503650375038503950405041504250435044504550465047504850495050505150525053505450555056505750585059506050615062506350645065506650675068506950705071507250735074507550765077507850795080508150825083508450855086508750885089509050915092509350945095509650975098509951005101510251035104510551065107510851095110511151125113511451155116511751185119512051215122512351245125512651275128512951305131513251335134513551365137513851395140514151425143514451455146514751485149515051515152515351545155515651575158515951605161516251635164516551665167516851695170517151725173517451755176517751785179518051815182518351845185518651875188518951905191519251935194519551965197519851995200520152025203520452055206520752085209521052115212521352145215521652175218521952205221522252235224522552265227522852295230523152325233523452355236523752385239524052415242524352445245524652475248524952505251525252535254525552565257525852595260526152625263526452655266526752685269527052715272527352745275527652775278527952805281528252835284528552865287528852895290529152925293529452955296529752985299530053015302530353045305530653075308530953105311531253135314531553165317531853195320532153225323532453255326532753285329533053315332533353345335533653375338533953405341534253435344534553465347534853495350535153525353535453555356535753585359536053615362536353645365536653675368536953705371537253735374537553765377537853795380538153825383538453855386538753885389539053915392539353945395539653975398539954005401540254035404540554065407540854095410541154125413541454155416541754185419542054215422542354245425542654275428542954305431543254335434543554365437543854395440544154425443544454455446544754485449545054515452545354545455545654575458545954605461546254635464546554665467546854695470547154725473547454755476547754785479548054815482548354845485548654875488548954905491549254935494549554965497549854995500550155025503550455055506550755085509551055115512551355145515551655175518551955205521552255235524552555265527552855295530553155325533553455355536553755385539554055415542554355445545554655475548554955505551555255535554555555565557555855595560556155625563556455655566556755685569557055715572557355745575557655775578557955805581558255835584558555865587558855895590559155925593559455955596559755985599560056015602560356045605560656075608560956105611561256135614561556165617561856195620562156225623562456255626562756285629563056315632563356345635563656375638563956405641564256435644564556465647564856495650565156525653565456555656565756585659566056615662566356645665566656675668566956705671567256735674567556765677567856795680568156825683568456855686568756885689569056915692569356945695569656975698569957005701570257035704570557065707570857095710571157125713571457155716571757185719572057215722572357245725572657275728572957305731573257335734573557365737573857395740574157425743574457455746574757485749575057515752575357545755575657575758575957605761576257635764576557665767576857695770577157725773577457755776577757785779578057815782578357845785578657875788578957905791579257935794579557965797579857995800580158025803580458055806580758085809581058115812581358145815581658175818581958205821582258235824582558265827582858295830583158325833583458355836583758385839584058415842584358445845584658475848584958505851585258535854585558565857585858595860586158625863586458655866586758685869587058715872587358745875587658775878587958805881588258835884588558865887588858895890589158925893589458955896589758985899590059015902590359045905590659075908590959105911591259135914591559165917591859195920592159225923592459255926592759285929593059315932593359345935593659375938593959405941594259435944594559465947594859495950595159525953595459555956595759585959596059615962596359645965596659675968596959705971597259735974597559765977597859795980598159825983598459855986598759885989599059915992599359945995599659975998599960006001600260036004600560066007600860096010601160126013601460156016601760186019602060216022602360246025602660276028602960306031603260336034603560366037603860396040604160426043604460456046604760486049605060516052605360546055605660576058605960606061606260636064606560666067606860696070607160726073607460756076607760786079608060816082608360846085608660876088608960906091609260936094609560966097609860996100610161026103610461056106610761086109611061116112611361146115611661176118611961206121612261236124612561266127612861296130613161326133613461356136613761386139614061416142614361446145614661476148614961506151615261536154615561566157615861596160616161626163616461656166616761686169617061716172617361746175617661776178617961806181618261836184618561866187618861896190619161926193619461956196619761986199620062016202620362046205620662076208620962106211621262136214621562166217621862196220622162226223622462256226622762286229623062316232623362346235623662376238623962406241624262436244624562466247624862496250625162526253625462556256625762586259626062616262626362646265626662676268626962706271627262736274627562766277627862796280628162826283628462856286628762886289629062916292629362946295629662976298629963006301630263036304630563066307630863096310631163126313631463156316631763186319632063216322632363246325632663276328632963306331633263336334633563366337633863396340634163426343634463456346634763486349635063516352635363546355635663576358635963606361636263636364636563666367636863696370637163726373637463756376637763786379638063816382638363846385638663876388638963906391639263936394639563966397639863996400640164026403640464056406640764086409641064116412641364146415641664176418641964206421642264236424642564266427642864296430643164326433643464356436643764386439644064416442644364446445644664476448644964506451645264536454645564566457645864596460646164626463646464656466646764686469647064716472647364746475647664776478647964806481648264836484648564866487648864896490649164926493649464956496649764986499650065016502650365046505650665076508650965106511651265136514651565166517651865196520652165226523652465256526652765286529653065316532653365346535653665376538653965406541654265436544654565466547654865496550655165526553655465556556655765586559656065616562656365646565656665676568656965706571657265736574657565766577657865796580658165826583658465856586658765886589659065916592659365946595659665976598659966006601660266036604660566066607660866096610661166126613661466156616661766186619662066216622662366246625662666276628662966306631663266336634663566366637663866396640664166426643664466456646664766486649665066516652665366546655665666576658665966606661666266636664666566666667666866696670667166726673667466756676667766786679668066816682668366846685668666876688668966906691669266936694669566966697669866996700670167026703670467056706670767086709671067116712671367146715671667176718671967206721672267236724672567266727672867296730673167326733673467356736673767386739674067416742674367446745674667476748674967506751675267536754675567566757675867596760676167626763676467656766676767686769677067716772677367746775677667776778677967806781678267836784678567866787678867896790679167926793679467956796679767986799680068016802680368046805680668076808680968106811681268136814681568166817681868196820682168226823682468256826682768286829683068316832683368346835683668376838683968406841684268436844684568466847684868496850685168526853685468556856685768586859686068616862686368646865686668676868686968706871687268736874687568766877687868796880688168826883688468856886688768886889689068916892689368946895689668976898689969006901690269036904690569066907690869096910691169126913691469156916691769186919692069216922692369246925692669276928692969306931693269336934693569366937693869396940694169426943694469456946694769486949695069516952695369546955695669576958695969606961696269636964696569666967696869696970697169726973697469756976697769786979698069816982698369846985698669876988698969906991699269936994699569966997699869997000700170027003700470057006700770087009701070117012701370147015701670177018701970207021702270237024702570267027702870297030703170327033703470357036703770387039704070417042704370447045704670477048704970507051705270537054705570567057705870597060706170627063706470657066706770687069707070717072707370747075707670777078707970807081708270837084708570867087708870897090709170927093709470957096709770987099710071017102710371047105710671077108710971107111711271137114711571167117711871197120712171227123712471257126712771287129713071317132713371347135713671377138713971407141714271437144714571467147714871497150715171527153715471557156715771587159716071617162716371647165716671677168716971707171717271737174717571767177717871797180718171827183718471857186718771887189719071917192719371947195719671977198719972007201720272037204720572067207720872097210721172127213721472157216721772187219722072217222722372247225722672277228722972307231723272337234723572367237723872397240724172427243724472457246724772487249725072517252725372547255725672577258725972607261726272637264726572667267726872697270727172727273727472757276727772787279728072817282728372847285728672877288728972907291729272937294729572967297729872997300730173027303730473057306730773087309731073117312731373147315731673177318731973207321732273237324732573267327732873297330733173327333733473357336733773387339734073417342734373447345734673477348734973507351735273537354735573567357735873597360736173627363736473657366736773687369737073717372737373747375737673777378737973807381738273837384738573867387738873897390739173927393739473957396739773987399740074017402740374047405740674077408740974107411741274137414741574167417741874197420742174227423742474257426742774287429743074317432743374347435743674377438743974407441744274437444744574467447744874497450745174527453745474557456745774587459746074617462746374647465746674677468746974707471747274737474747574767477747874797480748174827483748474857486748774887489749074917492749374947495749674977498749975007501750275037504750575067507750875097510751175127513751475157516751775187519752075217522752375247525752675277528752975307531753275337534753575367537753875397540754175427543754475457546754775487549755075517552755375547555755675577558755975607561756275637564756575667567756875697570757175727573757475757576757775787579758075817582758375847585758675877588758975907591759275937594759575967597759875997600760176027603760476057606760776087609761076117612761376147615761676177618761976207621762276237624762576267627762876297630763176327633763476357636763776387639764076417642764376447645764676477648764976507651765276537654765576567657765876597660766176627663766476657666766776687669767076717672767376747675767676777678767976807681768276837684768576867687768876897690769176927693769476957696769776987699770077017702770377047705770677077708770977107711771277137714771577167717771877197720772177227723772477257726772777287729773077317732773377347735773677377738773977407741774277437744774577467747774877497750775177527753775477557756775777587759776077617762776377647765776677677768776977707771777277737774777577767777777877797780778177827783778477857786778777887789779077917792779377947795779677977798779978007801780278037804780578067807780878097810781178127813781478157816781778187819782078217822782378247825782678277828782978307831783278337834783578367837783878397840784178427843784478457846784778487849785078517852785378547855785678577858785978607861786278637864786578667867786878697870787178727873787478757876787778787879788078817882788378847885788678877888788978907891789278937894789578967897789878997900790179027903790479057906790779087909791079117912791379147915791679177918791979207921792279237924792579267927792879297930793179327933793479357936793779387939794079417942794379447945794679477948794979507951795279537954795579567957795879597960796179627963796479657966796779687969797079717972797379747975797679777978797979807981798279837984798579867987798879897990799179927993799479957996799779987999800080018002800380048005800680078008800980108011801280138014801580168017801880198020802180228023802480258026802780288029803080318032803380348035803680378038803980408041804280438044804580468047804880498050805180528053805480558056805780588059806080618062806380648065806680678068806980708071807280738074807580768077807880798080808180828083808480858086808780888089809080918092809380948095809680978098809981008101810281038104810581068107810881098110811181128113811481158116811781188119812081218122812381248125812681278128812981308131813281338134813581368137813881398140814181428143814481458146814781488149815081518152815381548155815681578158815981608161816281638164816581668167816881698170817181728173817481758176817781788179818081818182818381848185818681878188818981908191819281938194819581968197819881998200820182028203820482058206820782088209821082118212821382148215821682178218821982208221822282238224822582268227822882298230823182328233823482358236823782388239824082418242824382448245824682478248824982508251825282538254825582568257825882598260826182628263826482658266826782688269827082718272827382748275827682778278827982808281828282838284828582868287828882898290829182928293829482958296829782988299830083018302830383048305830683078308830983108311831283138314831583168317831883198320832183228323832483258326832783288329833083318332833383348335833683378338833983408341834283438344834583468347834883498350835183528353835483558356835783588359836083618362836383648365836683678368836983708371837283738374837583768377837883798380838183828383838483858386838783888389839083918392839383948395839683978398839984008401840284038404840584068407840884098410841184128413841484158416841784188419842084218422842384248425842684278428842984308431843284338434843584368437843884398440844184428443844484458446844784488449845084518452845384548455845684578458845984608461846284638464846584668467846884698470847184728473847484758476847784788479848084818482848384848485848684878488848984908491849284938494849584968497849884998500850185028503850485058506850785088509851085118512851385148515851685178518851985208521852285238524852585268527852885298530853185328533853485358536853785388539854085418542854385448545854685478548854985508551855285538554855585568557855885598560856185628563856485658566856785688569857085718572857385748575857685778578857985808581858285838584858585868587858885898590859185928593859485958596859785988599860086018602860386048605860686078608860986108611861286138614861586168617861886198620862186228623862486258626862786288629863086318632863386348635863686378638863986408641864286438644864586468647864886498650865186528653865486558656865786588659866086618662866386648665866686678668866986708671867286738674867586768677867886798680868186828683868486858686868786888689869086918692869386948695869686978698869987008701870287038704870587068707870887098710871187128713871487158716871787188719872087218722872387248725872687278728872987308731873287338734873587368737873887398740874187428743874487458746874787488749875087518752875387548755875687578758875987608761876287638764876587668767876887698770877187728773877487758776877787788779878087818782878387848785878687878788878987908791879287938794879587968797879887998800880188028803880488058806880788088809881088118812881388148815881688178818881988208821882288238824882588268827882888298830883188328833883488358836883788388839884088418842884388448845884688478848884988508851885288538854885588568857885888598860886188628863886488658866886788688869887088718872887388748875887688778878887988808881888288838884888588868887888888898890889188928893889488958896889788988899890089018902890389048905890689078908890989108911891289138914891589168917891889198920892189228923892489258926892789288929893089318932893389348935893689378938893989408941894289438944894589468947894889498950895189528953895489558956895789588959896089618962896389648965896689678968896989708971897289738974897589768977897889798980898189828983898489858986898789888989899089918992899389948995899689978998899990009001900290039004900590069007900890099010901190129013901490159016901790189019902090219022902390249025902690279028902990309031903290339034903590369037903890399040904190429043904490459046904790489049905090519052905390549055905690579058905990609061906290639064906590669067906890699070907190729073907490759076907790789079908090819082908390849085908690879088908990909091909290939094909590969097909890999100910191029103910491059106910791089109911091119112911391149115911691179118911991209121912291239124912591269127912891299130913191329133913491359136913791389139914091419142914391449145914691479148914991509151915291539154915591569157915891599160916191629163916491659166916791689169917091719172917391749175917691779178917991809181918291839184918591869187918891899190919191929193919491959196919791989199920092019202920392049205920692079208920992109211921292139214921592169217921892199220922192229223922492259226922792289229923092319232923392349235923692379238923992409241924292439244924592469247924892499250925192529253925492559256925792589259926092619262926392649265926692679268926992709271927292739274927592769277927892799280928192829283928492859286928792889289929092919292929392949295929692979298929993009301930293039304930593069307930893099310931193129313931493159316931793189319932093219322932393249325932693279328932993309331933293339334933593369337933893399340934193429343934493459346934793489349935093519352935393549355935693579358935993609361936293639364936593669367936893699370937193729373937493759376937793789379938093819382938393849385938693879388938993909391939293939394939593969397939893999400940194029403940494059406940794089409941094119412941394149415941694179418941994209421942294239424942594269427942894299430943194329433943494359436943794389439944094419442944394449445944694479448944994509451945294539454945594569457945894599460946194629463946494659466946794689469947094719472947394749475947694779478947994809481948294839484948594869487948894899490949194929493949494959496949794989499950095019502950395049505950695079508950995109511951295139514951595169517951895199520952195229523952495259526952795289529953095319532953395349535953695379538953995409541954295439544954595469547954895499550955195529553955495559556955795589559956095619562956395649565956695679568956995709571957295739574957595769577957895799580958195829583958495859586958795889589959095919592959395949595959695979598959996009601960296039604960596069607960896099610961196129613961496159616961796189619962096219622962396249625962696279628962996309631963296339634963596369637963896399640964196429643964496459646964796489649965096519652965396549655965696579658965996609661966296639664966596669667966896699670967196729673967496759676967796789679968096819682968396849685968696879688968996909691969296939694969596969697969896999700970197029703970497059706970797089709971097119712971397149715971697179718971997209721972297239724972597269727972897299730973197329733973497359736973797389739974097419742974397449745974697479748974997509751975297539754975597569757975897599760976197629763976497659766976797689769977097719772977397749775977697779778977997809781978297839784978597869787978897899790979197929793979497959796979797989799980098019802980398049805980698079808980998109811981298139814981598169817981898199820982198229823982498259826982798289829983098319832983398349835983698379838983998409841984298439844984598469847984898499850985198529853985498559856985798589859986098619862986398649865986698679868986998709871987298739874987598769877987898799880988198829883988498859886988798889889989098919892989398949895989698979898989999009901990299039904990599069907990899099910991199129913991499159916991799189919992099219922992399249925992699279928992999309931993299339934993599369937993899399940994199429943994499459946994799489949995099519952995399549955995699579958995999609961996299639964996599669967996899699970997199729973997499759976997799789979998099819982998399849985998699879988998999909991999299939994999599969997999899991000010001100021000310004100051000610007100081000910010100111001210013100141001510016100171001810019100201002110022100231002410025100261002710028100291003010031100321003310034100351003610037100381003910040100411004210043100441004510046100471004810049100501005110052100531005410055100561005710058100591006010061100621006310064100651006610067100681006910070100711007210073100741007510076100771007810079100801008110082100831008410085100861008710088100891009010091100921009310094100951009610097100981009910100101011010210103101041010510106101071010810109101101011110112101131011410115101161011710118101191012010121101221012310124101251012610127101281012910130101311013210133101341013510136101371013810139101401014110142101431014410145101461014710148101491015010151101521015310154101551015610157101581015910160101611016210163101641016510166101671016810169101701017110172101731017410175101761017710178101791018010181101821018310184101851018610187101881018910190101911019210193101941019510196101971019810199102001020110202102031020410205102061020710208102091021010211102121021310214102151021610217102181021910220102211022210223102241022510226102271022810229102301023110232102331023410235102361023710238102391024010241102421024310244102451024610247102481024910250102511025210253102541025510256102571025810259102601026110262102631026410265102661026710268102691027010271102721027310274102751027610277102781027910280102811028210283102841028510286102871028810289102901029110292102931029410295102961029710298102991030010301103021030310304103051030610307103081030910310103111031210313103141031510316103171031810319103201032110322103231032410325103261032710328103291033010331103321033310334103351033610337103381033910340103411034210343103441034510346103471034810349103501035110352103531035410355103561035710358103591036010361103621036310364103651036610367103681036910370103711037210373103741037510376103771037810379103801038110382103831038410385103861038710388103891039010391103921039310394103951039610397103981039910400104011040210403104041040510406104071040810409104101041110412104131041410415104161041710418104191042010421104221042310424104251042610427104281042910430104311043210433104341043510436104371043810439104401044110442104431044410445104461044710448104491045010451104521045310454104551045610457104581045910460104611046210463104641046510466104671046810469104701047110472104731047410475104761047710478104791048010481104821048310484104851048610487104881048910490104911049210493104941049510496104971049810499105001050110502105031050410505105061050710508105091051010511105121051310514105151051610517105181051910520105211052210523105241052510526105271052810529105301053110532105331053410535105361053710538105391054010541105421054310544105451054610547105481054910550105511055210553105541055510556105571055810559105601056110562105631056410565105661056710568105691057010571105721057310574105751057610577105781057910580105811058210583105841058510586105871058810589105901059110592105931059410595105961059710598105991060010601106021060310604106051060610607106081060910610106111061210613106141061510616106171061810619106201062110622106231062410625106261062710628106291063010631106321063310634106351063610637106381063910640106411064210643106441064510646106471064810649106501065110652106531065410655106561065710658106591066010661106621066310664106651066610667106681066910670106711067210673106741067510676106771067810679106801068110682106831068410685106861068710688106891069010691106921069310694106951069610697106981069910700107011070210703107041070510706107071070810709107101071110712107131071410715107161071710718107191072010721107221072310724107251072610727107281072910730107311073210733107341073510736107371073810739107401074110742107431074410745107461074710748107491075010751107521075310754107551075610757107581075910760107611076210763107641076510766107671076810769107701077110772107731077410775107761077710778107791078010781107821078310784107851078610787107881078910790107911079210793107941079510796107971079810799108001080110802108031080410805108061080710808108091081010811108121081310814108151081610817108181081910820108211082210823108241082510826108271082810829108301083110832108331083410835108361083710838108391084010841108421084310844108451084610847108481084910850108511085210853108541085510856108571085810859108601086110862108631086410865108661086710868108691087010871108721087310874108751087610877108781087910880108811088210883108841088510886108871088810889108901089110892108931089410895108961089710898108991090010901109021090310904109051090610907109081090910910109111091210913109141091510916109171091810919109201092110922109231092410925109261092710928109291093010931109321093310934109351093610937109381093910940109411094210943109441094510946109471094810949109501095110952109531095410955109561095710958109591096010961109621096310964109651096610967109681096910970109711097210973109741097510976109771097810979109801098110982109831098410985109861098710988109891099010991109921099310994109951099610997109981099911000110011100211003110041100511006110071100811009110101101111012110131101411015110161101711018110191102011021110221102311024110251102611027110281102911030110311103211033110341103511036110371103811039110401104111042110431104411045110461104711048110491105011051110521105311054110551105611057110581105911060110611106211063110641106511066110671106811069110701107111072110731107411075110761107711078110791108011081110821108311084110851108611087110881108911090110911109211093110941109511096110971109811099111001110111102111031110411105111061110711108111091111011111111121111311114111151111611117111181111911120111211112211123111241112511126111271112811129111301113111132111331113411135111361113711138111391114011141111421114311144111451114611147111481114911150111511115211153111541115511156111571115811159111601116111162111631116411165111661116711168111691117011171111721117311174111751117611177111781117911180111811118211183111841118511186111871118811189111901119111192111931119411195111961119711198111991120011201112021120311204112051120611207112081120911210112111121211213112141121511216112171121811219112201122111222112231122411225112261122711228112291123011231112321123311234112351123611237112381123911240112411124211243112441124511246112471124811249112501125111252112531125411255112561125711258112591126011261112621126311264112651126611267112681126911270112711127211273112741127511276112771127811279112801128111282112831128411285112861128711288112891129011291112921129311294112951129611297112981129911300113011130211303113041130511306113071130811309113101131111312113131131411315113161131711318113191132011321113221132311324113251132611327113281132911330113311133211333113341133511336113371133811339113401134111342113431134411345113461134711348113491135011351113521135311354113551135611357113581135911360113611136211363113641136511366113671136811369113701137111372113731137411375113761137711378113791138011381113821138311384113851138611387113881138911390113911139211393113941139511396113971139811399114001140111402114031140411405114061140711408114091141011411114121141311414114151141611417114181141911420114211142211423114241142511426114271142811429114301143111432114331143411435114361143711438114391144011441114421144311444114451144611447114481144911450114511145211453114541145511456114571145811459114601146111462114631146411465114661146711468114691147011471114721147311474114751147611477114781147911480114811148211483114841148511486114871148811489114901149111492114931149411495114961149711498114991150011501115021150311504115051150611507115081150911510115111151211513115141151511516115171151811519115201152111522115231152411525115261152711528115291153011531115321153311534115351153611537115381153911540115411154211543115441154511546115471154811549115501155111552115531155411555115561155711558115591156011561115621156311564115651156611567115681156911570115711157211573115741157511576115771157811579115801158111582115831158411585115861158711588115891159011591115921159311594115951159611597115981159911600116011160211603116041160511606116071160811609116101161111612116131161411615116161161711618116191162011621116221162311624116251162611627116281162911630116311163211633116341163511636116371163811639116401164111642116431164411645116461164711648116491165011651116521165311654116551165611657116581165911660116611166211663116641166511666116671166811669116701167111672116731167411675116761167711678116791168011681116821168311684116851168611687116881168911690116911169211693116941169511696116971169811699117001170111702117031170411705117061170711708117091171011711117121171311714117151171611717117181171911720117211172211723117241172511726117271172811729117301173111732117331173411735117361173711738117391174011741117421174311744117451174611747117481174911750117511175211753117541175511756117571175811759117601176111762117631176411765117661176711768117691177011771117721177311774117751177611777117781177911780117811178211783117841178511786117871178811789117901179111792117931179411795117961179711798117991180011801118021180311804118051180611807118081180911810118111181211813118141181511816118171181811819118201182111822118231182411825118261182711828118291183011831118321183311834118351183611837118381183911840118411184211843118441184511846118471184811849118501185111852118531185411855118561185711858118591186011861118621186311864118651186611867118681186911870118711187211873118741187511876118771187811879118801188111882118831188411885118861188711888118891189011891118921189311894118951189611897118981189911900119011190211903119041190511906119071190811909119101191111912119131191411915119161191711918119191192011921119221192311924119251192611927119281192911930119311193211933119341193511936119371193811939119401194111942119431194411945119461194711948119491195011951119521195311954119551195611957119581195911960119611196211963119641196511966119671196811969119701197111972119731197411975119761197711978119791198011981119821198311984119851198611987119881198911990119911199211993119941199511996119971199811999120001200112002120031200412005120061200712008120091201012011120121201312014120151201612017120181201912020120211202212023120241202512026120271202812029120301203112032120331203412035120361203712038120391204012041120421204312044120451204612047120481204912050120511205212053120541205512056120571205812059120601206112062120631206412065120661206712068120691207012071120721207312074120751207612077120781207912080120811208212083120841208512086120871208812089120901209112092120931209412095120961209712098120991210012101121021210312104121051210612107121081210912110121111211212113121141211512116121171211812119121201212112122121231212412125121261212712128121291213012131121321213312134121351213612137121381213912140121411214212143121441214512146121471214812149121501215112152121531215412155121561215712158121591216012161121621216312164121651216612167121681216912170121711217212173121741217512176121771217812179121801218112182121831218412185121861218712188121891219012191121921219312194121951219612197121981219912200122011220212203122041220512206122071220812209122101221112212122131221412215122161221712218122191222012221122221222312224122251222612227122281222912230122311223212233122341223512236122371223812239122401224112242122431224412245122461224712248122491225012251122521225312254122551225612257122581225912260122611226212263122641226512266122671226812269122701227112272122731227412275122761227712278122791228012281122821228312284122851228612287122881228912290122911229212293122941229512296122971229812299123001230112302123031230412305123061230712308123091231012311123121231312314123151231612317123181231912320123211232212323123241232512326123271232812329123301233112332123331233412335123361233712338123391234012341123421234312344123451234612347123481234912350123511235212353123541235512356123571235812359123601236112362123631236412365123661236712368123691237012371123721237312374123751237612377123781237912380123811238212383123841238512386123871238812389123901239112392123931239412395123961239712398123991240012401124021240312404124051240612407124081240912410124111241212413124141241512416124171241812419124201242112422124231242412425124261242712428124291243012431124321243312434124351243612437124381243912440124411244212443124441244512446124471244812449124501245112452124531245412455124561245712458124591246012461124621246312464124651246612467124681246912470124711247212473124741247512476124771247812479124801248112482124831248412485124861248712488124891249012491124921249312494124951249612497124981249912500125011250212503125041250512506125071250812509125101251112512125131251412515125161251712518125191252012521125221252312524125251252612527125281252912530125311253212533125341253512536125371253812539125401254112542125431254412545125461254712548125491255012551125521255312554125551255612557125581255912560125611256212563125641256512566125671256812569125701257112572125731257412575125761257712578125791258012581125821258312584125851258612587125881258912590125911259212593125941259512596125971259812599126001260112602126031260412605126061260712608126091261012611126121261312614126151261612617126181261912620126211262212623126241262512626126271262812629126301263112632126331263412635126361263712638126391264012641126421264312644126451264612647126481264912650126511265212653126541265512656126571265812659126601266112662126631266412665126661266712668126691267012671126721267312674126751267612677126781267912680126811268212683126841268512686126871268812689126901269112692126931269412695126961269712698126991270012701127021270312704127051270612707127081270912710127111271212713127141271512716127171271812719127201272112722127231272412725127261272712728127291273012731127321273312734127351273612737127381273912740127411274212743127441274512746127471274812749127501275112752127531275412755127561275712758127591276012761127621276312764127651276612767127681276912770127711277212773127741277512776127771277812779127801278112782127831278412785127861278712788127891279012791127921279312794127951279612797127981279912800128011280212803128041280512806128071280812809128101281112812128131281412815128161281712818128191282012821128221282312824128251282612827128281282912830128311283212833128341283512836128371283812839128401284112842128431284412845128461284712848128491285012851128521285312854128551285612857128581285912860128611286212863128641286512866128671286812869128701287112872128731287412875128761287712878128791288012881128821288312884128851288612887128881288912890128911289212893128941289512896128971289812899129001290112902129031290412905129061290712908129091291012911129121291312914129151291612917129181291912920129211292212923129241292512926129271292812929129301293112932129331293412935129361293712938129391294012941129421294312944129451294612947129481294912950129511295212953129541295512956129571295812959129601296112962129631296412965129661296712968129691297012971129721297312974129751297612977129781297912980129811298212983129841298512986129871298812989129901299112992129931299412995129961299712998129991300013001130021300313004130051300613007130081300913010130111301213013130141301513016130171301813019130201302113022130231302413025130261302713028130291303013031130321303313034130351303613037130381303913040130411304213043130441304513046130471304813049130501305113052130531305413055130561305713058130591306013061130621306313064130651306613067130681306913070130711307213073130741307513076130771307813079130801308113082130831308413085130861308713088130891309013091130921309313094130951309613097130981309913100131011310213103131041310513106131071310813109131101311113112131131311413115131161311713118131191312013121131221312313124131251312613127131281312913130131311313213133131341313513136131371313813139131401314113142131431314413145131461314713148131491315013151131521315313154131551315613157131581315913160131611316213163131641316513166131671316813169131701317113172131731317413175131761317713178131791318013181131821318313184131851318613187131881318913190131911319213193131941319513196131971319813199132001320113202132031320413205132061320713208132091321013211132121321313214132151321613217132181321913220132211322213223132241322513226132271322813229132301323113232132331323413235132361323713238132391324013241132421324313244132451324613247132481324913250132511325213253132541325513256132571325813259132601326113262132631326413265132661326713268132691327013271132721327313274132751327613277132781327913280132811328213283132841328513286132871328813289132901329113292132931329413295132961329713298132991330013301133021330313304133051330613307133081330913310133111331213313133141331513316133171331813319133201332113322133231332413325133261332713328133291333013331133321333313334133351333613337133381333913340133411334213343133441334513346133471334813349133501335113352133531335413355133561335713358133591336013361133621336313364133651336613367133681336913370133711337213373133741337513376133771337813379133801338113382133831338413385133861338713388133891339013391133921339313394133951339613397133981339913400134011340213403134041340513406134071340813409134101341113412134131341413415134161341713418134191342013421134221342313424134251342613427134281342913430134311343213433134341343513436134371343813439134401344113442134431344413445134461344713448134491345013451134521345313454134551345613457134581345913460134611346213463134641346513466134671346813469134701347113472134731347413475134761347713478134791348013481134821348313484134851348613487134881348913490134911349213493134941349513496134971349813499135001350113502135031350413505135061350713508135091351013511135121351313514135151351613517135181351913520135211352213523135241352513526135271352813529135301353113532135331353413535135361353713538135391354013541135421354313544135451354613547135481354913550135511355213553135541355513556135571355813559135601356113562135631356413565135661356713568135691357013571135721357313574135751357613577135781357913580135811358213583135841358513586135871358813589135901359113592135931359413595135961359713598135991360013601136021360313604136051360613607136081360913610136111361213613136141361513616136171361813619136201362113622136231362413625136261362713628136291363013631136321363313634136351363613637136381363913640136411364213643136441364513646136471364813649136501365113652136531365413655136561365713658136591366013661136621366313664136651366613667136681366913670136711367213673136741367513676136771367813679136801368113682136831368413685136861368713688136891369013691136921369313694136951369613697136981369913700137011370213703137041370513706137071370813709137101371113712137131371413715137161371713718137191372013721137221372313724137251372613727137281372913730137311373213733137341373513736137371373813739137401374113742137431374413745137461374713748137491375013751137521375313754137551375613757137581375913760137611376213763137641376513766137671376813769137701377113772137731377413775137761377713778137791378013781137821378313784137851378613787137881378913790137911379213793137941379513796137971379813799138001380113802138031380413805138061380713808138091381013811138121381313814138151381613817138181381913820138211382213823138241382513826138271382813829138301383113832138331383413835138361383713838138391384013841138421384313844138451384613847138481384913850138511385213853138541385513856138571385813859138601386113862138631386413865138661386713868138691387013871138721387313874138751387613877138781387913880138811388213883138841388513886138871388813889138901389113892138931389413895138961389713898138991390013901139021390313904139051390613907139081390913910139111391213913139141391513916139171391813919139201392113922139231392413925139261392713928139291393013931139321393313934139351393613937139381393913940139411394213943139441394513946139471394813949139501395113952139531395413955139561395713958139591396013961139621396313964139651396613967139681396913970139711397213973139741397513976139771397813979139801398113982139831398413985139861398713988139891399013991139921399313994139951399613997139981399914000140011400214003140041400514006140071400814009140101401114012140131401414015140161401714018140191402014021140221402314024140251402614027140281402914030140311403214033140341403514036140371403814039140401404114042140431404414045140461404714048140491405014051140521405314054140551405614057140581405914060140611406214063140641406514066140671406814069140701407114072140731407414075140761407714078140791408014081140821408314084140851408614087140881408914090140911409214093140941409514096140971409814099141001410114102141031410414105141061410714108141091411014111141121411314114141151411614117141181411914120141211412214123141241412514126141271412814129141301413114132141331413414135141361413714138141391414014141141421414314144141451414614147141481414914150141511415214153141541415514156141571415814159141601416114162141631416414165141661416714168141691417014171141721417314174141751417614177141781417914180141811418214183141841418514186141871418814189141901419114192141931419414195141961419714198141991420014201142021420314204142051420614207142081420914210142111421214213142141421514216142171421814219142201422114222142231422414225142261422714228142291423014231142321423314234142351423614237142381423914240142411424214243142441424514246142471424814249142501425114252142531425414255142561425714258142591426014261142621426314264142651426614267142681426914270142711427214273142741427514276142771427814279142801428114282142831428414285142861428714288142891429014291142921429314294142951429614297142981429914300143011430214303143041430514306143071430814309143101431114312143131431414315143161431714318143191432014321143221432314324143251432614327143281432914330143311433214333143341433514336143371433814339143401434114342143431434414345143461434714348143491435014351143521435314354143551435614357143581435914360143611436214363143641436514366143671436814369143701437114372143731437414375143761437714378143791438014381143821438314384143851438614387143881438914390143911439214393143941439514396143971439814399144001440114402144031440414405144061440714408144091441014411144121441314414144151441614417144181441914420144211442214423144241442514426144271442814429144301443114432144331443414435144361443714438144391444014441144421444314444144451444614447144481444914450144511445214453144541445514456144571445814459144601446114462144631446414465144661446714468144691447014471144721447314474144751447614477144781447914480144811448214483144841448514486144871448814489144901449114492144931449414495144961449714498144991450014501145021450314504145051450614507145081450914510145111451214513145141451514516145171451814519145201452114522145231452414525145261452714528145291453014531145321453314534145351453614537145381453914540145411454214543145441454514546145471454814549145501455114552145531455414555145561455714558145591456014561145621456314564145651456614567145681456914570145711457214573145741457514576145771457814579145801458114582145831458414585145861458714588145891459014591145921459314594145951459614597145981459914600146011460214603146041460514606146071460814609146101461114612146131461414615146161461714618146191462014621146221462314624146251462614627146281462914630146311463214633146341463514636146371463814639146401464114642146431464414645146461464714648146491465014651146521465314654146551465614657146581465914660146611466214663146641466514666146671466814669146701467114672146731467414675146761467714678146791468014681146821468314684146851468614687146881468914690146911469214693146941469514696146971469814699147001470114702147031470414705147061470714708147091471014711147121471314714147151471614717147181471914720147211472214723147241472514726147271472814729147301473114732147331473414735147361473714738147391474014741147421474314744147451474614747147481474914750147511475214753147541475514756147571475814759147601476114762147631476414765147661476714768147691477014771147721477314774147751477614777147781477914780147811478214783147841478514786147871478814789147901479114792147931479414795147961479714798147991480014801148021480314804148051480614807148081480914810148111481214813148141481514816148171481814819148201482114822148231482414825148261482714828148291483014831148321483314834148351483614837148381483914840148411484214843148441484514846148471484814849148501485114852148531485414855148561485714858148591486014861148621486314864148651486614867148681486914870148711487214873148741487514876148771487814879148801488114882148831488414885148861488714888148891489014891148921489314894148951489614897148981489914900149011490214903149041490514906149071490814909149101491114912149131491414915149161491714918149191492014921149221492314924149251492614927149281492914930149311493214933149341493514936149371493814939149401494114942149431494414945149461494714948149491495014951149521495314954149551495614957149581495914960149611496214963149641496514966149671496814969149701497114972149731497414975149761497714978149791498014981149821498314984149851498614987149881498914990149911499214993149941499514996149971499814999150001500115002150031500415005150061500715008150091501015011150121501315014150151501615017150181501915020150211502215023150241502515026150271502815029150301503115032150331503415035150361503715038150391504015041150421504315044150451504615047150481504915050150511505215053150541505515056150571505815059150601506115062150631506415065150661506715068150691507015071150721507315074150751507615077150781507915080150811508215083150841508515086150871508815089150901509115092150931509415095150961509715098150991510015101151021510315104151051510615107151081510915110151111511215113151141511515116151171511815119151201512115122151231512415125151261512715128151291513015131151321513315134151351513615137151381513915140151411514215143151441514515146151471514815149151501515115152151531515415155151561515715158151591516015161151621516315164151651516615167151681516915170151711517215173151741517515176151771517815179151801518115182151831518415185151861518715188151891519015191151921519315194151951519615197151981519915200152011520215203152041520515206152071520815209152101521115212152131521415215152161521715218152191522015221152221522315224152251522615227152281522915230152311523215233152341523515236152371523815239152401524115242152431524415245152461524715248152491525015251152521525315254152551525615257152581525915260152611526215263152641526515266152671526815269152701527115272152731527415275152761527715278152791528015281152821528315284152851528615287152881528915290152911529215293152941529515296152971529815299153001530115302153031530415305153061530715308153091531015311153121531315314153151531615317153181531915320153211532215323153241532515326153271532815329153301533115332153331533415335153361533715338153391534015341153421534315344153451534615347153481534915350153511535215353153541535515356153571535815359153601536115362153631536415365153661536715368153691537015371153721537315374153751537615377153781537915380153811538215383153841538515386153871538815389153901539115392153931539415395153961539715398153991540015401154021540315404154051540615407154081540915410154111541215413154141541515416154171541815419154201542115422154231542415425154261542715428154291543015431154321543315434154351543615437154381543915440154411544215443154441544515446154471544815449154501545115452154531545415455154561545715458154591546015461154621546315464154651546615467154681546915470154711547215473154741547515476154771547815479154801548115482154831548415485154861548715488154891549015491154921549315494154951549615497154981549915500155011550215503155041550515506155071550815509155101551115512155131551415515155161551715518155191552015521155221552315524155251552615527155281552915530155311553215533155341553515536155371553815539155401554115542155431554415545155461554715548155491555015551155521555315554155551555615557155581555915560155611556215563155641556515566155671556815569155701557115572155731557415575155761557715578155791558015581155821558315584155851558615587155881558915590155911559215593155941559515596155971559815599156001560115602156031560415605156061560715608156091561015611156121561315614156151561615617156181561915620156211562215623156241562515626156271562815629156301563115632156331563415635156361563715638156391564015641156421564315644156451564615647156481564915650156511565215653156541565515656156571565815659156601566115662156631566415665156661566715668156691567015671156721567315674156751567615677156781567915680156811568215683156841568515686156871568815689156901569115692156931569415695156961569715698156991570015701157021570315704157051570615707157081570915710157111571215713157141571515716157171571815719157201572115722157231572415725157261572715728157291573015731157321573315734157351573615737157381573915740157411574215743157441574515746157471574815749157501575115752157531575415755157561575715758157591576015761157621576315764157651576615767157681576915770157711577215773157741577515776157771577815779157801578115782157831578415785157861578715788157891579015791157921579315794157951579615797157981579915800158011580215803158041580515806158071580815809158101581115812158131581415815158161581715818158191582015821158221582315824158251582615827158281582915830158311583215833158341583515836158371583815839158401584115842158431584415845158461584715848158491585015851158521585315854158551585615857158581585915860158611586215863158641586515866158671586815869158701587115872158731587415875158761587715878158791588015881158821588315884158851588615887158881588915890158911589215893158941589515896158971589815899159001590115902159031590415905159061590715908159091591015911159121591315914159151591615917159181591915920159211592215923159241592515926159271592815929159301593115932159331593415935159361593715938159391594015941159421594315944159451594615947159481594915950159511595215953159541595515956159571595815959159601596115962159631596415965159661596715968159691597015971159721597315974159751597615977159781597915980159811598215983159841598515986159871598815989159901599115992159931599415995159961599715998159991600016001160021600316004160051600616007160081600916010160111601216013160141601516016160171601816019160201602116022160231602416025160261602716028160291603016031160321603316034160351603616037160381603916040160411604216043160441604516046160471604816049160501605116052160531605416055160561605716058160591606016061160621606316064160651606616067160681606916070160711607216073160741607516076160771607816079160801608116082160831608416085160861608716088160891609016091160921609316094160951609616097160981609916100161011610216103161041610516106161071610816109161101611116112161131611416115161161611716118161191612016121161221612316124161251612616127161281612916130161311613216133161341613516136161371613816139161401614116142161431614416145161461614716148161491615016151161521615316154161551615616157161581615916160161611616216163161641616516166161671616816169161701617116172161731617416175161761617716178161791618016181161821618316184161851618616187161881618916190161911619216193161941619516196161971619816199162001620116202162031620416205162061620716208162091621016211162121621316214162151621616217162181621916220162211622216223162241622516226162271622816229162301623116232162331623416235162361623716238162391624016241162421624316244162451624616247162481624916250162511625216253162541625516256162571625816259162601626116262162631626416265162661626716268162691627016271162721627316274162751627616277162781627916280162811628216283162841628516286162871628816289162901629116292162931629416295162961629716298162991630016301163021630316304163051630616307163081630916310163111631216313163141631516316163171631816319163201632116322163231632416325163261632716328163291633016331163321633316334163351633616337163381633916340163411634216343163441634516346163471634816349163501635116352163531635416355163561635716358163591636016361163621636316364163651636616367163681636916370163711637216373163741637516376163771637816379163801638116382163831638416385163861638716388163891639016391163921639316394163951639616397163981639916400164011640216403164041640516406164071640816409164101641116412164131641416415164161641716418164191642016421164221642316424164251642616427164281642916430164311643216433164341643516436164371643816439164401644116442164431644416445164461644716448164491645016451164521645316454164551645616457164581645916460164611646216463164641646516466164671646816469164701647116472164731647416475164761647716478164791648016481164821648316484164851648616487164881648916490164911649216493164941649516496164971649816499165001650116502165031650416505165061650716508165091651016511165121651316514165151651616517165181651916520165211652216523165241652516526165271652816529165301653116532165331653416535165361653716538165391654016541165421654316544165451654616547165481654916550165511655216553165541655516556165571655816559165601656116562165631656416565165661656716568165691657016571165721657316574165751657616577165781657916580165811658216583165841658516586165871658816589165901659116592165931659416595165961659716598165991660016601166021660316604166051660616607166081660916610166111661216613166141661516616166171661816619166201662116622166231662416625166261662716628166291663016631166321663316634166351663616637166381663916640166411664216643166441664516646166471664816649166501665116652166531665416655166561665716658166591666016661166621666316664166651666616667166681666916670166711667216673166741667516676166771667816679166801668116682166831668416685166861668716688166891669016691166921669316694166951669616697166981669916700167011670216703167041670516706167071670816709167101671116712167131671416715167161671716718167191672016721167221672316724167251672616727167281672916730167311673216733167341673516736167371673816739167401674116742167431674416745167461674716748167491675016751167521675316754167551675616757167581675916760167611676216763167641676516766167671676816769167701677116772167731677416775167761677716778167791678016781167821678316784167851678616787167881678916790167911679216793167941679516796167971679816799168001680116802168031680416805168061680716808168091681016811168121681316814168151681616817168181681916820168211682216823168241682516826168271682816829168301683116832168331683416835168361683716838168391684016841168421684316844168451684616847168481684916850168511685216853168541685516856168571685816859168601686116862168631686416865168661686716868168691687016871168721687316874168751687616877168781687916880168811688216883168841688516886168871688816889168901689116892168931689416895168961689716898168991690016901169021690316904169051690616907169081690916910169111691216913169141691516916169171691816919169201692116922169231692416925169261692716928169291693016931169321693316934169351693616937169381693916940169411694216943169441694516946169471694816949169501695116952169531695416955169561695716958169591696016961169621696316964169651696616967169681696916970169711697216973169741697516976169771697816979169801698116982169831698416985169861698716988169891699016991169921699316994169951699616997169981699917000170011700217003170041700517006170071700817009170101701117012170131701417015170161701717018170191702017021170221702317024170251702617027170281702917030170311703217033170341703517036170371703817039170401704117042170431704417045170461704717048170491705017051170521705317054170551705617057170581705917060170611706217063170641706517066170671706817069170701707117072170731707417075170761707717078170791708017081170821708317084170851708617087170881708917090170911709217093170941709517096170971709817099171001710117102171031710417105171061710717108171091711017111171121711317114171151711617117171181711917120171211712217123171241712517126171271712817129171301713117132171331713417135171361713717138171391714017141171421714317144171451714617147171481714917150171511715217153171541715517156171571715817159171601716117162171631716417165171661716717168171691717017171171721717317174171751717617177171781717917180171811718217183171841718517186171871718817189171901719117192171931719417195171961719717198171991720017201172021720317204172051720617207172081720917210172111721217213172141721517216172171721817219172201722117222172231722417225172261722717228172291723017231172321723317234172351723617237172381723917240172411724217243172441724517246172471724817249172501725117252172531725417255172561725717258172591726017261172621726317264172651726617267172681726917270172711727217273172741727517276172771727817279172801728117282172831728417285172861728717288172891729017291172921729317294172951729617297172981729917300173011730217303173041730517306173071730817309173101731117312173131731417315173161731717318173191732017321173221732317324173251732617327173281732917330173311733217333173341733517336173371733817339173401734117342173431734417345173461734717348173491735017351173521735317354173551735617357173581735917360173611736217363173641736517366173671736817369173701737117372173731737417375173761737717378173791738017381173821738317384173851738617387173881738917390173911739217393173941739517396173971739817399174001740117402174031740417405174061740717408174091741017411174121741317414174151741617417174181741917420174211742217423174241742517426174271742817429174301743117432174331743417435174361743717438174391744017441174421744317444174451744617447174481744917450174511745217453174541745517456174571745817459174601746117462174631746417465174661746717468174691747017471174721747317474174751747617477174781747917480174811748217483174841748517486174871748817489174901749117492174931749417495174961749717498174991750017501175021750317504175051750617507175081750917510175111751217513175141751517516175171751817519175201752117522175231752417525175261752717528175291753017531175321753317534175351753617537175381753917540175411754217543175441754517546175471754817549175501755117552175531755417555175561755717558175591756017561175621756317564175651756617567175681756917570175711757217573175741757517576175771757817579175801758117582175831758417585175861758717588175891759017591175921759317594175951759617597175981759917600176011760217603176041760517606176071760817609176101761117612176131761417615176161761717618176191762017621176221762317624176251762617627176281762917630176311763217633176341763517636176371763817639176401764117642176431764417645176461764717648176491765017651176521765317654176551765617657176581765917660176611766217663176641766517666176671766817669176701767117672176731767417675176761767717678176791768017681176821768317684176851768617687176881768917690176911769217693176941769517696176971769817699177001770117702177031770417705177061770717708177091771017711177121771317714177151771617717177181771917720177211772217723177241772517726177271772817729177301773117732177331773417735177361773717738177391774017741177421774317744177451774617747177481774917750177511775217753177541775517756177571775817759177601776117762177631776417765177661776717768177691777017771177721777317774177751777617777177781777917780177811778217783177841778517786177871778817789177901779117792177931779417795177961779717798177991780017801178021780317804178051780617807178081780917810178111781217813178141781517816178171781817819178201782117822178231782417825178261782717828178291783017831178321783317834178351783617837178381783917840178411784217843178441784517846178471784817849178501785117852178531785417855178561785717858178591786017861178621786317864178651786617867178681786917870178711787217873178741787517876178771787817879178801788117882178831788417885178861788717888178891789017891178921789317894178951789617897178981789917900179011790217903179041790517906179071790817909179101791117912179131791417915179161791717918179191792017921179221792317924179251792617927179281792917930179311793217933179341793517936179371793817939179401794117942179431794417945179461794717948179491795017951179521795317954179551795617957179581795917960179611796217963179641796517966179671796817969179701797117972179731797417975179761797717978179791798017981179821798317984179851798617987179881798917990179911799217993179941799517996179971799817999180001800118002180031800418005180061800718008180091801018011180121801318014180151801618017180181801918020180211802218023180241802518026180271802818029180301803118032180331803418035180361803718038180391804018041180421804318044180451804618047180481804918050180511805218053180541805518056180571805818059180601806118062180631806418065180661806718068180691807018071180721807318074180751807618077180781807918080180811808218083180841808518086180871808818089180901809118092180931809418095180961809718098180991810018101181021810318104181051810618107181081810918110181111811218113181141811518116181171811818119181201812118122181231812418125181261812718128181291813018131181321813318134181351813618137181381813918140181411814218143181441814518146181471814818149181501815118152181531815418155181561815718158181591816018161181621816318164181651816618167181681816918170181711817218173181741817518176181771817818179181801818118182181831818418185181861818718188181891819018191181921819318194181951819618197181981819918200182011820218203182041820518206182071820818209182101821118212182131821418215182161821718218182191822018221182221822318224182251822618227182281822918230182311823218233182341823518236182371823818239182401824118242182431824418245182461824718248182491825018251182521825318254182551825618257182581825918260182611826218263182641826518266182671826818269182701827118272182731827418275182761827718278182791828018281182821828318284182851828618287182881828918290182911829218293182941829518296182971829818299183001830118302183031830418305183061830718308183091831018311183121831318314183151831618317183181831918320183211832218323183241832518326183271832818329183301833118332183331833418335183361833718338183391834018341183421834318344183451834618347183481834918350183511835218353183541835518356183571835818359183601836118362183631836418365183661836718368183691837018371183721837318374183751837618377183781837918380183811838218383183841838518386183871838818389183901839118392183931839418395183961839718398183991840018401184021840318404184051840618407184081840918410184111841218413184141841518416184171841818419184201842118422184231842418425184261842718428184291843018431184321843318434184351843618437184381843918440184411844218443184441844518446184471844818449184501845118452184531845418455184561845718458184591846018461184621846318464184651846618467184681846918470184711847218473184741847518476184771847818479184801848118482184831848418485184861848718488184891849018491184921849318494184951849618497184981849918500185011850218503185041850518506185071850818509185101851118512185131851418515185161851718518185191852018521185221852318524185251852618527185281852918530185311853218533185341853518536185371853818539185401854118542185431854418545185461854718548185491855018551185521855318554185551855618557185581855918560185611856218563185641856518566185671856818569185701857118572185731857418575185761857718578185791858018581185821858318584185851858618587185881858918590185911859218593185941859518596185971859818599186001860118602186031860418605186061860718608186091861018611186121861318614186151861618617186181861918620186211862218623186241862518626186271862818629186301863118632186331863418635186361863718638186391864018641186421864318644186451864618647186481864918650186511865218653186541865518656186571865818659186601866118662186631866418665186661866718668186691867018671186721867318674186751867618677186781867918680186811868218683186841868518686186871868818689186901869118692186931869418695186961869718698186991870018701187021870318704187051870618707187081870918710187111871218713187141871518716187171871818719187201872118722187231872418725187261872718728187291873018731187321873318734187351873618737187381873918740187411874218743187441874518746187471874818749187501875118752187531875418755187561875718758187591876018761187621876318764187651876618767187681876918770187711877218773187741877518776187771877818779187801878118782187831878418785187861878718788187891879018791187921879318794187951879618797187981879918800188011880218803188041880518806188071880818809188101881118812188131881418815188161881718818188191882018821188221882318824188251882618827188281882918830188311883218833188341883518836188371883818839188401884118842188431884418845188461884718848188491885018851188521885318854188551885618857188581885918860188611886218863188641886518866188671886818869188701887118872188731887418875188761887718878188791888018881188821888318884188851888618887188881888918890188911889218893188941889518896188971889818899189001890118902189031890418905189061890718908189091891018911189121891318914189151891618917189181891918920189211892218923189241892518926189271892818929189301893118932189331893418935189361893718938189391894018941189421894318944189451894618947189481894918950189511895218953189541895518956189571895818959189601896118962189631896418965189661896718968189691897018971189721897318974189751897618977189781897918980189811898218983189841898518986189871898818989189901899118992189931899418995189961899718998189991900019001190021900319004190051900619007190081900919010190111901219013190141901519016190171901819019190201902119022190231902419025190261902719028190291903019031190321903319034190351903619037190381903919040190411904219043190441904519046190471904819049190501905119052190531905419055190561905719058190591906019061190621906319064190651906619067190681906919070190711907219073190741907519076190771907819079190801908119082190831908419085190861908719088190891909019091190921909319094190951909619097190981909919100191011910219103191041910519106191071910819109191101911119112191131911419115191161911719118191191912019121191221912319124191251912619127191281912919130191311913219133191341913519136191371913819139191401914119142191431914419145191461914719148191491915019151191521915319154191551915619157191581915919160191611916219163191641916519166191671916819169191701917119172191731917419175191761917719178191791918019181191821918319184191851918619187191881918919190191911919219193191941919519196191971919819199192001920119202192031920419205192061920719208192091921019211192121921319214192151921619217192181921919220192211922219223192241922519226192271922819229192301923119232192331923419235192361923719238192391924019241192421924319244192451924619247192481924919250192511925219253192541925519256192571925819259192601926119262192631926419265192661926719268192691927019271192721927319274192751927619277192781927919280192811928219283192841928519286192871928819289192901929119292192931929419295192961929719298192991930019301193021930319304193051930619307193081930919310193111931219313193141931519316193171931819319193201932119322193231932419325193261932719328193291933019331193321933319334193351933619337193381933919340193411934219343193441934519346193471934819349193501935119352193531935419355193561935719358193591936019361193621936319364193651936619367193681936919370193711937219373193741937519376193771937819379193801938119382193831938419385193861938719388193891939019391193921939319394193951939619397193981939919400194011940219403194041940519406194071940819409194101941119412194131941419415194161941719418194191942019421194221942319424194251942619427194281942919430194311943219433194341943519436194371943819439194401944119442194431944419445194461944719448194491945019451194521945319454194551945619457194581945919460194611946219463194641946519466194671946819469194701947119472194731947419475194761947719478194791948019481194821948319484194851948619487194881948919490194911949219493194941949519496194971949819499195001950119502195031950419505195061950719508195091951019511195121951319514195151951619517195181951919520195211952219523195241952519526195271952819529195301953119532195331953419535195361953719538195391954019541195421954319544195451954619547195481954919550195511955219553195541955519556195571955819559195601956119562195631956419565195661956719568195691957019571195721957319574195751957619577195781957919580195811958219583195841958519586195871958819589195901959119592195931959419595195961959719598195991960019601196021960319604196051960619607196081960919610196111961219613196141961519616196171961819619196201962119622196231962419625196261962719628196291963019631196321963319634196351963619637196381963919640196411964219643196441964519646196471964819649196501965119652196531965419655196561965719658196591966019661196621966319664196651966619667196681966919670196711967219673196741967519676196771967819679196801968119682196831968419685196861968719688196891969019691196921969319694196951969619697196981969919700197011970219703197041970519706197071970819709197101971119712197131971419715197161971719718197191972019721197221972319724197251972619727197281972919730197311973219733197341973519736197371973819739197401974119742197431974419745197461974719748197491975019751197521975319754197551975619757197581975919760197611976219763197641976519766197671976819769197701977119772197731977419775197761977719778197791978019781197821978319784197851978619787197881978919790197911979219793197941979519796197971979819799198001980119802198031980419805198061980719808198091981019811198121981319814198151981619817198181981919820198211982219823198241982519826198271982819829198301983119832198331983419835198361983719838198391984019841198421984319844198451984619847198481984919850198511985219853198541985519856198571985819859198601986119862198631986419865198661986719868198691987019871198721987319874198751987619877198781987919880198811988219883198841988519886198871988819889198901989119892198931989419895198961989719898198991990019901199021990319904199051990619907199081990919910199111991219913199141991519916199171991819919199201992119922199231992419925199261992719928199291993019931199321993319934199351993619937199381993919940199411994219943199441994519946199471994819949199501995119952199531995419955199561995719958199591996019961199621996319964199651996619967199681996919970199711997219973199741997519976199771997819979199801998119982199831998419985199861998719988199891999019991199921999319994199951999619997199981999920000200012000220003200042000520006200072000820009200102001120012200132001420015200162001720018200192002020021200222002320024200252002620027200282002920030200312003220033200342003520036200372003820039200402004120042200432004420045200462004720048200492005020051200522005320054200552005620057200582005920060200612006220063200642006520066200672006820069200702007120072200732007420075200762007720078200792008020081200822008320084200852008620087200882008920090200912009220093200942009520096200972009820099201002010120102201032010420105201062010720108201092011020111201122011320114201152011620117201182011920120201212012220123201242012520126201272012820129201302013120132201332013420135201362013720138201392014020141201422014320144201452014620147201482014920150201512015220153201542015520156201572015820159201602016120162201632016420165201662016720168201692017020171201722017320174201752017620177201782017920180201812018220183201842018520186201872018820189201902019120192201932019420195201962019720198201992020020201202022020320204202052020620207202082020920210202112021220213202142021520216202172021820219202202022120222202232022420225202262022720228202292023020231202322023320234202352023620237202382023920240202412024220243202442024520246202472024820249202502025120252202532025420255202562025720258202592026020261202622026320264202652026620267202682026920270202712027220273202742027520276202772027820279202802028120282202832028420285202862028720288202892029020291202922029320294202952029620297202982029920300203012030220303203042030520306203072030820309203102031120312203132031420315203162031720318203192032020321203222032320324203252032620327203282032920330203312033220333203342033520336203372033820339203402034120342203432034420345203462034720348203492035020351203522035320354203552035620357203582035920360203612036220363203642036520366203672036820369203702037120372203732037420375203762037720378203792038020381203822038320384203852038620387203882038920390203912039220393203942039520396203972039820399204002040120402204032040420405204062040720408204092041020411204122041320414204152041620417204182041920420204212042220423204242042520426204272042820429204302043120432204332043420435204362043720438204392044020441204422044320444204452044620447204482044920450204512045220453204542045520456204572045820459204602046120462204632046420465204662046720468204692047020471204722047320474204752047620477204782047920480204812048220483204842048520486204872048820489204902049120492204932049420495204962049720498204992050020501205022050320504205052050620507205082050920510205112051220513205142051520516205172051820519205202052120522205232052420525205262052720528205292053020531205322053320534205352053620537205382053920540205412054220543205442054520546205472054820549205502055120552205532055420555205562055720558205592056020561205622056320564205652056620567205682056920570205712057220573205742057520576205772057820579205802058120582205832058420585205862058720588205892059020591205922059320594205952059620597205982059920600206012060220603206042060520606206072060820609206102061120612206132061420615206162061720618206192062020621206222062320624206252062620627206282062920630206312063220633206342063520636206372063820639206402064120642206432064420645206462064720648206492065020651206522065320654206552065620657206582065920660206612066220663206642066520666206672066820669206702067120672206732067420675206762067720678206792068020681206822068320684206852068620687206882068920690206912069220693206942069520696206972069820699207002070120702207032070420705207062070720708207092071020711207122071320714207152071620717207182071920720207212072220723207242072520726207272072820729207302073120732207332073420735207362073720738207392074020741207422074320744207452074620747207482074920750207512075220753207542075520756207572075820759207602076120762207632076420765207662076720768207692077020771207722077320774207752077620777207782077920780207812078220783207842078520786207872078820789207902079120792207932079420795207962079720798207992080020801208022080320804208052080620807208082080920810208112081220813208142081520816208172081820819208202082120822208232082420825208262082720828208292083020831208322083320834208352083620837208382083920840208412084220843208442084520846208472084820849208502085120852208532085420855208562085720858208592086020861208622086320864208652086620867208682086920870208712087220873208742087520876208772087820879208802088120882208832088420885208862088720888208892089020891208922089320894208952089620897208982089920900209012090220903209042090520906209072090820909209102091120912209132091420915209162091720918209192092020921209222092320924209252092620927209282092920930209312093220933209342093520936209372093820939209402094120942209432094420945209462094720948209492095020951209522095320954209552095620957209582095920960209612096220963209642096520966209672096820969209702097120972209732097420975209762097720978209792098020981209822098320984209852098620987209882098920990209912099220993209942099520996209972099820999210002100121002210032100421005210062100721008210092101021011210122101321014210152101621017210182101921020210212102221023210242102521026210272102821029210302103121032210332103421035210362103721038210392104021041210422104321044210452104621047210482104921050210512105221053210542105521056210572105821059210602106121062210632106421065210662106721068210692107021071210722107321074210752107621077210782107921080210812108221083210842108521086210872108821089210902109121092210932109421095210962109721098210992110021101211022110321104211052110621107211082110921110211112111221113211142111521116211172111821119211202112121122211232112421125211262112721128211292113021131211322113321134211352113621137211382113921140211412114221143211442114521146211472114821149211502115121152211532115421155211562115721158211592116021161211622116321164211652116621167211682116921170211712117221173211742117521176211772117821179211802118121182211832118421185211862118721188211892119021191211922119321194211952119621197211982119921200212012120221203212042120521206212072120821209212102121121212212132121421215212162121721218212192122021221212222122321224212252122621227212282122921230212312123221233212342123521236212372123821239212402124121242212432124421245212462124721248212492125021251212522125321254212552125621257212582125921260212612126221263212642126521266212672126821269212702127121272212732127421275212762127721278212792128021281212822128321284212852128621287212882128921290212912129221293212942129521296212972129821299213002130121302213032130421305213062130721308213092131021311213122131321314213152131621317213182131921320213212132221323213242132521326213272132821329213302133121332213332133421335213362133721338213392134021341213422134321344213452134621347213482134921350213512135221353213542135521356213572135821359213602136121362213632136421365213662136721368213692137021371213722137321374213752137621377213782137921380213812138221383213842138521386213872138821389213902139121392213932139421395213962139721398213992140021401214022140321404214052140621407214082140921410214112141221413214142141521416214172141821419214202142121422214232142421425214262142721428214292143021431214322143321434214352143621437214382143921440214412144221443214442144521446214472144821449214502145121452214532145421455214562145721458214592146021461214622146321464214652146621467214682146921470214712147221473214742147521476214772147821479214802148121482214832148421485214862148721488214892149021491214922149321494214952149621497214982149921500215012150221503215042150521506215072150821509215102151121512215132151421515215162151721518215192152021521215222152321524215252152621527215282152921530215312153221533215342153521536215372153821539215402154121542215432154421545215462154721548215492155021551215522155321554215552155621557215582155921560215612156221563215642156521566215672156821569215702157121572215732157421575215762157721578215792158021581215822158321584215852158621587215882158921590215912159221593215942159521596215972159821599216002160121602216032160421605216062160721608216092161021611216122161321614216152161621617216182161921620216212162221623216242162521626216272162821629216302163121632216332163421635216362163721638216392164021641216422164321644216452164621647216482164921650216512165221653216542165521656216572165821659216602166121662216632166421665216662166721668216692167021671216722167321674216752167621677216782167921680216812168221683216842168521686216872168821689216902169121692216932169421695216962169721698216992170021701217022170321704217052170621707217082170921710217112171221713217142171521716217172171821719217202172121722217232172421725217262172721728217292173021731217322173321734217352173621737217382173921740217412174221743217442174521746217472174821749217502175121752217532175421755217562175721758217592176021761217622176321764217652176621767217682176921770217712177221773217742177521776217772177821779217802178121782217832178421785217862178721788217892179021791217922179321794217952179621797217982179921800218012180221803218042180521806218072180821809218102181121812218132181421815218162181721818218192182021821218222182321824218252182621827218282182921830218312183221833218342183521836218372183821839218402184121842218432184421845218462184721848218492185021851218522185321854218552185621857218582185921860218612186221863218642186521866218672186821869218702187121872218732187421875218762187721878218792188021881218822188321884218852188621887218882188921890218912189221893218942189521896218972189821899219002190121902219032190421905219062190721908219092191021911219122191321914219152191621917219182191921920219212192221923219242192521926219272192821929219302193121932219332193421935219362193721938219392194021941219422194321944219452194621947219482194921950219512195221953219542195521956219572195821959219602196121962219632196421965219662196721968219692197021971219722197321974219752197621977219782197921980219812198221983219842198521986219872198821989219902199121992219932199421995219962199721998219992200022001220022200322004220052200622007220082200922010220112201222013220142201522016220172201822019220202202122022220232202422025220262202722028220292203022031220322203322034220352203622037220382203922040220412204222043220442204522046220472204822049220502205122052220532205422055220562205722058220592206022061220622206322064220652206622067220682206922070220712207222073220742207522076220772207822079220802208122082220832208422085220862208722088220892209022091220922209322094220952209622097220982209922100221012210222103221042210522106221072210822109221102211122112221132211422115221162211722118221192212022121221222212322124221252212622127221282212922130221312213222133221342213522136221372213822139221402214122142221432214422145221462214722148221492215022151221522215322154221552215622157221582215922160221612216222163221642216522166221672216822169221702217122172221732217422175221762217722178221792218022181221822218322184221852218622187221882218922190221912219222193221942219522196221972219822199222002220122202222032220422205222062220722208222092221022211222122221322214222152221622217222182221922220222212222222223222242222522226222272222822229222302223122232222332223422235222362223722238222392224022241222422224322244222452224622247222482224922250222512225222253222542225522256222572225822259222602226122262222632226422265222662226722268222692227022271222722227322274222752227622277222782227922280222812228222283222842228522286222872228822289222902229122292222932229422295222962229722298222992230022301223022230322304223052230622307223082230922310223112231222313223142231522316223172231822319223202232122322223232232422325223262232722328223292233022331223322233322334223352233622337223382233922340223412234222343223442234522346223472234822349223502235122352223532235422355223562235722358223592236022361223622236322364223652236622367223682236922370223712237222373223742237522376223772237822379223802238122382223832238422385223862238722388223892239022391223922239322394223952239622397223982239922400224012240222403224042240522406224072240822409224102241122412224132241422415224162241722418224192242022421224222242322424224252242622427224282242922430224312243222433224342243522436224372243822439224402244122442224432244422445224462244722448224492245022451224522245322454224552245622457224582245922460224612246222463224642246522466224672246822469224702247122472224732247422475224762247722478224792248022481224822248322484224852248622487224882248922490224912249222493224942249522496224972249822499225002250122502225032250422505225062250722508225092251022511225122251322514225152251622517225182251922520225212252222523225242252522526225272252822529225302253122532225332253422535225362253722538225392254022541225422254322544225452254622547225482254922550225512255222553225542255522556225572255822559225602256122562225632256422565225662256722568225692257022571225722257322574225752257622577225782257922580225812258222583225842258522586225872258822589225902259122592225932259422595225962259722598225992260022601226022260322604226052260622607226082260922610226112261222613226142261522616226172261822619226202262122622226232262422625226262262722628226292263022631226322263322634226352263622637226382263922640226412264222643226442264522646226472264822649226502265122652226532265422655226562265722658226592266022661226622266322664226652266622667226682266922670226712267222673226742267522676226772267822679226802268122682226832268422685226862268722688226892269022691226922269322694226952269622697226982269922700227012270222703227042270522706227072270822709227102271122712227132271422715227162271722718227192272022721227222272322724227252272622727227282272922730227312273222733227342273522736227372273822739227402274122742227432274422745227462274722748227492275022751227522275322754227552275622757227582275922760227612276222763227642276522766227672276822769227702277122772227732277422775227762277722778227792278022781227822278322784227852278622787227882278922790227912279222793227942279522796227972279822799228002280122802228032280422805228062280722808228092281022811228122281322814228152281622817228182281922820228212282222823228242282522826228272282822829228302283122832228332283422835228362283722838228392284022841228422284322844228452284622847228482284922850228512285222853228542285522856228572285822859228602286122862228632286422865228662286722868228692287022871228722287322874228752287622877228782287922880228812288222883228842288522886228872288822889228902289122892228932289422895228962289722898228992290022901229022290322904229052290622907229082290922910229112291222913229142291522916229172291822919229202292122922229232292422925229262292722928229292293022931229322293322934229352293622937229382293922940229412294222943229442294522946229472294822949229502295122952229532295422955229562295722958229592296022961229622296322964229652296622967229682296922970229712297222973229742297522976229772297822979229802298122982229832298422985229862298722988229892299022991229922299322994229952299622997229982299923000230012300223003230042300523006230072300823009230102301123012230132301423015230162301723018230192302023021230222302323024230252302623027230282302923030230312303223033230342303523036230372303823039230402304123042230432304423045230462304723048230492305023051230522305323054230552305623057230582305923060230612306223063230642306523066230672306823069230702307123072230732307423075230762307723078230792308023081230822308323084230852308623087230882308923090230912309223093230942309523096230972309823099231002310123102231032310423105231062310723108231092311023111231122311323114231152311623117231182311923120231212312223123231242312523126231272312823129231302313123132231332313423135231362313723138231392314023141231422314323144231452314623147231482314923150231512315223153231542315523156231572315823159231602316123162231632316423165231662316723168231692317023171231722317323174231752317623177231782317923180231812318223183231842318523186231872318823189231902319123192231932319423195231962319723198231992320023201232022320323204232052320623207232082320923210232112321223213232142321523216232172321823219232202322123222232232322423225232262322723228232292323023231232322323323234232352323623237232382323923240232412324223243232442324523246232472324823249232502325123252232532325423255232562325723258232592326023261232622326323264232652326623267232682326923270232712327223273232742327523276232772327823279232802328123282232832328423285232862328723288232892329023291232922329323294232952329623297232982329923300233012330223303233042330523306233072330823309233102331123312233132331423315233162331723318233192332023321233222332323324233252332623327233282332923330233312333223333233342333523336233372333823339233402334123342233432334423345233462334723348233492335023351233522335323354233552335623357233582335923360233612336223363233642336523366233672336823369233702337123372233732337423375233762337723378233792338023381233822338323384233852338623387233882338923390233912339223393233942339523396233972339823399234002340123402234032340423405234062340723408234092341023411234122341323414234152341623417234182341923420234212342223423234242342523426234272342823429234302343123432234332343423435234362343723438234392344023441234422344323444234452344623447234482344923450234512345223453234542345523456234572345823459234602346123462234632346423465234662346723468234692347023471234722347323474234752347623477234782347923480234812348223483234842348523486234872348823489234902349123492234932349423495234962349723498234992350023501235022350323504235052350623507235082350923510235112351223513235142351523516235172351823519235202352123522235232352423525235262352723528235292353023531235322353323534235352353623537235382353923540235412354223543235442354523546235472354823549235502355123552235532355423555235562355723558235592356023561235622356323564235652356623567235682356923570235712357223573235742357523576235772357823579235802358123582235832358423585235862358723588235892359023591235922359323594235952359623597235982359923600236012360223603236042360523606236072360823609236102361123612236132361423615236162361723618236192362023621236222362323624236252362623627236282362923630236312363223633236342363523636236372363823639236402364123642236432364423645236462364723648236492365023651236522365323654236552365623657236582365923660236612366223663236642366523666236672366823669236702367123672236732367423675236762367723678236792368023681236822368323684236852368623687236882368923690236912369223693236942369523696236972369823699237002370123702237032370423705237062370723708237092371023711237122371323714237152371623717237182371923720237212372223723237242372523726237272372823729237302373123732237332373423735237362373723738237392374023741237422374323744237452374623747237482374923750237512375223753237542375523756237572375823759237602376123762237632376423765237662376723768237692377023771237722377323774237752377623777237782377923780237812378223783237842378523786237872378823789237902379123792237932379423795237962379723798237992380023801238022380323804238052380623807238082380923810238112381223813238142381523816238172381823819238202382123822238232382423825238262382723828238292383023831238322383323834238352383623837238382383923840238412384223843238442384523846238472384823849238502385123852238532385423855238562385723858238592386023861238622386323864238652386623867238682386923870238712387223873238742387523876238772387823879238802388123882238832388423885238862388723888238892389023891238922389323894238952389623897238982389923900239012390223903239042390523906239072390823909239102391123912239132391423915239162391723918239192392023921239222392323924239252392623927239282392923930239312393223933239342393523936239372393823939239402394123942239432394423945239462394723948239492395023951239522395323954239552395623957239582395923960239612396223963239642396523966239672396823969239702397123972239732397423975239762397723978239792398023981239822398323984239852398623987239882398923990239912399223993239942399523996239972399823999240002400124002240032400424005240062400724008240092401024011240122401324014240152401624017240182401924020240212402224023240242402524026240272402824029240302403124032240332403424035240362403724038240392404024041240422404324044240452404624047240482404924050240512405224053240542405524056240572405824059240602406124062240632406424065240662406724068240692407024071240722407324074240752407624077240782407924080240812408224083240842408524086240872408824089240902409124092240932409424095240962409724098240992410024101241022410324104241052410624107241082410924110241112411224113241142411524116241172411824119241202412124122241232412424125241262412724128241292413024131241322413324134241352413624137241382413924140241412414224143241442414524146241472414824149241502415124152241532415424155241562415724158241592416024161241622416324164241652416624167241682416924170241712417224173241742417524176241772417824179241802418124182241832418424185241862418724188241892419024191241922419324194241952419624197241982419924200242012420224203242042420524206242072420824209242102421124212242132421424215242162421724218242192422024221242222422324224242252422624227242282422924230242312423224233242342423524236242372423824239242402424124242242432424424245242462424724248242492425024251242522425324254242552425624257242582425924260242612426224263242642426524266242672426824269242702427124272242732427424275242762427724278242792428024281242822428324284242852428624287242882428924290242912429224293242942429524296242972429824299243002430124302243032430424305243062430724308243092431024311243122431324314243152431624317243182431924320243212432224323243242432524326243272432824329243302433124332243332433424335243362433724338243392434024341243422434324344243452434624347243482434924350243512435224353243542435524356243572435824359243602436124362243632436424365243662436724368243692437024371243722437324374243752437624377243782437924380243812438224383243842438524386243872438824389243902439124392243932439424395243962439724398243992440024401244022440324404244052440624407244082440924410244112441224413244142441524416244172441824419244202442124422244232442424425244262442724428244292443024431244322443324434244352443624437244382443924440244412444224443244442444524446244472444824449244502445124452244532445424455244562445724458244592446024461244622446324464244652446624467244682446924470244712447224473244742447524476244772447824479244802448124482244832448424485244862448724488244892449024491244922449324494244952449624497244982449924500245012450224503245042450524506245072450824509245102451124512245132451424515245162451724518245192452024521245222452324524245252452624527245282452924530245312453224533245342453524536245372453824539245402454124542245432454424545245462454724548245492455024551245522455324554245552455624557245582455924560245612456224563245642456524566245672456824569245702457124572245732457424575245762457724578245792458024581245822458324584245852458624587245882458924590245912459224593245942459524596245972459824599246002460124602246032460424605246062460724608246092461024611246122461324614246152461624617246182461924620246212462224623246242462524626246272462824629246302463124632246332463424635246362463724638246392464024641246422464324644246452464624647246482464924650246512465224653246542465524656246572465824659246602466124662246632466424665246662466724668246692467024671246722467324674246752467624677246782467924680246812468224683246842468524686246872468824689246902469124692246932469424695246962469724698246992470024701247022470324704247052470624707247082470924710247112471224713247142471524716247172471824719247202472124722247232472424725247262472724728247292473024731247322473324734247352473624737247382473924740247412474224743247442474524746247472474824749247502475124752247532475424755247562475724758247592476024761247622476324764247652476624767247682476924770247712477224773247742477524776247772477824779247802478124782247832478424785247862478724788247892479024791247922479324794247952479624797247982479924800248012480224803248042480524806248072480824809248102481124812248132481424815248162481724818248192482024821248222482324824248252482624827248282482924830248312483224833248342483524836248372483824839248402484124842248432484424845248462484724848248492485024851248522485324854248552485624857248582485924860248612486224863248642486524866248672486824869248702487124872248732487424875248762487724878248792488024881248822488324884248852488624887248882488924890248912489224893248942489524896248972489824899249002490124902249032490424905249062490724908249092491024911249122491324914249152491624917249182491924920249212492224923249242492524926249272492824929249302493124932249332493424935249362493724938249392494024941249422494324944249452494624947249482494924950249512495224953249542495524956249572495824959249602496124962249632496424965249662496724968249692497024971249722497324974249752497624977249782497924980249812498224983249842498524986249872498824989249902499124992249932499424995249962499724998249992500025001250022500325004250052500625007250082500925010250112501225013250142501525016250172501825019250202502125022250232502425025250262502725028250292503025031250322503325034250352503625037250382503925040250412504225043250442504525046250472504825049250502505125052250532505425055250562505725058250592506025061250622506325064250652506625067250682506925070250712507225073250742507525076250772507825079250802508125082250832508425085250862508725088250892509025091250922509325094250952509625097250982509925100251012510225103251042510525106251072510825109251102511125112251132511425115251162511725118251192512025121251222512325124251252512625127251282512925130251312513225133251342513525136251372513825139251402514125142251432514425145251462514725148251492515025151251522515325154251552515625157251582515925160251612516225163251642516525166251672516825169251702517125172251732517425175251762517725178251792518025181251822518325184251852518625187251882518925190251912519225193251942519525196251972519825199252002520125202252032520425205252062520725208252092521025211252122521325214252152521625217252182521925220252212522225223252242522525226252272522825229252302523125232252332523425235252362523725238252392524025241252422524325244252452524625247252482524925250252512525225253252542525525256252572525825259252602526125262252632526425265252662526725268252692527025271252722527325274252752527625277252782527925280252812528225283252842528525286252872528825289252902529125292252932529425295252962529725298252992530025301253022530325304253052530625307253082530925310253112531225313253142531525316253172531825319253202532125322253232532425325253262532725328253292533025331253322533325334253352533625337253382533925340253412534225343253442534525346253472534825349253502535125352253532535425355253562535725358253592536025361253622536325364253652536625367253682536925370253712537225373253742537525376253772537825379253802538125382253832538425385253862538725388253892539025391253922539325394253952539625397253982539925400254012540225403254042540525406254072540825409254102541125412254132541425415254162541725418254192542025421254222542325424254252542625427254282542925430254312543225433254342543525436254372543825439254402544125442254432544425445254462544725448254492545025451254522545325454254552545625457254582545925460254612546225463254642546525466254672546825469254702547125472254732547425475254762547725478254792548025481254822548325484254852548625487254882548925490254912549225493254942549525496254972549825499255002550125502255032550425505255062550725508255092551025511255122551325514255152551625517255182551925520255212552225523255242552525526255272552825529255302553125532255332553425535255362553725538255392554025541255422554325544255452554625547255482554925550255512555225553255542555525556255572555825559255602556125562255632556425565255662556725568255692557025571255722557325574255752557625577255782557925580255812558225583255842558525586255872558825589255902559125592255932559425595255962559725598255992560025601256022560325604256052560625607256082560925610256112561225613256142561525616256172561825619256202562125622256232562425625256262562725628256292563025631256322563325634256352563625637256382563925640256412564225643256442564525646256472564825649256502565125652256532565425655256562565725658256592566025661256622566325664256652566625667256682566925670256712567225673256742567525676256772567825679256802568125682256832568425685256862568725688256892569025691256922569325694256952569625697256982569925700257012570225703257042570525706257072570825709257102571125712257132571425715257162571725718257192572025721257222572325724257252572625727257282572925730257312573225733257342573525736257372573825739257402574125742257432574425745257462574725748257492575025751257522575325754257552575625757257582575925760257612576225763257642576525766257672576825769257702577125772257732577425775257762577725778257792578025781257822578325784257852578625787257882578925790257912579225793257942579525796257972579825799258002580125802258032580425805258062580725808258092581025811258122581325814258152581625817258182581925820258212582225823258242582525826258272582825829258302583125832258332583425835258362583725838258392584025841258422584325844258452584625847258482584925850258512585225853258542585525856258572585825859258602586125862258632586425865258662586725868258692587025871258722587325874258752587625877258782587925880258812588225883258842588525886258872588825889258902589125892258932589425895258962589725898258992590025901259022590325904259052590625907259082590925910259112591225913259142591525916259172591825919259202592125922259232592425925259262592725928259292593025931259322593325934259352593625937259382593925940259412594225943259442594525946259472594825949259502595125952259532595425955259562595725958259592596025961259622596325964259652596625967259682596925970259712597225973259742597525976259772597825979259802598125982259832598425985259862598725988259892599025991259922599325994259952599625997259982599926000260012600226003260042600526006260072600826009260102601126012260132601426015260162601726018260192602026021260222602326024260252602626027260282602926030260312603226033260342603526036260372603826039260402604126042260432604426045260462604726048260492605026051260522605326054260552605626057260582605926060260612606226063260642606526066260672606826069260702607126072260732607426075260762607726078260792608026081260822608326084260852608626087260882608926090260912609226093260942609526096260972609826099261002610126102261032610426105261062610726108261092611026111261122611326114261152611626117261182611926120261212612226123261242612526126261272612826129261302613126132261332613426135261362613726138261392614026141261422614326144261452614626147261482614926150261512615226153261542615526156261572615826159261602616126162261632616426165261662616726168261692617026171261722617326174261752617626177261782617926180261812618226183261842618526186261872618826189261902619126192261932619426195261962619726198261992620026201262022620326204262052620626207262082620926210262112621226213262142621526216262172621826219262202622126222262232622426225262262622726228262292623026231262322623326234262352623626237262382623926240262412624226243262442624526246262472624826249262502625126252262532625426255262562625726258262592626026261262622626326264262652626626267262682626926270262712627226273262742627526276262772627826279262802628126282262832628426285262862628726288262892629026291262922629326294262952629626297262982629926300263012630226303263042630526306263072630826309263102631126312263132631426315263162631726318263192632026321263222632326324263252632626327263282632926330263312633226333263342633526336263372633826339263402634126342263432634426345263462634726348263492635026351263522635326354263552635626357263582635926360263612636226363263642636526366263672636826369263702637126372263732637426375263762637726378263792638026381263822638326384263852638626387263882638926390263912639226393263942639526396263972639826399264002640126402264032640426405264062640726408264092641026411264122641326414264152641626417264182641926420264212642226423264242642526426264272642826429264302643126432264332643426435264362643726438264392644026441264422644326444264452644626447264482644926450264512645226453264542645526456264572645826459264602646126462264632646426465264662646726468264692647026471264722647326474264752647626477264782647926480264812648226483264842648526486264872648826489264902649126492264932649426495264962649726498264992650026501265022650326504265052650626507265082650926510265112651226513265142651526516265172651826519265202652126522265232652426525265262652726528265292653026531265322653326534265352653626537265382653926540265412654226543265442654526546265472654826549265502655126552265532655426555265562655726558265592656026561265622656326564265652656626567265682656926570265712657226573265742657526576265772657826579265802658126582265832658426585265862658726588265892659026591265922659326594265952659626597265982659926600266012660226603266042660526606266072660826609266102661126612266132661426615266162661726618266192662026621266222662326624266252662626627266282662926630266312663226633266342663526636266372663826639266402664126642266432664426645266462664726648266492665026651266522665326654266552665626657266582665926660266612666226663266642666526666266672666826669266702667126672266732667426675266762667726678266792668026681266822668326684266852668626687266882668926690266912669226693266942669526696266972669826699267002670126702267032670426705267062670726708267092671026711267122671326714267152671626717267182671926720267212672226723267242672526726267272672826729267302673126732267332673426735267362673726738267392674026741267422674326744267452674626747267482674926750267512675226753267542675526756267572675826759267602676126762267632676426765267662676726768267692677026771267722677326774267752677626777267782677926780267812678226783267842678526786267872678826789267902679126792267932679426795267962679726798267992680026801268022680326804268052680626807268082680926810268112681226813268142681526816268172681826819268202682126822268232682426825268262682726828268292683026831268322683326834268352683626837268382683926840268412684226843268442684526846268472684826849268502685126852268532685426855268562685726858268592686026861268622686326864268652686626867268682686926870268712687226873268742687526876268772687826879268802688126882268832688426885268862688726888268892689026891268922689326894268952689626897268982689926900269012690226903269042690526906269072690826909269102691126912269132691426915269162691726918269192692026921269222692326924269252692626927269282692926930269312693226933269342693526936269372693826939269402694126942269432694426945269462694726948269492695026951269522695326954269552695626957269582695926960269612696226963269642696526966269672696826969269702697126972269732697426975269762697726978269792698026981269822698326984269852698626987269882698926990269912699226993269942699526996269972699826999270002700127002270032700427005270062700727008270092701027011270122701327014270152701627017270182701927020270212702227023270242702527026270272702827029270302703127032270332703427035270362703727038270392704027041270422704327044270452704627047270482704927050270512705227053270542705527056270572705827059270602706127062270632706427065270662706727068270692707027071270722707327074270752707627077270782707927080270812708227083270842708527086270872708827089270902709127092270932709427095270962709727098270992710027101271022710327104271052710627107271082710927110271112711227113271142711527116271172711827119271202712127122271232712427125271262712727128271292713027131271322713327134271352713627137271382713927140271412714227143271442714527146271472714827149271502715127152271532715427155271562715727158271592716027161271622716327164271652716627167271682716927170271712717227173271742717527176271772717827179271802718127182271832718427185271862718727188271892719027191271922719327194271952719627197271982719927200272012720227203272042720527206272072720827209272102721127212272132721427215272162721727218272192722027221272222722327224272252722627227272282722927230272312723227233272342723527236272372723827239272402724127242272432724427245272462724727248272492725027251272522725327254272552725627257272582725927260272612726227263272642726527266272672726827269272702727127272272732727427275272762727727278272792728027281272822728327284272852728627287272882728927290272912729227293272942729527296272972729827299273002730127302273032730427305273062730727308273092731027311273122731327314273152731627317273182731927320273212732227323273242732527326273272732827329273302733127332273332733427335273362733727338273392734027341273422734327344273452734627347273482734927350273512735227353273542735527356273572735827359273602736127362273632736427365273662736727368273692737027371273722737327374273752737627377273782737927380273812738227383273842738527386273872738827389273902739127392273932739427395273962739727398273992740027401274022740327404274052740627407274082740927410274112741227413274142741527416274172741827419274202742127422274232742427425274262742727428274292743027431274322743327434274352743627437274382743927440274412744227443274442744527446274472744827449274502745127452274532745427455274562745727458274592746027461274622746327464274652746627467274682746927470274712747227473274742747527476274772747827479274802748127482274832748427485274862748727488274892749027491274922749327494274952749627497274982749927500275012750227503275042750527506275072750827509275102751127512275132751427515275162751727518275192752027521275222752327524275252752627527275282752927530275312753227533275342753527536275372753827539275402754127542275432754427545275462754727548275492755027551275522755327554275552755627557275582755927560275612756227563275642756527566275672756827569275702757127572275732757427575275762757727578275792758027581275822758327584275852758627587275882758927590275912759227593275942759527596275972759827599276002760127602276032760427605276062760727608276092761027611276122761327614276152761627617276182761927620276212762227623276242762527626276272762827629276302763127632276332763427635276362763727638276392764027641276422764327644276452764627647276482764927650276512765227653276542765527656276572765827659276602766127662276632766427665276662766727668276692767027671276722767327674276752767627677276782767927680276812768227683276842768527686276872768827689276902769127692276932769427695276962769727698276992770027701277022770327704277052770627707277082770927710277112771227713277142771527716277172771827719277202772127722277232772427725277262772727728277292773027731277322773327734277352773627737277382773927740277412774227743277442774527746277472774827749277502775127752277532775427755277562775727758277592776027761277622776327764277652776627767277682776927770277712777227773277742777527776277772777827779277802778127782277832778427785277862778727788277892779027791277922779327794277952779627797277982779927800278012780227803278042780527806278072780827809278102781127812278132781427815278162781727818278192782027821278222782327824278252782627827278282782927830278312783227833278342783527836278372783827839278402784127842278432784427845278462784727848278492785027851278522785327854278552785627857278582785927860278612786227863278642786527866278672786827869278702787127872278732787427875278762787727878278792788027881278822788327884278852788627887278882788927890278912789227893278942789527896278972789827899279002790127902279032790427905279062790727908279092791027911279122791327914279152791627917279182791927920279212792227923279242792527926279272792827929279302793127932279332793427935279362793727938279392794027941279422794327944279452794627947279482794927950279512795227953279542795527956279572795827959279602796127962279632796427965279662796727968279692797027971279722797327974279752797627977279782797927980279812798227983279842798527986279872798827989279902799127992279932799427995279962799727998279992800028001280022800328004280052800628007280082800928010280112801228013280142801528016280172801828019280202802128022280232802428025280262802728028280292803028031280322803328034280352803628037280382803928040280412804228043280442804528046280472804828049280502805128052280532805428055280562805728058280592806028061280622806328064280652806628067280682806928070280712807228073280742807528076280772807828079280802808128082280832808428085280862808728088280892809028091280922809328094280952809628097280982809928100281012810228103281042810528106281072810828109281102811128112281132811428115281162811728118281192812028121281222812328124281252812628127281282812928130281312813228133281342813528136281372813828139281402814128142281432814428145281462814728148281492815028151281522815328154281552815628157281582815928160281612816228163281642816528166281672816828169281702817128172281732817428175281762817728178281792818028181281822818328184281852818628187281882818928190281912819228193281942819528196281972819828199282002820128202282032820428205282062820728208282092821028211282122821328214282152821628217282182821928220282212822228223282242822528226282272822828229282302823128232282332823428235282362823728238282392824028241282422824328244282452824628247282482824928250282512825228253282542825528256282572825828259282602826128262282632826428265282662826728268282692827028271282722827328274282752827628277282782827928280282812828228283282842828528286282872828828289282902829128292282932829428295282962829728298282992830028301283022830328304283052830628307283082830928310283112831228313283142831528316283172831828319283202832128322283232832428325283262832728328283292833028331283322833328334283352833628337283382833928340283412834228343283442834528346283472834828349283502835128352283532835428355283562835728358283592836028361283622836328364283652836628367283682836928370283712837228373283742837528376283772837828379283802838128382283832838428385283862838728388283892839028391283922839328394283952839628397283982839928400284012840228403284042840528406284072840828409284102841128412284132841428415284162841728418284192842028421284222842328424284252842628427284282842928430284312843228433284342843528436284372843828439284402844128442284432844428445284462844728448284492845028451284522845328454284552845628457284582845928460284612846228463284642846528466284672846828469284702847128472284732847428475284762847728478284792848028481284822848328484284852848628487284882848928490284912849228493284942849528496284972849828499285002850128502285032850428505285062850728508285092851028511285122851328514285152851628517285182851928520285212852228523285242852528526285272852828529285302853128532285332853428535285362853728538285392854028541285422854328544285452854628547285482854928550285512855228553285542855528556285572855828559285602856128562285632856428565285662856728568285692857028571285722857328574285752857628577285782857928580285812858228583285842858528586285872858828589285902859128592285932859428595285962859728598285992860028601286022860328604286052860628607286082860928610286112861228613286142861528616286172861828619286202862128622286232862428625286262862728628286292863028631286322863328634286352863628637286382863928640286412864228643286442864528646286472864828649286502865128652286532865428655286562865728658286592866028661286622866328664286652866628667286682866928670286712867228673286742867528676286772867828679286802868128682286832868428685286862868728688286892869028691286922869328694286952869628697286982869928700287012870228703287042870528706287072870828709287102871128712287132871428715287162871728718287192872028721287222872328724287252872628727287282872928730287312873228733287342873528736287372873828739287402874128742287432874428745287462874728748287492875028751287522875328754287552875628757287582875928760287612876228763287642876528766287672876828769287702877128772287732877428775287762877728778287792878028781287822878328784287852878628787287882878928790287912879228793287942879528796287972879828799288002880128802288032880428805288062880728808288092881028811288122881328814288152881628817288182881928820288212882228823288242882528826288272882828829288302883128832288332883428835288362883728838288392884028841288422884328844288452884628847288482884928850288512885228853288542885528856288572885828859288602886128862288632886428865288662886728868288692887028871288722887328874288752887628877288782887928880288812888228883288842888528886288872888828889288902889128892288932889428895288962889728898288992890028901289022890328904289052890628907289082890928910289112891228913289142891528916289172891828919289202892128922289232892428925289262892728928289292893028931289322893328934289352893628937289382893928940289412894228943289442894528946289472894828949289502895128952289532895428955289562895728958289592896028961289622896328964289652896628967289682896928970289712897228973289742897528976289772897828979289802898128982289832898428985289862898728988289892899028991289922899328994289952899628997289982899929000290012900229003290042900529006290072900829009290102901129012290132901429015290162901729018290192902029021290222902329024290252902629027290282902929030290312903229033290342903529036290372903829039290402904129042290432904429045290462904729048290492905029051290522905329054290552905629057290582905929060290612906229063290642906529066290672906829069290702907129072290732907429075290762907729078290792908029081290822908329084290852908629087290882908929090290912909229093290942909529096290972909829099291002910129102291032910429105291062910729108291092911029111291122911329114291152911629117291182911929120291212912229123291242912529126291272912829129291302913129132291332913429135291362913729138291392914029141291422914329144291452914629147291482914929150291512915229153291542915529156291572915829159291602916129162291632916429165291662916729168291692917029171291722917329174291752917629177291782917929180291812918229183291842918529186291872918829189291902919129192291932919429195291962919729198291992920029201292022920329204292052920629207292082920929210292112921229213292142921529216292172921829219292202922129222292232922429225292262922729228292292923029231292322923329234292352923629237292382923929240292412924229243292442924529246292472924829249292502925129252292532925429255292562925729258292592926029261292622926329264292652926629267292682926929270292712927229273292742927529276292772927829279292802928129282292832928429285292862928729288292892929029291292922929329294292952929629297292982929929300293012930229303293042930529306293072930829309293102931129312293132931429315293162931729318293192932029321293222932329324293252932629327293282932929330293312933229333293342933529336293372933829339293402934129342293432934429345293462934729348293492935029351293522935329354293552935629357293582935929360293612936229363293642936529366293672936829369293702937129372293732937429375293762937729378293792938029381293822938329384293852938629387293882938929390293912939229393293942939529396293972939829399294002940129402294032940429405294062940729408294092941029411294122941329414294152941629417294182941929420294212942229423294242942529426294272942829429294302943129432294332943429435294362943729438294392944029441294422944329444294452944629447294482944929450294512945229453294542945529456294572945829459294602946129462294632946429465294662946729468294692947029471294722947329474294752947629477294782947929480294812948229483294842948529486294872948829489294902949129492294932949429495294962949729498294992950029501295022950329504295052950629507295082950929510295112951229513295142951529516295172951829519295202952129522295232952429525295262952729528295292953029531295322953329534295352953629537295382953929540295412954229543295442954529546295472954829549295502955129552295532955429555295562955729558295592956029561295622956329564295652956629567295682956929570295712957229573295742957529576295772957829579295802958129582295832958429585295862958729588295892959029591295922959329594295952959629597295982959929600296012960229603296042960529606296072960829609296102961129612296132961429615296162961729618296192962029621296222962329624296252962629627296282962929630296312963229633296342963529636296372963829639296402964129642296432964429645296462964729648296492965029651296522965329654296552965629657296582965929660296612966229663296642966529666296672966829669296702967129672296732967429675296762967729678296792968029681296822968329684296852968629687296882968929690296912969229693296942969529696296972969829699297002970129702297032970429705297062970729708297092971029711297122971329714297152971629717297182971929720297212972229723297242972529726297272972829729297302973129732297332973429735297362973729738297392974029741297422974329744297452974629747297482974929750297512975229753297542975529756297572975829759297602976129762297632976429765297662976729768297692977029771297722977329774297752977629777297782977929780297812978229783297842978529786297872978829789297902979129792297932979429795297962979729798297992980029801298022980329804298052980629807298082980929810298112981229813298142981529816298172981829819298202982129822298232982429825298262982729828298292983029831298322983329834298352983629837298382983929840298412984229843298442984529846298472984829849298502985129852298532985429855298562985729858298592986029861298622986329864298652986629867298682986929870298712987229873298742987529876298772987829879298802988129882298832988429885298862988729888298892989029891298922989329894298952989629897298982989929900299012990229903299042990529906299072990829909299102991129912299132991429915299162991729918299192992029921299222992329924299252992629927299282992929930299312993229933299342993529936299372993829939299402994129942299432994429945299462994729948299492995029951299522995329954299552995629957299582995929960299612996229963299642996529966299672996829969299702997129972299732997429975299762997729978299792998029981299822998329984299852998629987299882998929990299912999229993299942999529996299972999829999300003000130002300033000430005300063000730008300093001030011300123001330014300153001630017300183001930020300213002230023300243002530026300273002830029300303003130032300333003430035300363003730038300393004030041300423004330044300453004630047300483004930050300513005230053300543005530056300573005830059300603006130062300633006430065300663006730068300693007030071300723007330074300753007630077300783007930080300813008230083300843008530086300873008830089300903009130092300933009430095300963009730098300993010030101301023010330104301053010630107301083010930110301113011230113301143011530116301173011830119301203012130122301233012430125301263012730128301293013030131301323013330134301353013630137301383013930140301413014230143301443014530146301473014830149301503015130152301533015430155301563015730158301593016030161301623016330164301653016630167301683016930170301713017230173301743017530176301773017830179301803018130182301833018430185301863018730188301893019030191301923019330194301953019630197301983019930200302013020230203302043020530206302073020830209302103021130212302133021430215302163021730218302193022030221302223022330224302253022630227302283022930230302313023230233302343023530236302373023830239302403024130242302433024430245302463024730248302493025030251302523025330254302553025630257302583025930260302613026230263302643026530266302673026830269302703027130272302733027430275302763027730278302793028030281302823028330284302853028630287302883028930290302913029230293302943029530296302973029830299303003030130302303033030430305303063030730308303093031030311303123031330314303153031630317303183031930320303213032230323303243032530326303273032830329303303033130332303333033430335303363033730338303393034030341303423034330344303453034630347303483034930350303513035230353303543035530356303573035830359303603036130362303633036430365303663036730368303693037030371303723037330374303753037630377303783037930380303813038230383303843038530386303873038830389303903039130392303933039430395303963039730398303993040030401304023040330404304053040630407304083040930410304113041230413304143041530416304173041830419304203042130422304233042430425304263042730428304293043030431304323043330434304353043630437304383043930440304413044230443304443044530446304473044830449304503045130452304533045430455304563045730458304593046030461304623046330464304653046630467304683046930470304713047230473304743047530476304773047830479304803048130482304833048430485304863048730488304893049030491304923049330494304953049630497304983049930500305013050230503305043050530506305073050830509305103051130512305133051430515305163051730518305193052030521305223052330524305253052630527305283052930530305313053230533305343053530536305373053830539305403054130542305433054430545305463054730548305493055030551305523055330554305553055630557305583055930560305613056230563305643056530566305673056830569305703057130572305733057430575305763057730578305793058030581305823058330584305853058630587305883058930590305913059230593305943059530596305973059830599306003060130602306033060430605306063060730608306093061030611306123061330614306153061630617306183061930620306213062230623306243062530626306273062830629306303063130632306333063430635306363063730638306393064030641306423064330644306453064630647306483064930650306513065230653306543065530656306573065830659306603066130662306633066430665306663066730668306693067030671306723067330674306753067630677306783067930680306813068230683306843068530686306873068830689306903069130692306933069430695306963069730698306993070030701307023070330704307053070630707307083070930710307113071230713307143071530716307173071830719307203072130722307233072430725307263072730728307293073030731307323073330734307353073630737307383073930740307413074230743307443074530746307473074830749307503075130752307533075430755307563075730758307593076030761307623076330764307653076630767307683076930770307713077230773307743077530776307773077830779307803078130782307833078430785307863078730788307893079030791307923079330794307953079630797307983079930800308013080230803308043080530806308073080830809308103081130812308133081430815308163081730818308193082030821308223082330824308253082630827308283082930830308313083230833308343083530836308373083830839308403084130842308433084430845308463084730848308493085030851308523085330854308553085630857308583085930860308613086230863308643086530866308673086830869308703087130872308733087430875308763087730878308793088030881308823088330884308853088630887308883088930890308913089230893308943089530896308973089830899309003090130902309033090430905309063090730908309093091030911309123091330914309153091630917309183091930920309213092230923309243092530926309273092830929309303093130932309333093430935309363093730938309393094030941309423094330944309453094630947309483094930950309513095230953309543095530956309573095830959309603096130962309633096430965309663096730968309693097030971309723097330974309753097630977309783097930980309813098230983309843098530986309873098830989309903099130992309933099430995309963099730998309993100031001310023100331004310053100631007310083100931010310113101231013310143101531016310173101831019310203102131022310233102431025310263102731028310293103031031310323103331034310353103631037310383103931040310413104231043310443104531046310473104831049310503105131052310533105431055310563105731058310593106031061310623106331064310653106631067310683106931070310713107231073310743107531076310773107831079310803108131082310833108431085310863108731088310893109031091310923109331094310953109631097310983109931100311013110231103311043110531106311073110831109311103111131112311133111431115311163111731118311193112031121311223112331124311253112631127311283112931130311313113231133311343113531136311373113831139311403114131142311433114431145311463114731148311493115031151311523115331154311553115631157311583115931160311613116231163311643116531166311673116831169311703117131172311733117431175311763117731178311793118031181311823118331184311853118631187311883118931190311913119231193311943119531196311973119831199312003120131202312033120431205312063120731208312093121031211312123121331214312153121631217312183121931220312213122231223312243122531226312273122831229312303123131232312333123431235312363123731238312393124031241312423124331244312453124631247312483124931250312513125231253312543125531256312573125831259312603126131262312633126431265312663126731268312693127031271312723127331274312753127631277312783127931280312813128231283312843128531286312873128831289312903129131292312933129431295312963129731298312993130031301313023130331304313053130631307313083130931310313113131231313313143131531316313173131831319313203132131322313233132431325313263132731328313293133031331313323133331334313353133631337313383133931340313413134231343313443134531346313473134831349313503135131352313533135431355313563135731358313593136031361313623136331364313653136631367313683136931370313713137231373313743137531376313773137831379313803138131382313833138431385313863138731388313893139031391313923139331394313953139631397313983139931400314013140231403314043140531406314073140831409314103141131412314133141431415314163141731418314193142031421314223142331424314253142631427314283142931430314313143231433314343143531436314373143831439314403144131442314433144431445314463144731448314493145031451314523145331454314553145631457314583145931460314613146231463314643146531466314673146831469314703147131472314733147431475314763147731478314793148031481314823148331484314853148631487314883148931490314913149231493314943149531496314973149831499315003150131502315033150431505315063150731508315093151031511315123151331514315153151631517315183151931520315213152231523315243152531526315273152831529315303153131532315333153431535315363153731538315393154031541315423154331544315453154631547315483154931550315513155231553315543155531556315573155831559315603156131562315633156431565315663156731568315693157031571315723157331574315753157631577315783157931580315813158231583315843158531586315873158831589315903159131592315933159431595315963159731598315993160031601316023160331604316053160631607316083160931610316113161231613316143161531616316173161831619316203162131622316233162431625316263162731628316293163031631316323163331634316353163631637316383163931640316413164231643316443164531646316473164831649316503165131652316533165431655316563165731658316593166031661316623166331664316653166631667316683166931670316713167231673316743167531676316773167831679316803168131682316833168431685316863168731688316893169031691316923169331694316953169631697316983169931700317013170231703317043170531706317073170831709317103171131712317133171431715317163171731718317193172031721317223172331724317253172631727317283172931730317313173231733317343173531736317373173831739317403174131742317433174431745317463174731748317493175031751317523175331754317553175631757317583175931760317613176231763317643176531766317673176831769317703177131772317733177431775317763177731778317793178031781317823178331784317853178631787317883178931790317913179231793317943179531796317973179831799318003180131802318033180431805318063180731808318093181031811318123181331814318153181631817318183181931820318213182231823318243182531826318273182831829318303183131832318333183431835318363183731838318393184031841318423184331844318453184631847318483184931850318513185231853318543185531856318573185831859318603186131862318633186431865318663186731868318693187031871318723187331874318753187631877318783187931880318813188231883318843188531886318873188831889318903189131892318933189431895318963189731898318993190031901319023190331904319053190631907319083190931910319113191231913319143191531916319173191831919319203192131922319233192431925319263192731928319293193031931319323193331934319353193631937319383193931940319413194231943319443194531946319473194831949319503195131952319533195431955319563195731958319593196031961319623196331964319653196631967319683196931970319713197231973319743197531976319773197831979319803198131982319833198431985319863198731988319893199031991319923199331994319953199631997319983199932000320013200232003320043200532006320073200832009320103201132012320133201432015320163201732018320193202032021320223202332024320253202632027320283202932030320313203232033320343203532036320373203832039320403204132042320433204432045320463204732048320493205032051320523205332054320553205632057320583205932060320613206232063320643206532066320673206832069320703207132072320733207432075320763207732078320793208032081320823208332084320853208632087320883208932090320913209232093320943209532096320973209832099321003210132102321033210432105321063210732108321093211032111321123211332114321153211632117321183211932120321213212232123321243212532126321273212832129321303213132132321333213432135321363213732138321393214032141321423214332144321453214632147321483214932150321513215232153321543215532156321573215832159321603216132162321633216432165321663216732168321693217032171321723217332174321753217632177321783217932180321813218232183321843218532186321873218832189321903219132192321933219432195321963219732198321993220032201322023220332204322053220632207322083220932210322113221232213322143221532216322173221832219322203222132222322233222432225322263222732228322293223032231322323223332234322353223632237322383223932240322413224232243322443224532246322473224832249322503225132252322533225432255322563225732258322593226032261322623226332264322653226632267322683226932270322713227232273322743227532276322773227832279322803228132282322833228432285322863228732288322893229032291322923229332294322953229632297322983229932300323013230232303323043230532306323073230832309323103231132312323133231432315323163231732318323193232032321323223232332324323253232632327323283232932330323313233232333323343233532336323373233832339323403234132342323433234432345323463234732348323493235032351323523235332354323553235632357323583235932360323613236232363323643236532366323673236832369323703237132372323733237432375323763237732378323793238032381323823238332384323853238632387323883238932390323913239232393323943239532396323973239832399324003240132402324033240432405324063240732408324093241032411324123241332414324153241632417324183241932420324213242232423324243242532426324273242832429324303243132432324333243432435324363243732438324393244032441324423244332444324453244632447324483244932450324513245232453324543245532456324573245832459324603246132462324633246432465324663246732468324693247032471324723247332474324753247632477324783247932480324813248232483324843248532486324873248832489324903249132492324933249432495324963249732498324993250032501325023250332504325053250632507325083250932510325113251232513325143251532516325173251832519325203252132522325233252432525325263252732528325293253032531325323253332534325353253632537325383253932540325413254232543325443254532546325473254832549325503255132552325533255432555325563255732558325593256032561325623256332564325653256632567325683256932570325713257232573325743257532576325773257832579325803258132582325833258432585325863258732588325893259032591325923259332594325953259632597325983259932600326013260232603326043260532606326073260832609326103261132612326133261432615326163261732618326193262032621326223262332624326253262632627326283262932630326313263232633326343263532636326373263832639326403264132642326433264432645326463264732648326493265032651326523265332654326553265632657326583265932660326613266232663326643266532666326673266832669326703267132672326733267432675326763267732678326793268032681326823268332684326853268632687326883268932690326913269232693326943269532696326973269832699327003270132702327033270432705327063270732708327093271032711327123271332714327153271632717327183271932720327213272232723327243272532726327273272832729327303273132732327333273432735327363273732738327393274032741327423274332744327453274632747327483274932750327513275232753327543275532756327573275832759327603276132762327633276432765327663276732768327693277032771327723277332774327753277632777327783277932780327813278232783327843278532786327873278832789327903279132792327933279432795327963279732798327993280032801328023280332804328053280632807328083280932810328113281232813328143281532816328173281832819328203282132822328233282432825328263282732828328293283032831328323283332834328353283632837328383283932840328413284232843328443284532846328473284832849328503285132852328533285432855328563285732858328593286032861328623286332864328653286632867328683286932870328713287232873328743287532876328773287832879328803288132882328833288432885328863288732888328893289032891328923289332894328953289632897328983289932900329013290232903329043290532906329073290832909329103291132912329133291432915329163291732918329193292032921329223292332924329253292632927329283292932930329313293232933329343293532936329373293832939329403294132942329433294432945329463294732948329493295032951329523295332954329553295632957329583295932960329613296232963329643296532966329673296832969329703297132972329733297432975329763297732978329793298032981329823298332984329853298632987329883298932990329913299232993329943299532996329973299832999330003300133002330033300433005330063300733008330093301033011330123301333014330153301633017330183301933020330213302233023330243302533026330273302833029330303303133032330333303433035330363303733038330393304033041330423304333044330453304633047330483304933050330513305233053330543305533056330573305833059330603306133062330633306433065330663306733068330693307033071330723307333074330753307633077330783307933080330813308233083330843308533086330873308833089330903309133092330933309433095330963309733098330993310033101331023310333104331053310633107331083310933110331113311233113331143311533116331173311833119331203312133122331233312433125331263312733128331293313033131331323313333134331353313633137331383313933140331413314233143331443314533146331473314833149331503315133152331533315433155331563315733158331593316033161331623316333164331653316633167331683316933170331713317233173331743317533176331773317833179331803318133182331833318433185331863318733188331893319033191331923319333194331953319633197331983319933200332013320233203332043320533206332073320833209332103321133212332133321433215332163321733218332193322033221332223322333224332253322633227332283322933230332313323233233332343323533236332373323833239332403324133242332433324433245332463324733248332493325033251332523325333254332553325633257332583325933260332613326233263332643326533266332673326833269332703327133272332733327433275332763327733278332793328033281332823328333284332853328633287332883328933290332913329233293332943329533296332973329833299333003330133302333033330433305333063330733308333093331033311333123331333314333153331633317333183331933320333213332233323333243332533326333273332833329333303333133332333333333433335333363333733338333393334033341333423334333344333453334633347333483334933350333513335233353333543335533356333573335833359333603336133362333633336433365333663336733368333693337033371333723337333374333753337633377333783337933380333813338233383333843338533386333873338833389333903339133392333933339433395333963339733398333993340033401334023340333404334053340633407334083340933410334113341233413334143341533416334173341833419334203342133422334233342433425334263342733428334293343033431334323343333434334353343633437334383343933440334413344233443334443344533446334473344833449334503345133452334533345433455334563345733458334593346033461334623346333464334653346633467334683346933470334713347233473334743347533476334773347833479334803348133482334833348433485334863348733488334893349033491334923349333494334953349633497334983349933500335013350233503335043350533506335073350833509335103351133512335133351433515335163351733518335193352033521335223352333524335253352633527335283352933530335313353233533335343353533536335373353833539335403354133542335433354433545335463354733548335493355033551335523355333554335553355633557335583355933560335613356233563335643356533566335673356833569335703357133572335733357433575335763357733578335793358033581335823358333584335853358633587335883358933590335913359233593335943359533596335973359833599336003360133602336033360433605336063360733608336093361033611336123361333614336153361633617336183361933620336213362233623336243362533626336273362833629336303363133632336333363433635336363363733638336393364033641336423364333644336453364633647336483364933650336513365233653336543365533656336573365833659336603366133662336633366433665336663366733668336693367033671336723367333674336753367633677336783367933680336813368233683336843368533686336873368833689336903369133692336933369433695336963369733698336993370033701337023370333704337053370633707337083370933710337113371233713337143371533716337173371833719337203372133722337233372433725337263372733728337293373033731337323373333734337353373633737337383373933740337413374233743337443374533746337473374833749337503375133752337533375433755337563375733758337593376033761337623376333764337653376633767337683376933770337713377233773337743377533776337773377833779337803378133782337833378433785337863378733788337893379033791337923379333794337953379633797337983379933800338013380233803338043380533806338073380833809338103381133812338133381433815338163381733818338193382033821338223382333824338253382633827338283382933830338313383233833338343383533836338373383833839338403384133842338433384433845338463384733848338493385033851338523385333854338553385633857338583385933860338613386233863338643386533866338673386833869338703387133872338733387433875338763387733878338793388033881338823388333884338853388633887338883388933890338913389233893338943389533896338973389833899339003390133902339033390433905339063390733908339093391033911339123391333914339153391633917339183391933920339213392233923339243392533926339273392833929339303393133932339333393433935339363393733938339393394033941339423394333944339453394633947339483394933950339513395233953339543395533956339573395833959339603396133962339633396433965339663396733968339693397033971339723397333974339753397633977339783397933980339813398233983339843398533986339873398833989339903399133992339933399433995339963399733998339993400034001340023400334004340053400634007340083400934010340113401234013340143401534016340173401834019340203402134022340233402434025340263402734028340293403034031340323403334034340353403634037340383403934040340413404234043340443404534046340473404834049340503405134052340533405434055340563405734058340593406034061340623406334064340653406634067340683406934070340713407234073340743407534076340773407834079340803408134082340833408434085340863408734088340893409034091340923409334094340953409634097340983409934100341013410234103341043410534106341073410834109341103411134112341133411434115341163411734118341193412034121341223412334124341253412634127341283412934130341313413234133341343413534136341373413834139341403414134142341433414434145341463414734148341493415034151341523415334154341553415634157341583415934160341613416234163341643416534166341673416834169341703417134172341733417434175341763417734178341793418034181341823418334184341853418634187341883418934190341913419234193341943419534196341973419834199342003420134202342033420434205342063420734208342093421034211342123421334214342153421634217342183421934220342213422234223342243422534226342273422834229342303423134232342333423434235342363423734238342393424034241342423424334244342453424634247342483424934250342513425234253342543425534256342573425834259342603426134262342633426434265342663426734268342693427034271342723427334274342753427634277342783427934280342813428234283342843428534286342873428834289342903429134292342933429434295342963429734298342993430034301343023430334304343053430634307343083430934310343113431234313343143431534316343173431834319343203432134322343233432434325343263432734328343293433034331343323433334334343353433634337343383433934340343413434234343343443434534346343473434834349343503435134352343533435434355343563435734358343593436034361343623436334364343653436634367343683436934370343713437234373343743437534376343773437834379343803438134382343833438434385343863438734388343893439034391343923439334394343953439634397343983439934400344013440234403344043440534406344073440834409344103441134412344133441434415344163441734418344193442034421344223442334424344253442634427344283442934430344313443234433344343443534436344373443834439344403444134442344433444434445344463444734448344493445034451344523445334454344553445634457344583445934460344613446234463344643446534466344673446834469344703447134472344733447434475344763447734478344793448034481344823448334484344853448634487344883448934490344913449234493344943449534496344973449834499345003450134502345033450434505345063450734508345093451034511345123451334514345153451634517345183451934520345213452234523345243452534526345273452834529345303453134532345333453434535345363453734538345393454034541345423454334544345453454634547345483454934550345513455234553345543455534556345573455834559345603456134562345633456434565345663456734568345693457034571345723457334574345753457634577345783457934580345813458234583345843458534586345873458834589345903459134592345933459434595345963459734598345993460034601346023460334604346053460634607346083460934610346113461234613346143461534616346173461834619346203462134622346233462434625346263462734628346293463034631346323463334634346353463634637346383463934640346413464234643346443464534646346473464834649346503465134652346533465434655346563465734658346593466034661346623466334664346653466634667346683466934670346713467234673346743467534676346773467834679346803468134682346833468434685346863468734688346893469034691346923469334694346953469634697346983469934700347013470234703347043470534706347073470834709347103471134712347133471434715347163471734718347193472034721347223472334724347253472634727347283472934730347313473234733347343473534736347373473834739347403474134742347433474434745347463474734748347493475034751347523475334754347553475634757347583475934760347613476234763347643476534766347673476834769347703477134772347733477434775347763477734778347793478034781347823478334784347853478634787347883478934790347913479234793347943479534796347973479834799348003480134802348033480434805348063480734808348093481034811348123481334814348153481634817348183481934820348213482234823348243482534826348273482834829348303483134832348333483434835348363483734838348393484034841348423484334844348453484634847348483484934850348513485234853348543485534856348573485834859348603486134862348633486434865348663486734868348693487034871348723487334874348753487634877348783487934880348813488234883348843488534886348873488834889348903489134892348933489434895348963489734898348993490034901349023490334904349053490634907349083490934910349113491234913349143491534916349173491834919349203492134922349233492434925349263492734928349293493034931349323493334934349353493634937349383493934940349413494234943349443494534946349473494834949349503495134952349533495434955349563495734958349593496034961349623496334964349653496634967349683496934970349713497234973349743497534976349773497834979349803498134982349833498434985349863498734988349893499034991349923499334994349953499634997349983499935000350013500235003350043500535006350073500835009350103501135012350133501435015350163501735018350193502035021350223502335024350253502635027350283502935030350313503235033350343503535036350373503835039350403504135042350433504435045350463504735048350493505035051350523505335054350553505635057350583505935060350613506235063350643506535066350673506835069350703507135072350733507435075350763507735078350793508035081350823508335084350853508635087350883508935090350913509235093350943509535096350973509835099351003510135102351033510435105351063510735108351093511035111351123511335114351153511635117351183511935120351213512235123351243512535126351273512835129351303513135132351333513435135351363513735138351393514035141351423514335144351453514635147351483514935150351513515235153351543515535156351573515835159351603516135162351633516435165351663516735168351693517035171351723517335174351753517635177351783517935180351813518235183351843518535186351873518835189351903519135192351933519435195351963519735198351993520035201352023520335204352053520635207352083520935210352113521235213352143521535216352173521835219352203522135222352233522435225352263522735228352293523035231352323523335234352353523635237352383523935240352413524235243352443524535246352473524835249352503525135252352533525435255352563525735258352593526035261352623526335264352653526635267352683526935270352713527235273352743527535276352773527835279352803528135282352833528435285352863528735288352893529035291352923529335294352953529635297352983529935300353013530235303353043530535306353073530835309353103531135312353133531435315353163531735318353193532035321353223532335324353253532635327353283532935330353313533235333353343533535336353373533835339353403534135342353433534435345353463534735348353493535035351353523535335354353553535635357353583535935360353613536235363353643536535366353673536835369353703537135372353733537435375353763537735378353793538035381353823538335384353853538635387353883538935390353913539235393353943539535396353973539835399354003540135402354033540435405354063540735408354093541035411354123541335414354153541635417354183541935420354213542235423354243542535426354273542835429354303543135432354333543435435354363543735438354393544035441354423544335444354453544635447354483544935450354513545235453354543545535456354573545835459354603546135462354633546435465354663546735468354693547035471354723547335474354753547635477354783547935480354813548235483354843548535486354873548835489354903549135492354933549435495354963549735498354993550035501355023550335504355053550635507355083550935510355113551235513355143551535516355173551835519355203552135522355233552435525355263552735528355293553035531355323553335534355353553635537355383553935540355413554235543355443554535546355473554835549355503555135552355533555435555355563555735558355593556035561355623556335564355653556635567355683556935570355713557235573355743557535576355773557835579355803558135582355833558435585355863558735588355893559035591355923559335594355953559635597355983559935600356013560235603356043560535606356073560835609356103561135612356133561435615356163561735618356193562035621356223562335624356253562635627356283562935630356313563235633356343563535636356373563835639356403564135642356433564435645356463564735648356493565035651356523565335654356553565635657356583565935660356613566235663356643566535666356673566835669356703567135672356733567435675356763567735678356793568035681356823568335684356853568635687356883568935690356913569235693356943569535696356973569835699357003570135702357033570435705357063570735708357093571035711357123571335714357153571635717357183571935720357213572235723357243572535726357273572835729357303573135732357333573435735357363573735738357393574035741357423574335744357453574635747357483574935750357513575235753357543575535756357573575835759357603576135762357633576435765357663576735768357693577035771357723577335774357753577635777357783577935780357813578235783357843578535786357873578835789357903579135792357933579435795357963579735798357993580035801358023580335804358053580635807358083580935810358113581235813358143581535816358173581835819358203582135822358233582435825358263582735828358293583035831358323583335834358353583635837358383583935840358413584235843358443584535846358473584835849358503585135852358533585435855358563585735858358593586035861358623586335864358653586635867358683586935870358713587235873358743587535876358773587835879358803588135882358833588435885358863588735888358893589035891358923589335894358953589635897358983589935900359013590235903359043590535906359073590835909359103591135912359133591435915359163591735918359193592035921359223592335924359253592635927359283592935930359313593235933359343593535936359373593835939359403594135942359433594435945359463594735948359493595035951359523595335954359553595635957359583595935960359613596235963359643596535966359673596835969359703597135972359733597435975359763597735978359793598035981359823598335984359853598635987359883598935990359913599235993359943599535996359973599835999360003600136002360033600436005360063600736008360093601036011360123601336014360153601636017360183601936020360213602236023360243602536026360273602836029360303603136032360333603436035360363603736038360393604036041360423604336044360453604636047360483604936050360513605236053360543605536056360573605836059360603606136062360633606436065360663606736068360693607036071360723607336074360753607636077360783607936080360813608236083360843608536086360873608836089360903609136092360933609436095360963609736098360993610036101361023610336104361053610636107361083610936110361113611236113361143611536116361173611836119361203612136122361233612436125361263612736128361293613036131361323613336134361353613636137361383613936140361413614236143361443614536146361473614836149361503615136152361533615436155361563615736158361593616036161361623616336164361653616636167361683616936170361713617236173361743617536176361773617836179361803618136182361833618436185361863618736188361893619036191361923619336194361953619636197361983619936200362013620236203362043620536206362073620836209362103621136212362133621436215362163621736218362193622036221362223622336224362253622636227362283622936230362313623236233362343623536236362373623836239362403624136242362433624436245362463624736248362493625036251362523625336254362553625636257362583625936260362613626236263362643626536266362673626836269362703627136272362733627436275362763627736278362793628036281362823628336284362853628636287362883628936290362913629236293362943629536296362973629836299363003630136302363033630436305363063630736308363093631036311363123631336314363153631636317363183631936320363213632236323363243632536326363273632836329363303633136332363333633436335363363633736338363393634036341363423634336344363453634636347363483634936350363513635236353363543635536356363573635836359363603636136362363633636436365363663636736368363693637036371363723637336374363753637636377363783637936380363813638236383363843638536386363873638836389363903639136392363933639436395363963639736398363993640036401364023640336404364053640636407364083640936410364113641236413364143641536416364173641836419364203642136422364233642436425364263642736428364293643036431364323643336434364353643636437364383643936440364413644236443364443644536446364473644836449364503645136452364533645436455364563645736458364593646036461364623646336464364653646636467364683646936470364713647236473364743647536476364773647836479364803648136482364833648436485364863648736488364893649036491364923649336494364953649636497364983649936500365013650236503365043650536506365073650836509365103651136512365133651436515365163651736518365193652036521365223652336524365253652636527365283652936530365313653236533365343653536536365373653836539365403654136542365433654436545365463654736548365493655036551365523655336554365553655636557365583655936560365613656236563365643656536566365673656836569365703657136572365733657436575365763657736578365793658036581365823658336584365853658636587365883658936590365913659236593365943659536596365973659836599366003660136602366033660436605366063660736608366093661036611366123661336614366153661636617366183661936620366213662236623366243662536626366273662836629366303663136632366333663436635366363663736638366393664036641366423664336644366453664636647366483664936650366513665236653366543665536656366573665836659366603666136662366633666436665366663666736668366693667036671366723667336674366753667636677366783667936680366813668236683366843668536686366873668836689366903669136692366933669436695366963669736698366993670036701367023670336704367053670636707367083670936710367113671236713367143671536716367173671836719367203672136722367233672436725367263672736728367293673036731367323673336734367353673636737367383673936740367413674236743367443674536746367473674836749367503675136752367533675436755367563675736758367593676036761367623676336764367653676636767367683676936770367713677236773367743677536776367773677836779367803678136782367833678436785367863678736788367893679036791367923679336794367953679636797367983679936800368013680236803368043680536806368073680836809368103681136812368133681436815368163681736818368193682036821368223682336824368253682636827368283682936830368313683236833368343683536836368373683836839368403684136842368433684436845368463684736848368493685036851368523685336854368553685636857368583685936860368613686236863368643686536866368673686836869368703687136872368733687436875368763687736878368793688036881368823688336884368853688636887368883688936890368913689236893368943689536896368973689836899369003690136902369033690436905369063690736908369093691036911369123691336914369153691636917369183691936920369213692236923369243692536926369273692836929369303693136932369333693436935369363693736938369393694036941369423694336944369453694636947369483694936950369513695236953369543695536956369573695836959369603696136962369633696436965369663696736968369693697036971369723697336974369753697636977369783697936980369813698236983369843698536986369873698836989369903699136992369933699436995369963699736998369993700037001370023700337004370053700637007370083700937010370113701237013370143701537016370173701837019370203702137022370233702437025370263702737028370293703037031370323703337034370353703637037370383703937040370413704237043370443704537046370473704837049370503705137052370533705437055370563705737058370593706037061370623706337064370653706637067370683706937070370713707237073370743707537076370773707837079370803708137082370833708437085370863708737088370893709037091370923709337094370953709637097370983709937100371013710237103371043710537106371073710837109371103711137112371133711437115371163711737118371193712037121371223712337124371253712637127371283712937130371313713237133371343713537136371373713837139371403714137142371433714437145371463714737148371493715037151371523715337154371553715637157371583715937160371613716237163371643716537166371673716837169371703717137172371733717437175371763717737178371793718037181371823718337184371853718637187371883718937190371913719237193371943719537196371973719837199372003720137202372033720437205372063720737208372093721037211372123721337214372153721637217372183721937220372213722237223372243722537226372273722837229372303723137232372333723437235372363723737238372393724037241372423724337244372453724637247372483724937250372513725237253372543725537256372573725837259372603726137262372633726437265372663726737268372693727037271372723727337274372753727637277372783727937280372813728237283372843728537286372873728837289372903729137292372933729437295372963729737298372993730037301373023730337304373053730637307373083730937310373113731237313373143731537316373173731837319373203732137322373233732437325373263732737328373293733037331373323733337334373353733637337373383733937340373413734237343373443734537346373473734837349373503735137352373533735437355373563735737358373593736037361373623736337364373653736637367373683736937370373713737237373373743737537376373773737837379373803738137382373833738437385373863738737388373893739037391373923739337394373953739637397373983739937400374013740237403374043740537406374073740837409374103741137412374133741437415374163741737418374193742037421374223742337424374253742637427374283742937430374313743237433374343743537436374373743837439374403744137442374433744437445374463744737448374493745037451374523745337454374553745637457374583745937460374613746237463374643746537466374673746837469374703747137472374733747437475374763747737478374793748037481374823748337484374853748637487374883748937490374913749237493374943749537496374973749837499375003750137502375033750437505375063750737508375093751037511375123751337514375153751637517375183751937520375213752237523375243752537526375273752837529375303753137532375333753437535375363753737538375393754037541375423754337544375453754637547375483754937550375513755237553375543755537556375573755837559375603756137562375633756437565375663756737568375693757037571375723757337574375753757637577375783757937580375813758237583375843758537586375873758837589375903759137592375933759437595375963759737598375993760037601376023760337604376053760637607376083760937610376113761237613376143761537616376173761837619376203762137622376233762437625376263762737628376293763037631376323763337634376353763637637376383763937640376413764237643376443764537646376473764837649376503765137652376533765437655376563765737658376593766037661376623766337664376653766637667376683766937670376713767237673376743767537676376773767837679376803768137682376833768437685376863768737688376893769037691376923769337694376953769637697376983769937700377013770237703377043770537706377073770837709377103771137712377133771437715377163771737718377193772037721377223772337724377253772637727377283772937730377313773237733377343773537736377373773837739377403774137742377433774437745377463774737748377493775037751377523775337754377553775637757377583775937760377613776237763377643776537766377673776837769377703777137772377733777437775377763777737778377793778037781377823778337784377853778637787377883778937790377913779237793377943779537796377973779837799378003780137802378033780437805378063780737808378093781037811378123781337814378153781637817378183781937820378213782237823378243782537826378273782837829378303783137832378333783437835378363783737838378393784037841378423784337844378453784637847378483784937850378513785237853378543785537856378573785837859378603786137862378633786437865378663786737868378693787037871378723787337874378753787637877378783787937880378813788237883378843788537886378873788837889378903789137892378933789437895378963789737898378993790037901379023790337904379053790637907379083790937910379113791237913379143791537916379173791837919379203792137922379233792437925379263792737928379293793037931379323793337934379353793637937379383793937940379413794237943379443794537946379473794837949379503795137952379533795437955379563795737958379593796037961379623796337964379653796637967379683796937970379713797237973379743797537976379773797837979379803798137982379833798437985379863798737988379893799037991379923799337994379953799637997379983799938000380013800238003380043800538006380073800838009380103801138012380133801438015380163801738018380193802038021380223802338024380253802638027380283802938030380313803238033380343803538036380373803838039380403804138042380433804438045380463804738048380493805038051380523805338054380553805638057380583805938060380613806238063380643806538066380673806838069380703807138072380733807438075380763807738078380793808038081380823808338084380853808638087380883808938090380913809238093380943809538096380973809838099381003810138102381033810438105381063810738108381093811038111381123811338114381153811638117381183811938120381213812238123381243812538126381273812838129381303813138132381333813438135381363813738138381393814038141381423814338144381453814638147381483814938150381513815238153381543815538156381573815838159381603816138162381633816438165381663816738168381693817038171381723817338174381753817638177381783817938180381813818238183381843818538186381873818838189381903819138192381933819438195381963819738198381993820038201382023820338204382053820638207382083820938210382113821238213382143821538216382173821838219382203822138222382233822438225382263822738228382293823038231382323823338234382353823638237382383823938240382413824238243382443824538246382473824838249382503825138252382533825438255382563825738258382593826038261382623826338264382653826638267382683826938270382713827238273382743827538276382773827838279382803828138282382833828438285382863828738288382893829038291382923829338294382953829638297382983829938300383013830238303383043830538306383073830838309383103831138312383133831438315383163831738318383193832038321383223832338324383253832638327383283832938330383313833238333383343833538336383373833838339383403834138342383433834438345383463834738348383493835038351383523835338354383553835638357383583835938360383613836238363383643836538366383673836838369383703837138372383733837438375383763837738378383793838038381383823838338384383853838638387383883838938390383913839238393383943839538396383973839838399384003840138402384033840438405384063840738408384093841038411384123841338414384153841638417384183841938420384213842238423384243842538426384273842838429384303843138432384333843438435384363843738438384393844038441384423844338444384453844638447384483844938450384513845238453384543845538456384573845838459384603846138462384633846438465384663846738468384693847038471384723847338474384753847638477384783847938480384813848238483384843848538486384873848838489384903849138492384933849438495384963849738498384993850038501385023850338504385053850638507385083850938510385113851238513385143851538516385173851838519385203852138522385233852438525385263852738528385293853038531385323853338534385353853638537385383853938540385413854238543385443854538546385473854838549385503855138552385533855438555385563855738558385593856038561385623856338564385653856638567385683856938570385713857238573385743857538576385773857838579385803858138582385833858438585385863858738588385893859038591385923859338594385953859638597385983859938600386013860238603386043860538606386073860838609386103861138612386133861438615386163861738618386193862038621386223862338624386253862638627386283862938630386313863238633386343863538636386373863838639386403864138642386433864438645386463864738648386493865038651386523865338654386553865638657386583865938660386613866238663386643866538666386673866838669386703867138672386733867438675386763867738678386793868038681386823868338684386853868638687386883868938690386913869238693386943869538696386973869838699387003870138702387033870438705387063870738708387093871038711387123871338714387153871638717387183871938720387213872238723387243872538726387273872838729387303873138732387333873438735387363873738738387393874038741387423874338744387453874638747387483874938750387513875238753387543875538756387573875838759387603876138762387633876438765387663876738768387693877038771387723877338774387753877638777387783877938780387813878238783387843878538786387873878838789387903879138792387933879438795387963879738798387993880038801388023880338804388053880638807388083880938810388113881238813388143881538816388173881838819388203882138822388233882438825388263882738828388293883038831388323883338834388353883638837388383883938840388413884238843388443884538846388473884838849388503885138852388533885438855388563885738858388593886038861388623886338864388653886638867388683886938870388713887238873388743887538876388773887838879388803888138882388833888438885388863888738888388893889038891388923889338894388953889638897388983889938900389013890238903389043890538906389073890838909389103891138912389133891438915389163891738918389193892038921389223892338924389253892638927389283892938930389313893238933389343893538936389373893838939389403894138942389433894438945389463894738948389493895038951389523895338954389553895638957389583895938960389613896238963389643896538966389673896838969389703897138972389733897438975389763897738978389793898038981389823898338984389853898638987389883898938990389913899238993389943899538996389973899838999390003900139002390033900439005390063900739008390093901039011390123901339014390153901639017390183901939020390213902239023390243902539026390273902839029390303903139032390333903439035390363903739038390393904039041390423904339044390453904639047390483904939050
  1. /*
  2. ******************************************************************
  3. * C++ Mathematical Expression Toolkit Library *
  4. * *
  5. * Author: Arash Partow (1999-2020) *
  6. * URL: http://www.partow.net/programming/exprtk/index.html *
  7. * *
  8. * Copyright notice: *
  9. * Free use of the C++ Mathematical Expression Toolkit Library is *
  10. * permitted under the guidelines and in accordance with the most *
  11. * current version of the MIT License. *
  12. * http://www.opensource.org/licenses/MIT *
  13. * *
  14. * Example expressions: *
  15. * (00) (y + x / y) * (x - y / x) *
  16. * (01) (x^2 / sin(2 * pi / y)) - x / 2 *
  17. * (02) sqrt(1 - (x^2)) *
  18. * (03) 1 - sin(2 * x) + cos(pi / y) *
  19. * (04) a * exp(2 * t) + c *
  20. * (05) if(((x + 2) == 3) and ((y + 5) <= 9),1 + w, 2 / z) *
  21. * (06) (avg(x,y) <= x + y ? x - y : x * y) + 2 * pi / x *
  22. * (07) z := x + sin(2 * pi / y) *
  23. * (08) u := 2 * (pi * z) / (w := x + cos(y / pi)) *
  24. * (09) clamp(-1,sin(2 * pi * x) + cos(y / 2 * pi),+1) *
  25. * (10) inrange(-2,m,+2) == if(({-2 <= m} and [m <= +2]),1,0) *
  26. * (11) (2sin(x)cos(2y)7 + 1) == (2 * sin(x) * cos(2*y) * 7 + 1) *
  27. * (12) (x ilike 's*ri?g') and [y < (3 z^7 + w)] *
  28. * *
  29. ******************************************************************
  30. */
  31. #ifndef INCLUDE_EXPRTK_HPP
  32. #define INCLUDE_EXPRTK_HPP
  33. #include <algorithm>
  34. #include <cctype>
  35. #include <cmath>
  36. #include <complex>
  37. #include <cstdio>
  38. #include <cstdlib>
  39. #include <cstring>
  40. #include <deque>
  41. #include <exception>
  42. #include <functional>
  43. #include <iterator>
  44. #include <limits>
  45. #include <list>
  46. #include <map>
  47. #include <set>
  48. #include <stack>
  49. #include <stdexcept>
  50. #include <string>
  51. #include <utility>
  52. #include <vector>
  53. namespace exprtk
  54. {
  55. #ifdef exprtk_enable_debugging
  56. #define exprtk_debug(params) printf params
  57. #else
  58. #define exprtk_debug(params) (void)0
  59. #endif
  60. #define exprtk_error_location \
  61. "exprtk.hpp:" + details::to_str(__LINE__) \
  62. #if defined(__GNUC__) && (__GNUC__ >= 7)
  63. #define exprtk_disable_fallthrough_begin \
  64. _Pragma ("GCC diagnostic push") \
  65. _Pragma ("GCC diagnostic ignored \"-Wimplicit-fallthrough\"") \
  66. #define exprtk_disable_fallthrough_end \
  67. _Pragma ("GCC diagnostic pop") \
  68. #else
  69. #define exprtk_disable_fallthrough_begin (void)0;
  70. #define exprtk_disable_fallthrough_end (void)0;
  71. #endif
  72. namespace details
  73. {
  74. typedef unsigned char uchar_t;
  75. typedef char char_t;
  76. typedef uchar_t* uchar_ptr;
  77. typedef char_t* char_ptr;
  78. typedef uchar_t const* uchar_cptr;
  79. typedef char_t const* char_cptr;
  80. typedef unsigned long long int _uint64_t;
  81. typedef long long int _int64_t;
  82. inline bool is_whitespace(const char_t c)
  83. {
  84. return (' ' == c) || ('\n' == c) ||
  85. ('\r' == c) || ('\t' == c) ||
  86. ('\b' == c) || ('\v' == c) ||
  87. ('\f' == c) ;
  88. }
  89. inline bool is_operator_char(const char_t c)
  90. {
  91. return ('+' == c) || ('-' == c) ||
  92. ('*' == c) || ('/' == c) ||
  93. ('^' == c) || ('<' == c) ||
  94. ('>' == c) || ('=' == c) ||
  95. (',' == c) || ('!' == c) ||
  96. ('(' == c) || (')' == c) ||
  97. ('[' == c) || (']' == c) ||
  98. ('{' == c) || ('}' == c) ||
  99. ('%' == c) || (':' == c) ||
  100. ('?' == c) || ('&' == c) ||
  101. ('|' == c) || (';' == c) ;
  102. }
  103. inline bool is_letter(const char_t c)
  104. {
  105. return (('a' <= c) && (c <= 'z')) ||
  106. (('A' <= c) && (c <= 'Z')) ;
  107. }
  108. inline bool is_digit(const char_t c)
  109. {
  110. return ('0' <= c) && (c <= '9');
  111. }
  112. inline bool is_letter_or_digit(const char_t c)
  113. {
  114. return is_letter(c) || is_digit(c);
  115. }
  116. inline bool is_left_bracket(const char_t c)
  117. {
  118. return ('(' == c) || ('[' == c) || ('{' == c);
  119. }
  120. inline bool is_right_bracket(const char_t c)
  121. {
  122. return (')' == c) || (']' == c) || ('}' == c);
  123. }
  124. inline bool is_bracket(const char_t c)
  125. {
  126. return is_left_bracket(c) || is_right_bracket(c);
  127. }
  128. inline bool is_sign(const char_t c)
  129. {
  130. return ('+' == c) || ('-' == c);
  131. }
  132. inline bool is_invalid(const char_t c)
  133. {
  134. return !is_whitespace (c) &&
  135. !is_operator_char(c) &&
  136. !is_letter (c) &&
  137. !is_digit (c) &&
  138. ('.' != c) &&
  139. ('_' != c) &&
  140. ('$' != c) &&
  141. ('~' != c) &&
  142. ('\'' != c);
  143. }
  144. #ifndef exprtk_disable_caseinsensitivity
  145. inline void case_normalise(std::string& s)
  146. {
  147. for (std::size_t i = 0; i < s.size(); ++i)
  148. {
  149. s[i] = static_cast<std::string::value_type>(std::tolower(s[i]));
  150. }
  151. }
  152. inline bool imatch(const char_t c1, const char_t c2)
  153. {
  154. return std::tolower(c1) == std::tolower(c2);
  155. }
  156. inline bool imatch(const std::string& s1, const std::string& s2)
  157. {
  158. if (s1.size() == s2.size())
  159. {
  160. for (std::size_t i = 0; i < s1.size(); ++i)
  161. {
  162. if (std::tolower(s1[i]) != std::tolower(s2[i]))
  163. {
  164. return false;
  165. }
  166. }
  167. return true;
  168. }
  169. return false;
  170. }
  171. struct ilesscompare
  172. {
  173. inline bool operator() (const std::string& s1, const std::string& s2) const
  174. {
  175. const std::size_t length = std::min(s1.size(),s2.size());
  176. for (std::size_t i = 0; i < length; ++i)
  177. {
  178. const char_t c1 = static_cast<char>(std::tolower(s1[i]));
  179. const char_t c2 = static_cast<char>(std::tolower(s2[i]));
  180. if (c1 > c2)
  181. return false;
  182. else if (c1 < c2)
  183. return true;
  184. }
  185. return s1.size() < s2.size();
  186. }
  187. };
  188. #else
  189. inline void case_normalise(std::string&)
  190. {}
  191. inline bool imatch(const char_t c1, const char_t c2)
  192. {
  193. return c1 == c2;
  194. }
  195. inline bool imatch(const std::string& s1, const std::string& s2)
  196. {
  197. return s1 == s2;
  198. }
  199. struct ilesscompare
  200. {
  201. inline bool operator() (const std::string& s1, const std::string& s2) const
  202. {
  203. return s1 < s2;
  204. }
  205. };
  206. #endif
  207. inline bool is_valid_sf_symbol(const std::string& symbol)
  208. {
  209. // Special function: $f12 or $F34
  210. return (4 == symbol.size()) &&
  211. ('$' == symbol[0]) &&
  212. imatch('f',symbol[1]) &&
  213. is_digit(symbol[2]) &&
  214. is_digit(symbol[3]);
  215. }
  216. inline const char_t& front(const std::string& s)
  217. {
  218. return s[0];
  219. }
  220. inline const char_t& back(const std::string& s)
  221. {
  222. return s[s.size() - 1];
  223. }
  224. inline std::string to_str(int i)
  225. {
  226. if (0 == i)
  227. return std::string("0");
  228. std::string result;
  229. if (i < 0)
  230. {
  231. for ( ; i; i /= 10)
  232. {
  233. result += '0' + char(-(i % 10));
  234. }
  235. result += '-';
  236. }
  237. else
  238. {
  239. for ( ; i; i /= 10)
  240. {
  241. result += '0' + char(i % 10);
  242. }
  243. }
  244. std::reverse(result.begin(), result.end());
  245. return result;
  246. }
  247. inline std::string to_str(std::size_t i)
  248. {
  249. return to_str(static_cast<int>(i));
  250. }
  251. inline bool is_hex_digit(const std::string::value_type digit)
  252. {
  253. return (('0' <= digit) && (digit <= '9')) ||
  254. (('A' <= digit) && (digit <= 'F')) ||
  255. (('a' <= digit) && (digit <= 'f')) ;
  256. }
  257. inline uchar_t hex_to_bin(uchar_t h)
  258. {
  259. if (('0' <= h) && (h <= '9'))
  260. return (h - '0');
  261. else
  262. return static_cast<unsigned char>(std::toupper(h) - 'A');
  263. }
  264. template <typename Iterator>
  265. inline void parse_hex(Iterator& itr, Iterator end, std::string::value_type& result)
  266. {
  267. if (
  268. (end != (itr )) &&
  269. (end != (itr + 1)) &&
  270. (end != (itr + 2)) &&
  271. (end != (itr + 3)) &&
  272. ('0' == *(itr )) &&
  273. (
  274. ('x' == *(itr + 1)) ||
  275. ('X' == *(itr + 1))
  276. ) &&
  277. (is_hex_digit(*(itr + 2))) &&
  278. (is_hex_digit(*(itr + 3)))
  279. )
  280. {
  281. result = hex_to_bin(static_cast<uchar_t>(*(itr + 2))) << 4 |
  282. hex_to_bin(static_cast<uchar_t>(*(itr + 3))) ;
  283. itr += 3;
  284. }
  285. else
  286. result = '\0';
  287. }
  288. inline void cleanup_escapes(std::string& s)
  289. {
  290. typedef std::string::iterator str_itr_t;
  291. str_itr_t itr1 = s.begin();
  292. str_itr_t itr2 = s.begin();
  293. str_itr_t end = s.end ();
  294. std::size_t removal_count = 0;
  295. while (end != itr1)
  296. {
  297. if ('\\' == (*itr1))
  298. {
  299. ++removal_count;
  300. if (end == ++itr1)
  301. break;
  302. else if ('\\' != (*itr1))
  303. {
  304. switch (*itr1)
  305. {
  306. case 'n' : (*itr1) = '\n'; break;
  307. case 'r' : (*itr1) = '\r'; break;
  308. case 't' : (*itr1) = '\t'; break;
  309. case '0' : parse_hex(itr1, end, (*itr1));
  310. removal_count += 3;
  311. break;
  312. }
  313. continue;
  314. }
  315. }
  316. if (itr1 != itr2)
  317. {
  318. (*itr2) = (*itr1);
  319. }
  320. ++itr1;
  321. ++itr2;
  322. }
  323. s.resize(s.size() - removal_count);
  324. }
  325. class build_string
  326. {
  327. public:
  328. build_string(const std::size_t& initial_size = 64)
  329. {
  330. data_.reserve(initial_size);
  331. }
  332. inline build_string& operator << (const std::string& s)
  333. {
  334. data_ += s;
  335. return (*this);
  336. }
  337. inline build_string& operator << (char_cptr s)
  338. {
  339. data_ += std::string(s);
  340. return (*this);
  341. }
  342. inline operator std::string () const
  343. {
  344. return data_;
  345. }
  346. inline std::string as_string() const
  347. {
  348. return data_;
  349. }
  350. private:
  351. std::string data_;
  352. };
  353. static const std::string reserved_words[] =
  354. {
  355. "break", "case", "continue", "default", "false", "for",
  356. "if", "else", "ilike", "in", "like", "and", "nand", "nor",
  357. "not", "null", "or", "repeat", "return", "shl", "shr",
  358. "swap", "switch", "true", "until", "var", "while", "xnor",
  359. "xor", "&", "|"
  360. };
  361. static const std::size_t reserved_words_size = sizeof(reserved_words) / sizeof(std::string);
  362. static const std::string reserved_symbols[] =
  363. {
  364. "abs", "acos", "acosh", "and", "asin", "asinh", "atan",
  365. "atanh", "atan2", "avg", "break", "case", "ceil", "clamp",
  366. "continue", "cos", "cosh", "cot", "csc", "default",
  367. "deg2grad", "deg2rad", "equal", "erf", "erfc", "exp",
  368. "expm1", "false", "floor", "for", "frac", "grad2deg",
  369. "hypot", "iclamp", "if", "else", "ilike", "in", "inrange",
  370. "like", "log", "log10", "log2", "logn", "log1p", "mand",
  371. "max", "min", "mod", "mor", "mul", "ncdf", "nand", "nor",
  372. "not", "not_equal", "null", "or", "pow", "rad2deg",
  373. "repeat", "return", "root", "round", "roundn", "sec", "sgn",
  374. "shl", "shr", "sin", "sinc", "sinh", "sqrt", "sum", "swap",
  375. "switch", "tan", "tanh", "true", "trunc", "until", "var",
  376. "while", "xnor", "xor", "&", "|"
  377. };
  378. static const std::size_t reserved_symbols_size = sizeof(reserved_symbols) / sizeof(std::string);
  379. static const std::string base_function_list[] =
  380. {
  381. "abs", "acos", "acosh", "asin", "asinh", "atan", "atanh",
  382. "atan2", "avg", "ceil", "clamp", "cos", "cosh", "cot",
  383. "csc", "equal", "erf", "erfc", "exp", "expm1", "floor",
  384. "frac", "hypot", "iclamp", "like", "log", "log10", "log2",
  385. "logn", "log1p", "mand", "max", "min", "mod", "mor", "mul",
  386. "ncdf", "pow", "root", "round", "roundn", "sec", "sgn",
  387. "sin", "sinc", "sinh", "sqrt", "sum", "swap", "tan", "tanh",
  388. "trunc", "not_equal", "inrange", "deg2grad", "deg2rad",
  389. "rad2deg", "grad2deg"
  390. };
  391. static const std::size_t base_function_list_size = sizeof(base_function_list) / sizeof(std::string);
  392. static const std::string logic_ops_list[] =
  393. {
  394. "and", "nand", "nor", "not", "or", "xnor", "xor", "&", "|"
  395. };
  396. static const std::size_t logic_ops_list_size = sizeof(logic_ops_list) / sizeof(std::string);
  397. static const std::string cntrl_struct_list[] =
  398. {
  399. "if", "switch", "for", "while", "repeat", "return"
  400. };
  401. static const std::size_t cntrl_struct_list_size = sizeof(cntrl_struct_list) / sizeof(std::string);
  402. static const std::string arithmetic_ops_list[] =
  403. {
  404. "+", "-", "*", "/", "%", "^"
  405. };
  406. static const std::size_t arithmetic_ops_list_size = sizeof(arithmetic_ops_list) / sizeof(std::string);
  407. static const std::string assignment_ops_list[] =
  408. {
  409. ":=", "+=", "-=",
  410. "*=", "/=", "%="
  411. };
  412. static const std::size_t assignment_ops_list_size = sizeof(assignment_ops_list) / sizeof(std::string);
  413. static const std::string inequality_ops_list[] =
  414. {
  415. "<", "<=", "==",
  416. "=", "!=", "<>",
  417. ">=", ">"
  418. };
  419. static const std::size_t inequality_ops_list_size = sizeof(inequality_ops_list) / sizeof(std::string);
  420. inline bool is_reserved_word(const std::string& symbol)
  421. {
  422. for (std::size_t i = 0; i < reserved_words_size; ++i)
  423. {
  424. if (imatch(symbol, reserved_words[i]))
  425. {
  426. return true;
  427. }
  428. }
  429. return false;
  430. }
  431. inline bool is_reserved_symbol(const std::string& symbol)
  432. {
  433. for (std::size_t i = 0; i < reserved_symbols_size; ++i)
  434. {
  435. if (imatch(symbol, reserved_symbols[i]))
  436. {
  437. return true;
  438. }
  439. }
  440. return false;
  441. }
  442. inline bool is_base_function(const std::string& function_name)
  443. {
  444. for (std::size_t i = 0; i < base_function_list_size; ++i)
  445. {
  446. if (imatch(function_name, base_function_list[i]))
  447. {
  448. return true;
  449. }
  450. }
  451. return false;
  452. }
  453. inline bool is_control_struct(const std::string& cntrl_strct)
  454. {
  455. for (std::size_t i = 0; i < cntrl_struct_list_size; ++i)
  456. {
  457. if (imatch(cntrl_strct, cntrl_struct_list[i]))
  458. {
  459. return true;
  460. }
  461. }
  462. return false;
  463. }
  464. inline bool is_logic_opr(const std::string& lgc_opr)
  465. {
  466. for (std::size_t i = 0; i < logic_ops_list_size; ++i)
  467. {
  468. if (imatch(lgc_opr, logic_ops_list[i]))
  469. {
  470. return true;
  471. }
  472. }
  473. return false;
  474. }
  475. struct cs_match
  476. {
  477. static inline bool cmp(const char_t c0, const char_t c1)
  478. {
  479. return (c0 == c1);
  480. }
  481. };
  482. struct cis_match
  483. {
  484. static inline bool cmp(const char_t c0, const char_t c1)
  485. {
  486. return (std::tolower(c0) == std::tolower(c1));
  487. }
  488. };
  489. template <typename Iterator, typename Compare>
  490. inline bool match_impl(const Iterator pattern_begin,
  491. const Iterator pattern_end ,
  492. const Iterator data_begin ,
  493. const Iterator data_end ,
  494. const typename std::iterator_traits<Iterator>::value_type& zero_or_more,
  495. const typename std::iterator_traits<Iterator>::value_type& zero_or_one )
  496. {
  497. const Iterator null_itr(0);
  498. Iterator d_itr = data_begin;
  499. Iterator p_itr = pattern_begin;
  500. Iterator tb_p_itr = null_itr;
  501. Iterator tb_d_itr = null_itr;
  502. while (d_itr != data_end)
  503. {
  504. if (zero_or_more == *p_itr)
  505. {
  506. while ((pattern_end != p_itr) && ((zero_or_more == *p_itr) || (zero_or_one == *p_itr)))
  507. {
  508. ++p_itr;
  509. }
  510. if (pattern_end == p_itr)
  511. return true;
  512. const typename std::iterator_traits<Iterator>::value_type c = *(p_itr);
  513. while ((data_end != d_itr) && !Compare::cmp(c,*d_itr))
  514. {
  515. ++d_itr;
  516. }
  517. tb_p_itr = p_itr;
  518. tb_d_itr = d_itr;
  519. continue;
  520. }
  521. else if (!Compare::cmp(*p_itr, *d_itr) && (zero_or_one != *p_itr))
  522. {
  523. if (null_itr == tb_d_itr)
  524. return false;
  525. d_itr = tb_d_itr++;
  526. p_itr = tb_p_itr;
  527. continue;
  528. }
  529. ++p_itr;
  530. ++d_itr;
  531. }
  532. while ((pattern_end != p_itr) && ((zero_or_more == *p_itr) || (zero_or_one == *p_itr)))
  533. {
  534. ++p_itr;
  535. }
  536. return (pattern_end == p_itr);
  537. }
  538. inline bool wc_match(const std::string& wild_card,
  539. const std::string& str)
  540. {
  541. return match_impl<char_cptr,cs_match>(wild_card.data(),
  542. wild_card.data() + wild_card.size(),
  543. str.data(),
  544. str.data() + str.size(),
  545. '*',
  546. '?');
  547. }
  548. inline bool wc_imatch(const std::string& wild_card,
  549. const std::string& str)
  550. {
  551. return match_impl<char_cptr,cis_match>(wild_card.data(),
  552. wild_card.data() + wild_card.size(),
  553. str.data(),
  554. str.data() + str.size(),
  555. '*',
  556. '?');
  557. }
  558. inline bool sequence_match(const std::string& pattern,
  559. const std::string& str,
  560. std::size_t& diff_index,
  561. char_t& diff_value)
  562. {
  563. if (str.empty())
  564. {
  565. return ("Z" == pattern);
  566. }
  567. else if ('*' == pattern[0])
  568. return false;
  569. typedef std::string::const_iterator itr_t;
  570. itr_t p_itr = pattern.begin();
  571. itr_t s_itr = str .begin();
  572. itr_t p_end = pattern.end();
  573. itr_t s_end = str .end();
  574. while ((s_end != s_itr) && (p_end != p_itr))
  575. {
  576. if ('*' == (*p_itr))
  577. {
  578. const char_t target = static_cast<char>(std::toupper(*(p_itr - 1)));
  579. if ('*' == target)
  580. {
  581. diff_index = static_cast<std::size_t>(std::distance(str.begin(),s_itr));
  582. diff_value = static_cast<char>(std::toupper(*p_itr));
  583. return false;
  584. }
  585. else
  586. ++p_itr;
  587. while (s_itr != s_end)
  588. {
  589. if (target != std::toupper(*s_itr))
  590. break;
  591. else
  592. ++s_itr;
  593. }
  594. continue;
  595. }
  596. else if (
  597. ('?' != *p_itr) &&
  598. std::toupper(*p_itr) != std::toupper(*s_itr)
  599. )
  600. {
  601. diff_index = static_cast<std::size_t>(std::distance(str.begin(),s_itr));
  602. diff_value = static_cast<char>(std::toupper(*p_itr));
  603. return false;
  604. }
  605. ++p_itr;
  606. ++s_itr;
  607. }
  608. return (
  609. (s_end == s_itr) &&
  610. (
  611. (p_end == p_itr) ||
  612. ('*' == *p_itr)
  613. )
  614. );
  615. }
  616. static const double pow10[] = {
  617. 1.0,
  618. 1.0E+001, 1.0E+002, 1.0E+003, 1.0E+004,
  619. 1.0E+005, 1.0E+006, 1.0E+007, 1.0E+008,
  620. 1.0E+009, 1.0E+010, 1.0E+011, 1.0E+012,
  621. 1.0E+013, 1.0E+014, 1.0E+015, 1.0E+016
  622. };
  623. static const std::size_t pow10_size = sizeof(pow10) / sizeof(double);
  624. namespace numeric
  625. {
  626. namespace constant
  627. {
  628. static const double e = 2.71828182845904523536028747135266249775724709369996;
  629. static const double pi = 3.14159265358979323846264338327950288419716939937510;
  630. static const double pi_2 = 1.57079632679489661923132169163975144209858469968755;
  631. static const double pi_4 = 0.78539816339744830961566084581987572104929234984378;
  632. static const double pi_180 = 0.01745329251994329576923690768488612713442871888542;
  633. static const double _1_pi = 0.31830988618379067153776752674502872406891929148091;
  634. static const double _2_pi = 0.63661977236758134307553505349005744813783858296183;
  635. static const double _180_pi = 57.29577951308232087679815481410517033240547246656443;
  636. static const double log2 = 0.69314718055994530941723212145817656807550013436026;
  637. static const double sqrt2 = 1.41421356237309504880168872420969807856967187537695;
  638. }
  639. namespace details
  640. {
  641. struct unknown_type_tag { unknown_type_tag() {} };
  642. struct real_type_tag { real_type_tag () {} };
  643. struct complex_type_tag { complex_type_tag() {} };
  644. struct int_type_tag { int_type_tag () {} };
  645. template <typename T>
  646. struct number_type
  647. {
  648. typedef unknown_type_tag type;
  649. number_type() {}
  650. };
  651. #define exprtk_register_real_type_tag(T) \
  652. template<> struct number_type<T> \
  653. { typedef real_type_tag type; number_type() {} }; \
  654. #define exprtk_register_complex_type_tag(T) \
  655. template<> struct number_type<std::complex<T> > \
  656. { typedef complex_type_tag type; number_type() {} }; \
  657. #define exprtk_register_int_type_tag(T) \
  658. template<> struct number_type<T> \
  659. { typedef int_type_tag type; number_type() {} }; \
  660. exprtk_register_real_type_tag(double )
  661. exprtk_register_real_type_tag(long double)
  662. exprtk_register_real_type_tag(float )
  663. exprtk_register_complex_type_tag(double )
  664. exprtk_register_complex_type_tag(long double)
  665. exprtk_register_complex_type_tag(float )
  666. exprtk_register_int_type_tag(short )
  667. exprtk_register_int_type_tag(int )
  668. exprtk_register_int_type_tag(_int64_t )
  669. exprtk_register_int_type_tag(unsigned short)
  670. exprtk_register_int_type_tag(unsigned int )
  671. exprtk_register_int_type_tag(_uint64_t )
  672. #undef exprtk_register_real_type_tag
  673. #undef exprtk_register_int_type_tag
  674. template <typename T>
  675. struct epsilon_type
  676. {
  677. static inline T value()
  678. {
  679. const T epsilon = T(0.0000000001);
  680. return epsilon;
  681. }
  682. };
  683. template <>
  684. struct epsilon_type <float>
  685. {
  686. static inline float value()
  687. {
  688. const float epsilon = float(0.000001f);
  689. return epsilon;
  690. }
  691. };
  692. template <>
  693. struct epsilon_type <long double>
  694. {
  695. static inline long double value()
  696. {
  697. const long double epsilon = (long double)(0.000000000001);
  698. return epsilon;
  699. }
  700. };
  701. template <typename T>
  702. inline bool is_nan_impl(const T v, real_type_tag)
  703. {
  704. return std::not_equal_to<T>()(v,v);
  705. }
  706. template <typename T>
  707. inline int to_int32_impl(const T v, real_type_tag)
  708. {
  709. return static_cast<int>(v);
  710. }
  711. template <typename T>
  712. inline _int64_t to_int64_impl(const T v, real_type_tag)
  713. {
  714. return static_cast<_int64_t>(v);
  715. }
  716. template <typename T>
  717. inline bool is_true_impl(const T v)
  718. {
  719. return std::not_equal_to<T>()(T(0),v);
  720. }
  721. template <typename T>
  722. inline bool is_false_impl(const T v)
  723. {
  724. return std::equal_to<T>()(T(0),v);
  725. }
  726. template <typename T>
  727. inline T abs_impl(const T v, real_type_tag)
  728. {
  729. return ((v < T(0)) ? -v : v);
  730. }
  731. template <typename T>
  732. inline T min_impl(const T v0, const T v1, real_type_tag)
  733. {
  734. return std::min<T>(v0,v1);
  735. }
  736. template <typename T>
  737. inline T max_impl(const T v0, const T v1, real_type_tag)
  738. {
  739. return std::max<T>(v0,v1);
  740. }
  741. template <typename T>
  742. inline T equal_impl(const T v0, const T v1, real_type_tag)
  743. {
  744. const T epsilon = epsilon_type<T>::value();
  745. return (abs_impl(v0 - v1,real_type_tag()) <= (std::max(T(1),std::max(abs_impl(v0,real_type_tag()),abs_impl(v1,real_type_tag()))) * epsilon)) ? T(1) : T(0);
  746. }
  747. inline float equal_impl(const float v0, const float v1, real_type_tag)
  748. {
  749. const float epsilon = epsilon_type<float>::value();
  750. return (abs_impl(v0 - v1,real_type_tag()) <= (std::max(1.0f,std::max(abs_impl(v0,real_type_tag()),abs_impl(v1,real_type_tag()))) * epsilon)) ? 1.0f : 0.0f;
  751. }
  752. template <typename T>
  753. inline T equal_impl(const T v0, const T v1, int_type_tag)
  754. {
  755. return (v0 == v1) ? 1 : 0;
  756. }
  757. template <typename T>
  758. inline T expm1_impl(const T v, real_type_tag)
  759. {
  760. // return std::expm1<T>(v);
  761. if (abs_impl(v,real_type_tag()) < T(0.00001))
  762. return v + (T(0.5) * v * v);
  763. else
  764. return std::exp(v) - T(1);
  765. }
  766. template <typename T>
  767. inline T expm1_impl(const T v, int_type_tag)
  768. {
  769. return T(std::exp<double>(v)) - T(1);
  770. }
  771. template <typename T>
  772. inline T nequal_impl(const T v0, const T v1, real_type_tag)
  773. {
  774. typedef real_type_tag rtg;
  775. const T epsilon = epsilon_type<T>::value();
  776. return (abs_impl(v0 - v1,rtg()) > (std::max(T(1),std::max(abs_impl(v0,rtg()),abs_impl(v1,rtg()))) * epsilon)) ? T(1) : T(0);
  777. }
  778. inline float nequal_impl(const float v0, const float v1, real_type_tag)
  779. {
  780. typedef real_type_tag rtg;
  781. const float epsilon = epsilon_type<float>::value();
  782. return (abs_impl(v0 - v1,rtg()) > (std::max(1.0f,std::max(abs_impl(v0,rtg()),abs_impl(v1,rtg()))) * epsilon)) ? 1.0f : 0.0f;
  783. }
  784. template <typename T>
  785. inline T nequal_impl(const T v0, const T v1, int_type_tag)
  786. {
  787. return (v0 != v1) ? 1 : 0;
  788. }
  789. template <typename T>
  790. inline T modulus_impl(const T v0, const T v1, real_type_tag)
  791. {
  792. return std::fmod(v0,v1);
  793. }
  794. template <typename T>
  795. inline T modulus_impl(const T v0, const T v1, int_type_tag)
  796. {
  797. return v0 % v1;
  798. }
  799. template <typename T>
  800. inline T pow_impl(const T v0, const T v1, real_type_tag)
  801. {
  802. return std::pow(v0,v1);
  803. }
  804. template <typename T>
  805. inline T pow_impl(const T v0, const T v1, int_type_tag)
  806. {
  807. return std::pow(static_cast<double>(v0),static_cast<double>(v1));
  808. }
  809. template <typename T>
  810. inline T logn_impl(const T v0, const T v1, real_type_tag)
  811. {
  812. return std::log(v0) / std::log(v1);
  813. }
  814. template <typename T>
  815. inline T logn_impl(const T v0, const T v1, int_type_tag)
  816. {
  817. return static_cast<T>(logn_impl<double>(static_cast<double>(v0),static_cast<double>(v1),real_type_tag()));
  818. }
  819. template <typename T>
  820. inline T log1p_impl(const T v, real_type_tag)
  821. {
  822. if (v > T(-1))
  823. {
  824. if (abs_impl(v,real_type_tag()) > T(0.0001))
  825. {
  826. return std::log(T(1) + v);
  827. }
  828. else
  829. return (T(-0.5) * v + T(1)) * v;
  830. }
  831. else
  832. return std::numeric_limits<T>::quiet_NaN();
  833. }
  834. template <typename T>
  835. inline T log1p_impl(const T v, int_type_tag)
  836. {
  837. if (v > T(-1))
  838. {
  839. return std::log(T(1) + v);
  840. }
  841. else
  842. return std::numeric_limits<T>::quiet_NaN();
  843. }
  844. template <typename T>
  845. inline T root_impl(const T v0, const T v1, real_type_tag)
  846. {
  847. if (v1 < T(0))
  848. return std::numeric_limits<T>::quiet_NaN();
  849. const std::size_t n = static_cast<std::size_t>(v1);
  850. if ((v0 < T(0)) && (0 == (n % 2)))
  851. return std::numeric_limits<T>::quiet_NaN();
  852. return std::pow(v0, T(1) / n);
  853. }
  854. template <typename T>
  855. inline T root_impl(const T v0, const T v1, int_type_tag)
  856. {
  857. return root_impl<double>(static_cast<double>(v0),static_cast<double>(v1),real_type_tag());
  858. }
  859. template <typename T>
  860. inline T round_impl(const T v, real_type_tag)
  861. {
  862. return ((v < T(0)) ? std::ceil(v - T(0.5)) : std::floor(v + T(0.5)));
  863. }
  864. template <typename T>
  865. inline T roundn_impl(const T v0, const T v1, real_type_tag)
  866. {
  867. const int index = std::max<int>(0, std::min<int>(pow10_size - 1, (int)std::floor(v1)));
  868. const T p10 = T(pow10[index]);
  869. if (v0 < T(0))
  870. return T(std::ceil ((v0 * p10) - T(0.5)) / p10);
  871. else
  872. return T(std::floor((v0 * p10) + T(0.5)) / p10);
  873. }
  874. template <typename T>
  875. inline T roundn_impl(const T v0, const T, int_type_tag)
  876. {
  877. return v0;
  878. }
  879. template <typename T>
  880. inline T hypot_impl(const T v0, const T v1, real_type_tag)
  881. {
  882. return std::sqrt((v0 * v0) + (v1 * v1));
  883. }
  884. template <typename T>
  885. inline T hypot_impl(const T v0, const T v1, int_type_tag)
  886. {
  887. return static_cast<T>(std::sqrt(static_cast<double>((v0 * v0) + (v1 * v1))));
  888. }
  889. template <typename T>
  890. inline T atan2_impl(const T v0, const T v1, real_type_tag)
  891. {
  892. return std::atan2(v0,v1);
  893. }
  894. template <typename T>
  895. inline T atan2_impl(const T, const T, int_type_tag)
  896. {
  897. return 0;
  898. }
  899. template <typename T>
  900. inline T shr_impl(const T v0, const T v1, real_type_tag)
  901. {
  902. return v0 * (T(1) / std::pow(T(2),static_cast<T>(static_cast<int>(v1))));
  903. }
  904. template <typename T>
  905. inline T shr_impl(const T v0, const T v1, int_type_tag)
  906. {
  907. return v0 >> v1;
  908. }
  909. template <typename T>
  910. inline T shl_impl(const T v0, const T v1, real_type_tag)
  911. {
  912. return v0 * std::pow(T(2),static_cast<T>(static_cast<int>(v1)));
  913. }
  914. template <typename T>
  915. inline T shl_impl(const T v0, const T v1, int_type_tag)
  916. {
  917. return v0 << v1;
  918. }
  919. template <typename T>
  920. inline T sgn_impl(const T v, real_type_tag)
  921. {
  922. if (v > T(0)) return T(+1);
  923. else if (v < T(0)) return T(-1);
  924. else return T( 0);
  925. }
  926. template <typename T>
  927. inline T sgn_impl(const T v, int_type_tag)
  928. {
  929. if (v > T(0)) return T(+1);
  930. else if (v < T(0)) return T(-1);
  931. else return T( 0);
  932. }
  933. template <typename T>
  934. inline T and_impl(const T v0, const T v1, real_type_tag)
  935. {
  936. return (is_true_impl(v0) && is_true_impl(v1)) ? T(1) : T(0);
  937. }
  938. template <typename T>
  939. inline T and_impl(const T v0, const T v1, int_type_tag)
  940. {
  941. return v0 && v1;
  942. }
  943. template <typename T>
  944. inline T nand_impl(const T v0, const T v1, real_type_tag)
  945. {
  946. return (is_false_impl(v0) || is_false_impl(v1)) ? T(1) : T(0);
  947. }
  948. template <typename T>
  949. inline T nand_impl(const T v0, const T v1, int_type_tag)
  950. {
  951. return !(v0 && v1);
  952. }
  953. template <typename T>
  954. inline T or_impl(const T v0, const T v1, real_type_tag)
  955. {
  956. return (is_true_impl(v0) || is_true_impl(v1)) ? T(1) : T(0);
  957. }
  958. template <typename T>
  959. inline T or_impl(const T v0, const T v1, int_type_tag)
  960. {
  961. return (v0 || v1);
  962. }
  963. template <typename T>
  964. inline T nor_impl(const T v0, const T v1, real_type_tag)
  965. {
  966. return (is_false_impl(v0) && is_false_impl(v1)) ? T(1) : T(0);
  967. }
  968. template <typename T>
  969. inline T nor_impl(const T v0, const T v1, int_type_tag)
  970. {
  971. return !(v0 || v1);
  972. }
  973. template <typename T>
  974. inline T xor_impl(const T v0, const T v1, real_type_tag)
  975. {
  976. return (is_false_impl(v0) != is_false_impl(v1)) ? T(1) : T(0);
  977. }
  978. template <typename T>
  979. inline T xor_impl(const T v0, const T v1, int_type_tag)
  980. {
  981. return v0 ^ v1;
  982. }
  983. template <typename T>
  984. inline T xnor_impl(const T v0, const T v1, real_type_tag)
  985. {
  986. const bool v0_true = is_true_impl(v0);
  987. const bool v1_true = is_true_impl(v1);
  988. if ((v0_true && v1_true) || (!v0_true && !v1_true))
  989. return T(1);
  990. else
  991. return T(0);
  992. }
  993. template <typename T>
  994. inline T xnor_impl(const T v0, const T v1, int_type_tag)
  995. {
  996. const bool v0_true = is_true_impl(v0);
  997. const bool v1_true = is_true_impl(v1);
  998. if ((v0_true && v1_true) || (!v0_true && !v1_true))
  999. return T(1);
  1000. else
  1001. return T(0);
  1002. }
  1003. #if (defined(_MSC_VER) && (_MSC_VER >= 1900)) || !defined(_MSC_VER)
  1004. #define exprtk_define_erf(TT,impl) \
  1005. inline TT erf_impl(TT v) { return impl(v); } \
  1006. exprtk_define_erf( float,::erff)
  1007. exprtk_define_erf( double,::erf )
  1008. exprtk_define_erf(long double,::erfl)
  1009. #undef exprtk_define_erf
  1010. #endif
  1011. template <typename T>
  1012. inline T erf_impl(T v, real_type_tag)
  1013. {
  1014. #if defined(_MSC_VER) && (_MSC_VER < 1900)
  1015. // Credits: Abramowitz & Stegun Equations 7.1.25-28
  1016. static const T c[] = {
  1017. T( 1.26551223), T(1.00002368),
  1018. T( 0.37409196), T(0.09678418),
  1019. T(-0.18628806), T(0.27886807),
  1020. T(-1.13520398), T(1.48851587),
  1021. T(-0.82215223), T(0.17087277)
  1022. };
  1023. const T t = T(1) / (T(1) + T(0.5) * abs_impl(v,real_type_tag()));
  1024. T result = T(1) - t * std::exp((-v * v) -
  1025. c[0] + t * (c[1] + t *
  1026. (c[2] + t * (c[3] + t *
  1027. (c[4] + t * (c[5] + t *
  1028. (c[6] + t * (c[7] + t *
  1029. (c[8] + t * (c[9]))))))))));
  1030. return (v >= T(0)) ? result : -result;
  1031. #else
  1032. return erf_impl(v);
  1033. #endif
  1034. }
  1035. template <typename T>
  1036. inline T erf_impl(T v, int_type_tag)
  1037. {
  1038. return erf_impl(static_cast<double>(v),real_type_tag());
  1039. }
  1040. #if (defined(_MSC_VER) && (_MSC_VER >= 1900)) || !defined(_MSC_VER)
  1041. #define exprtk_define_erfc(TT,impl) \
  1042. inline TT erfc_impl(TT v) { return impl(v); } \
  1043. exprtk_define_erfc( float,::erfcf)
  1044. exprtk_define_erfc( double,::erfc )
  1045. exprtk_define_erfc(long double,::erfcl)
  1046. #undef exprtk_define_erfc
  1047. #endif
  1048. template <typename T>
  1049. inline T erfc_impl(T v, real_type_tag)
  1050. {
  1051. #if defined(_MSC_VER) && (_MSC_VER < 1900)
  1052. return T(1) - erf_impl(v,real_type_tag());
  1053. #else
  1054. return erfc_impl(v);
  1055. #endif
  1056. }
  1057. template <typename T>
  1058. inline T erfc_impl(T v, int_type_tag)
  1059. {
  1060. return erfc_impl(static_cast<double>(v),real_type_tag());
  1061. }
  1062. template <typename T>
  1063. inline T ncdf_impl(T v, real_type_tag)
  1064. {
  1065. T cnd = T(0.5) * (T(1) + erf_impl(
  1066. abs_impl(v,real_type_tag()) /
  1067. T(numeric::constant::sqrt2),real_type_tag()));
  1068. return (v < T(0)) ? (T(1) - cnd) : cnd;
  1069. }
  1070. template <typename T>
  1071. inline T ncdf_impl(T v, int_type_tag)
  1072. {
  1073. return ncdf_impl(static_cast<double>(v),real_type_tag());
  1074. }
  1075. template <typename T>
  1076. inline T sinc_impl(T v, real_type_tag)
  1077. {
  1078. if (std::abs(v) >= std::numeric_limits<T>::epsilon())
  1079. return(std::sin(v) / v);
  1080. else
  1081. return T(1);
  1082. }
  1083. template <typename T>
  1084. inline T sinc_impl(T v, int_type_tag)
  1085. {
  1086. return sinc_impl(static_cast<double>(v),real_type_tag());
  1087. }
  1088. template <typename T> inline T acos_impl(const T v, real_type_tag) { return std::acos (v); }
  1089. template <typename T> inline T acosh_impl(const T v, real_type_tag) { return std::log(v + std::sqrt((v * v) - T(1))); }
  1090. template <typename T> inline T asin_impl(const T v, real_type_tag) { return std::asin (v); }
  1091. template <typename T> inline T asinh_impl(const T v, real_type_tag) { return std::log(v + std::sqrt((v * v) + T(1))); }
  1092. template <typename T> inline T atan_impl(const T v, real_type_tag) { return std::atan (v); }
  1093. template <typename T> inline T atanh_impl(const T v, real_type_tag) { return (std::log(T(1) + v) - std::log(T(1) - v)) / T(2); }
  1094. template <typename T> inline T ceil_impl(const T v, real_type_tag) { return std::ceil (v); }
  1095. template <typename T> inline T cos_impl(const T v, real_type_tag) { return std::cos (v); }
  1096. template <typename T> inline T cosh_impl(const T v, real_type_tag) { return std::cosh (v); }
  1097. template <typename T> inline T exp_impl(const T v, real_type_tag) { return std::exp (v); }
  1098. template <typename T> inline T floor_impl(const T v, real_type_tag) { return std::floor(v); }
  1099. template <typename T> inline T log_impl(const T v, real_type_tag) { return std::log (v); }
  1100. template <typename T> inline T log10_impl(const T v, real_type_tag) { return std::log10(v); }
  1101. template <typename T> inline T log2_impl(const T v, real_type_tag) { return std::log(v)/T(numeric::constant::log2); }
  1102. template <typename T> inline T neg_impl(const T v, real_type_tag) { return -v; }
  1103. template <typename T> inline T pos_impl(const T v, real_type_tag) { return +v; }
  1104. template <typename T> inline T sin_impl(const T v, real_type_tag) { return std::sin (v); }
  1105. template <typename T> inline T sinh_impl(const T v, real_type_tag) { return std::sinh (v); }
  1106. template <typename T> inline T sqrt_impl(const T v, real_type_tag) { return std::sqrt (v); }
  1107. template <typename T> inline T tan_impl(const T v, real_type_tag) { return std::tan (v); }
  1108. template <typename T> inline T tanh_impl(const T v, real_type_tag) { return std::tanh (v); }
  1109. template <typename T> inline T cot_impl(const T v, real_type_tag) { return T(1) / std::tan(v); }
  1110. template <typename T> inline T sec_impl(const T v, real_type_tag) { return T(1) / std::cos(v); }
  1111. template <typename T> inline T csc_impl(const T v, real_type_tag) { return T(1) / std::sin(v); }
  1112. template <typename T> inline T r2d_impl(const T v, real_type_tag) { return (v * T(numeric::constant::_180_pi)); }
  1113. template <typename T> inline T d2r_impl(const T v, real_type_tag) { return (v * T(numeric::constant::pi_180)); }
  1114. template <typename T> inline T d2g_impl(const T v, real_type_tag) { return (v * T(20.0/9.0)); }
  1115. template <typename T> inline T g2d_impl(const T v, real_type_tag) { return (v * T(9.0/20.0)); }
  1116. template <typename T> inline T notl_impl(const T v, real_type_tag) { return (std::not_equal_to<T>()(T(0),v) ? T(0) : T(1)); }
  1117. template <typename T> inline T frac_impl(const T v, real_type_tag) { return (v - static_cast<long long>(v)); }
  1118. template <typename T> inline T trunc_impl(const T v, real_type_tag) { return T(static_cast<long long>(v)); }
  1119. template <typename T> inline T const_pi_impl(real_type_tag) { return T(numeric::constant::pi); }
  1120. template <typename T> inline T const_e_impl (real_type_tag) { return T(numeric::constant::e); }
  1121. template <typename T> inline T abs_impl(const T v, int_type_tag) { return ((v >= T(0)) ? v : -v); }
  1122. template <typename T> inline T exp_impl(const T v, int_type_tag) { return std::exp (v); }
  1123. template <typename T> inline T log_impl(const T v, int_type_tag) { return std::log (v); }
  1124. template <typename T> inline T log10_impl(const T v, int_type_tag) { return std::log10(v); }
  1125. template <typename T> inline T log2_impl(const T v, int_type_tag) { return std::log(v)/T(numeric::constant::log2); }
  1126. template <typename T> inline T neg_impl(const T v, int_type_tag) { return -v; }
  1127. template <typename T> inline T pos_impl(const T v, int_type_tag) { return +v; }
  1128. template <typename T> inline T ceil_impl(const T v, int_type_tag) { return v; }
  1129. template <typename T> inline T floor_impl(const T v, int_type_tag) { return v; }
  1130. template <typename T> inline T round_impl(const T v, int_type_tag) { return v; }
  1131. template <typename T> inline T notl_impl(const T v, int_type_tag) { return !v; }
  1132. template <typename T> inline T sqrt_impl(const T v, int_type_tag) { return std::sqrt (v); }
  1133. template <typename T> inline T frac_impl(const T , int_type_tag) { return T(0); }
  1134. template <typename T> inline T trunc_impl(const T v, int_type_tag) { return v; }
  1135. template <typename T> inline T acos_impl(const T , int_type_tag) { return std::numeric_limits<T>::quiet_NaN(); }
  1136. template <typename T> inline T acosh_impl(const T , int_type_tag) { return std::numeric_limits<T>::quiet_NaN(); }
  1137. template <typename T> inline T asin_impl(const T , int_type_tag) { return std::numeric_limits<T>::quiet_NaN(); }
  1138. template <typename T> inline T asinh_impl(const T , int_type_tag) { return std::numeric_limits<T>::quiet_NaN(); }
  1139. template <typename T> inline T atan_impl(const T , int_type_tag) { return std::numeric_limits<T>::quiet_NaN(); }
  1140. template <typename T> inline T atanh_impl(const T , int_type_tag) { return std::numeric_limits<T>::quiet_NaN(); }
  1141. template <typename T> inline T cos_impl(const T , int_type_tag) { return std::numeric_limits<T>::quiet_NaN(); }
  1142. template <typename T> inline T cosh_impl(const T , int_type_tag) { return std::numeric_limits<T>::quiet_NaN(); }
  1143. template <typename T> inline T sin_impl(const T , int_type_tag) { return std::numeric_limits<T>::quiet_NaN(); }
  1144. template <typename T> inline T sinh_impl(const T , int_type_tag) { return std::numeric_limits<T>::quiet_NaN(); }
  1145. template <typename T> inline T tan_impl(const T , int_type_tag) { return std::numeric_limits<T>::quiet_NaN(); }
  1146. template <typename T> inline T tanh_impl(const T , int_type_tag) { return std::numeric_limits<T>::quiet_NaN(); }
  1147. template <typename T> inline T cot_impl(const T , int_type_tag) { return std::numeric_limits<T>::quiet_NaN(); }
  1148. template <typename T> inline T sec_impl(const T , int_type_tag) { return std::numeric_limits<T>::quiet_NaN(); }
  1149. template <typename T> inline T csc_impl(const T , int_type_tag) { return std::numeric_limits<T>::quiet_NaN(); }
  1150. template <typename T>
  1151. inline bool is_integer_impl(const T& v, real_type_tag)
  1152. {
  1153. return std::equal_to<T>()(T(0),std::fmod(v,T(1)));
  1154. }
  1155. template <typename T>
  1156. inline bool is_integer_impl(const T&, int_type_tag)
  1157. {
  1158. return true;
  1159. }
  1160. }
  1161. template <typename Type>
  1162. struct numeric_info { enum { length = 0, size = 32, bound_length = 0, min_exp = 0, max_exp = 0 }; };
  1163. template<> struct numeric_info<int> { enum { length = 10, size = 16, bound_length = 9}; };
  1164. template<> struct numeric_info<float> { enum { min_exp = -38, max_exp = +38}; };
  1165. template<> struct numeric_info<double> { enum { min_exp = -308, max_exp = +308}; };
  1166. template<> struct numeric_info<long double> { enum { min_exp = -308, max_exp = +308}; };
  1167. template <typename T>
  1168. inline int to_int32(const T v)
  1169. {
  1170. const typename details::number_type<T>::type num_type;
  1171. return to_int32_impl(v, num_type);
  1172. }
  1173. template <typename T>
  1174. inline _int64_t to_int64(const T v)
  1175. {
  1176. const typename details::number_type<T>::type num_type;
  1177. return to_int64_impl(v, num_type);
  1178. }
  1179. template <typename T>
  1180. inline bool is_nan(const T v)
  1181. {
  1182. const typename details::number_type<T>::type num_type;
  1183. return is_nan_impl(v, num_type);
  1184. }
  1185. template <typename T>
  1186. inline T min(const T v0, const T v1)
  1187. {
  1188. const typename details::number_type<T>::type num_type;
  1189. return min_impl(v0, v1, num_type);
  1190. }
  1191. template <typename T>
  1192. inline T max(const T v0, const T v1)
  1193. {
  1194. const typename details::number_type<T>::type num_type;
  1195. return max_impl(v0, v1, num_type);
  1196. }
  1197. template <typename T>
  1198. inline T equal(const T v0, const T v1)
  1199. {
  1200. const typename details::number_type<T>::type num_type;
  1201. return equal_impl(v0, v1, num_type);
  1202. }
  1203. template <typename T>
  1204. inline T nequal(const T v0, const T v1)
  1205. {
  1206. const typename details::number_type<T>::type num_type;
  1207. return nequal_impl(v0, v1, num_type);
  1208. }
  1209. template <typename T>
  1210. inline T modulus(const T v0, const T v1)
  1211. {
  1212. const typename details::number_type<T>::type num_type;
  1213. return modulus_impl(v0, v1, num_type);
  1214. }
  1215. template <typename T>
  1216. inline T pow(const T v0, const T v1)
  1217. {
  1218. const typename details::number_type<T>::type num_type;
  1219. return pow_impl(v0, v1, num_type);
  1220. }
  1221. template <typename T>
  1222. inline T logn(const T v0, const T v1)
  1223. {
  1224. const typename details::number_type<T>::type num_type;
  1225. return logn_impl(v0, v1, num_type);
  1226. }
  1227. template <typename T>
  1228. inline T root(const T v0, const T v1)
  1229. {
  1230. const typename details::number_type<T>::type num_type;
  1231. return root_impl(v0, v1, num_type);
  1232. }
  1233. template <typename T>
  1234. inline T roundn(const T v0, const T v1)
  1235. {
  1236. const typename details::number_type<T>::type num_type;
  1237. return roundn_impl(v0, v1, num_type);
  1238. }
  1239. template <typename T>
  1240. inline T hypot(const T v0, const T v1)
  1241. {
  1242. const typename details::number_type<T>::type num_type;
  1243. return hypot_impl(v0, v1, num_type);
  1244. }
  1245. template <typename T>
  1246. inline T atan2(const T v0, const T v1)
  1247. {
  1248. const typename details::number_type<T>::type num_type;
  1249. return atan2_impl(v0, v1, num_type);
  1250. }
  1251. template <typename T>
  1252. inline T shr(const T v0, const T v1)
  1253. {
  1254. const typename details::number_type<T>::type num_type;
  1255. return shr_impl(v0, v1, num_type);
  1256. }
  1257. template <typename T>
  1258. inline T shl(const T v0, const T v1)
  1259. {
  1260. const typename details::number_type<T>::type num_type;
  1261. return shl_impl(v0, v1, num_type);
  1262. }
  1263. template <typename T>
  1264. inline T and_opr(const T v0, const T v1)
  1265. {
  1266. const typename details::number_type<T>::type num_type;
  1267. return and_impl(v0, v1, num_type);
  1268. }
  1269. template <typename T>
  1270. inline T nand_opr(const T v0, const T v1)
  1271. {
  1272. const typename details::number_type<T>::type num_type;
  1273. return nand_impl(v0, v1, num_type);
  1274. }
  1275. template <typename T>
  1276. inline T or_opr(const T v0, const T v1)
  1277. {
  1278. const typename details::number_type<T>::type num_type;
  1279. return or_impl(v0, v1, num_type);
  1280. }
  1281. template <typename T>
  1282. inline T nor_opr(const T v0, const T v1)
  1283. {
  1284. const typename details::number_type<T>::type num_type;
  1285. return nor_impl(v0, v1, num_type);
  1286. }
  1287. template <typename T>
  1288. inline T xor_opr(const T v0, const T v1)
  1289. {
  1290. const typename details::number_type<T>::type num_type;
  1291. return xor_impl(v0, v1, num_type);
  1292. }
  1293. template <typename T>
  1294. inline T xnor_opr(const T v0, const T v1)
  1295. {
  1296. const typename details::number_type<T>::type num_type;
  1297. return xnor_impl(v0, v1, num_type);
  1298. }
  1299. template <typename T>
  1300. inline bool is_integer(const T v)
  1301. {
  1302. const typename details::number_type<T>::type num_type;
  1303. return is_integer_impl(v, num_type);
  1304. }
  1305. template <typename T, unsigned int N>
  1306. struct fast_exp
  1307. {
  1308. static inline T result(T v)
  1309. {
  1310. unsigned int k = N;
  1311. T l = T(1);
  1312. while (k)
  1313. {
  1314. if (k & 1)
  1315. {
  1316. l *= v;
  1317. --k;
  1318. }
  1319. v *= v;
  1320. k >>= 1;
  1321. }
  1322. return l;
  1323. }
  1324. };
  1325. template <typename T> struct fast_exp<T,10> { static inline T result(T v) { T v_5 = fast_exp<T,5>::result(v); return v_5 * v_5; } };
  1326. template <typename T> struct fast_exp<T, 9> { static inline T result(T v) { return fast_exp<T,8>::result(v) * v; } };
  1327. template <typename T> struct fast_exp<T, 8> { static inline T result(T v) { T v_4 = fast_exp<T,4>::result(v); return v_4 * v_4; } };
  1328. template <typename T> struct fast_exp<T, 7> { static inline T result(T v) { return fast_exp<T,6>::result(v) * v; } };
  1329. template <typename T> struct fast_exp<T, 6> { static inline T result(T v) { T v_3 = fast_exp<T,3>::result(v); return v_3 * v_3; } };
  1330. template <typename T> struct fast_exp<T, 5> { static inline T result(T v) { return fast_exp<T,4>::result(v) * v; } };
  1331. template <typename T> struct fast_exp<T, 4> { static inline T result(T v) { T v_2 = v * v; return v_2 * v_2; } };
  1332. template <typename T> struct fast_exp<T, 3> { static inline T result(T v) { return v * v * v; } };
  1333. template <typename T> struct fast_exp<T, 2> { static inline T result(T v) { return v * v; } };
  1334. template <typename T> struct fast_exp<T, 1> { static inline T result(T v) { return v; } };
  1335. template <typename T> struct fast_exp<T, 0> { static inline T result(T ) { return T(1); } };
  1336. #define exprtk_define_unary_function(FunctionName) \
  1337. template <typename T> \
  1338. inline T FunctionName (const T v) \
  1339. { \
  1340. const typename details::number_type<T>::type num_type; \
  1341. return FunctionName##_impl(v,num_type); \
  1342. } \
  1343. exprtk_define_unary_function(abs )
  1344. exprtk_define_unary_function(acos )
  1345. exprtk_define_unary_function(acosh)
  1346. exprtk_define_unary_function(asin )
  1347. exprtk_define_unary_function(asinh)
  1348. exprtk_define_unary_function(atan )
  1349. exprtk_define_unary_function(atanh)
  1350. exprtk_define_unary_function(ceil )
  1351. exprtk_define_unary_function(cos )
  1352. exprtk_define_unary_function(cosh )
  1353. exprtk_define_unary_function(exp )
  1354. exprtk_define_unary_function(expm1)
  1355. exprtk_define_unary_function(floor)
  1356. exprtk_define_unary_function(log )
  1357. exprtk_define_unary_function(log10)
  1358. exprtk_define_unary_function(log2 )
  1359. exprtk_define_unary_function(log1p)
  1360. exprtk_define_unary_function(neg )
  1361. exprtk_define_unary_function(pos )
  1362. exprtk_define_unary_function(round)
  1363. exprtk_define_unary_function(sin )
  1364. exprtk_define_unary_function(sinc )
  1365. exprtk_define_unary_function(sinh )
  1366. exprtk_define_unary_function(sqrt )
  1367. exprtk_define_unary_function(tan )
  1368. exprtk_define_unary_function(tanh )
  1369. exprtk_define_unary_function(cot )
  1370. exprtk_define_unary_function(sec )
  1371. exprtk_define_unary_function(csc )
  1372. exprtk_define_unary_function(r2d )
  1373. exprtk_define_unary_function(d2r )
  1374. exprtk_define_unary_function(d2g )
  1375. exprtk_define_unary_function(g2d )
  1376. exprtk_define_unary_function(notl )
  1377. exprtk_define_unary_function(sgn )
  1378. exprtk_define_unary_function(erf )
  1379. exprtk_define_unary_function(erfc )
  1380. exprtk_define_unary_function(ncdf )
  1381. exprtk_define_unary_function(frac )
  1382. exprtk_define_unary_function(trunc)
  1383. #undef exprtk_define_unary_function
  1384. }
  1385. template <typename T>
  1386. inline T compute_pow10(T d, const int exponent)
  1387. {
  1388. static const double fract10[] =
  1389. {
  1390. 0.0,
  1391. 1.0E+001, 1.0E+002, 1.0E+003, 1.0E+004, 1.0E+005, 1.0E+006, 1.0E+007, 1.0E+008, 1.0E+009, 1.0E+010,
  1392. 1.0E+011, 1.0E+012, 1.0E+013, 1.0E+014, 1.0E+015, 1.0E+016, 1.0E+017, 1.0E+018, 1.0E+019, 1.0E+020,
  1393. 1.0E+021, 1.0E+022, 1.0E+023, 1.0E+024, 1.0E+025, 1.0E+026, 1.0E+027, 1.0E+028, 1.0E+029, 1.0E+030,
  1394. 1.0E+031, 1.0E+032, 1.0E+033, 1.0E+034, 1.0E+035, 1.0E+036, 1.0E+037, 1.0E+038, 1.0E+039, 1.0E+040,
  1395. 1.0E+041, 1.0E+042, 1.0E+043, 1.0E+044, 1.0E+045, 1.0E+046, 1.0E+047, 1.0E+048, 1.0E+049, 1.0E+050,
  1396. 1.0E+051, 1.0E+052, 1.0E+053, 1.0E+054, 1.0E+055, 1.0E+056, 1.0E+057, 1.0E+058, 1.0E+059, 1.0E+060,
  1397. 1.0E+061, 1.0E+062, 1.0E+063, 1.0E+064, 1.0E+065, 1.0E+066, 1.0E+067, 1.0E+068, 1.0E+069, 1.0E+070,
  1398. 1.0E+071, 1.0E+072, 1.0E+073, 1.0E+074, 1.0E+075, 1.0E+076, 1.0E+077, 1.0E+078, 1.0E+079, 1.0E+080,
  1399. 1.0E+081, 1.0E+082, 1.0E+083, 1.0E+084, 1.0E+085, 1.0E+086, 1.0E+087, 1.0E+088, 1.0E+089, 1.0E+090,
  1400. 1.0E+091, 1.0E+092, 1.0E+093, 1.0E+094, 1.0E+095, 1.0E+096, 1.0E+097, 1.0E+098, 1.0E+099, 1.0E+100,
  1401. 1.0E+101, 1.0E+102, 1.0E+103, 1.0E+104, 1.0E+105, 1.0E+106, 1.0E+107, 1.0E+108, 1.0E+109, 1.0E+110,
  1402. 1.0E+111, 1.0E+112, 1.0E+113, 1.0E+114, 1.0E+115, 1.0E+116, 1.0E+117, 1.0E+118, 1.0E+119, 1.0E+120,
  1403. 1.0E+121, 1.0E+122, 1.0E+123, 1.0E+124, 1.0E+125, 1.0E+126, 1.0E+127, 1.0E+128, 1.0E+129, 1.0E+130,
  1404. 1.0E+131, 1.0E+132, 1.0E+133, 1.0E+134, 1.0E+135, 1.0E+136, 1.0E+137, 1.0E+138, 1.0E+139, 1.0E+140,
  1405. 1.0E+141, 1.0E+142, 1.0E+143, 1.0E+144, 1.0E+145, 1.0E+146, 1.0E+147, 1.0E+148, 1.0E+149, 1.0E+150,
  1406. 1.0E+151, 1.0E+152, 1.0E+153, 1.0E+154, 1.0E+155, 1.0E+156, 1.0E+157, 1.0E+158, 1.0E+159, 1.0E+160,
  1407. 1.0E+161, 1.0E+162, 1.0E+163, 1.0E+164, 1.0E+165, 1.0E+166, 1.0E+167, 1.0E+168, 1.0E+169, 1.0E+170,
  1408. 1.0E+171, 1.0E+172, 1.0E+173, 1.0E+174, 1.0E+175, 1.0E+176, 1.0E+177, 1.0E+178, 1.0E+179, 1.0E+180,
  1409. 1.0E+181, 1.0E+182, 1.0E+183, 1.0E+184, 1.0E+185, 1.0E+186, 1.0E+187, 1.0E+188, 1.0E+189, 1.0E+190,
  1410. 1.0E+191, 1.0E+192, 1.0E+193, 1.0E+194, 1.0E+195, 1.0E+196, 1.0E+197, 1.0E+198, 1.0E+199, 1.0E+200,
  1411. 1.0E+201, 1.0E+202, 1.0E+203, 1.0E+204, 1.0E+205, 1.0E+206, 1.0E+207, 1.0E+208, 1.0E+209, 1.0E+210,
  1412. 1.0E+211, 1.0E+212, 1.0E+213, 1.0E+214, 1.0E+215, 1.0E+216, 1.0E+217, 1.0E+218, 1.0E+219, 1.0E+220,
  1413. 1.0E+221, 1.0E+222, 1.0E+223, 1.0E+224, 1.0E+225, 1.0E+226, 1.0E+227, 1.0E+228, 1.0E+229, 1.0E+230,
  1414. 1.0E+231, 1.0E+232, 1.0E+233, 1.0E+234, 1.0E+235, 1.0E+236, 1.0E+237, 1.0E+238, 1.0E+239, 1.0E+240,
  1415. 1.0E+241, 1.0E+242, 1.0E+243, 1.0E+244, 1.0E+245, 1.0E+246, 1.0E+247, 1.0E+248, 1.0E+249, 1.0E+250,
  1416. 1.0E+251, 1.0E+252, 1.0E+253, 1.0E+254, 1.0E+255, 1.0E+256, 1.0E+257, 1.0E+258, 1.0E+259, 1.0E+260,
  1417. 1.0E+261, 1.0E+262, 1.0E+263, 1.0E+264, 1.0E+265, 1.0E+266, 1.0E+267, 1.0E+268, 1.0E+269, 1.0E+270,
  1418. 1.0E+271, 1.0E+272, 1.0E+273, 1.0E+274, 1.0E+275, 1.0E+276, 1.0E+277, 1.0E+278, 1.0E+279, 1.0E+280,
  1419. 1.0E+281, 1.0E+282, 1.0E+283, 1.0E+284, 1.0E+285, 1.0E+286, 1.0E+287, 1.0E+288, 1.0E+289, 1.0E+290,
  1420. 1.0E+291, 1.0E+292, 1.0E+293, 1.0E+294, 1.0E+295, 1.0E+296, 1.0E+297, 1.0E+298, 1.0E+299, 1.0E+300,
  1421. 1.0E+301, 1.0E+302, 1.0E+303, 1.0E+304, 1.0E+305, 1.0E+306, 1.0E+307, 1.0E+308
  1422. };
  1423. static const int fract10_size = static_cast<int>(sizeof(fract10) / sizeof(double));
  1424. const int e = std::abs(exponent);
  1425. if (exponent >= std::numeric_limits<T>::min_exponent10)
  1426. {
  1427. if (e < fract10_size)
  1428. {
  1429. if (exponent > 0)
  1430. return T(d * fract10[e]);
  1431. else
  1432. return T(d / fract10[e]);
  1433. }
  1434. else
  1435. return T(d * std::pow(10.0, 10.0 * exponent));
  1436. }
  1437. else
  1438. {
  1439. d /= T(fract10[ -std::numeric_limits<T>::min_exponent10]);
  1440. return T(d / fract10[-exponent + std::numeric_limits<T>::min_exponent10]);
  1441. }
  1442. }
  1443. template <typename Iterator, typename T>
  1444. inline bool string_to_type_converter_impl_ref(Iterator& itr, const Iterator end, T& result)
  1445. {
  1446. if (itr == end)
  1447. return false;
  1448. const bool negative = ('-' == (*itr));
  1449. if (negative || ('+' == (*itr)))
  1450. {
  1451. if (end == ++itr)
  1452. return false;
  1453. }
  1454. static const uchar_t zero = static_cast<uchar_t>('0');
  1455. while ((end != itr) && (zero == (*itr))) ++itr;
  1456. bool return_result = true;
  1457. unsigned int digit = 0;
  1458. const std::size_t length = static_cast<std::size_t>(std::distance(itr,end));
  1459. if (length <= 4)
  1460. {
  1461. exprtk_disable_fallthrough_begin
  1462. switch (length)
  1463. {
  1464. #ifdef exprtk_use_lut
  1465. #define exprtk_process_digit \
  1466. if ((digit = details::digit_table[(int)*itr++]) < 10) \
  1467. result = result * 10 + (digit); \
  1468. else \
  1469. { \
  1470. return_result = false; \
  1471. break; \
  1472. } \
  1473. #else
  1474. #define exprtk_process_digit \
  1475. if ((digit = (*itr++ - zero)) < 10) \
  1476. result = result * T(10) + digit; \
  1477. else \
  1478. { \
  1479. return_result = false; \
  1480. break; \
  1481. } \
  1482. #endif
  1483. case 4 : exprtk_process_digit
  1484. case 3 : exprtk_process_digit
  1485. case 2 : exprtk_process_digit
  1486. case 1 : if ((digit = (*itr - zero))>= 10) { digit = 0; return_result = false; }
  1487. #undef exprtk_process_digit
  1488. }
  1489. exprtk_disable_fallthrough_end
  1490. }
  1491. else
  1492. return_result = false;
  1493. if (length && return_result)
  1494. {
  1495. result = result * 10 + static_cast<T>(digit);
  1496. ++itr;
  1497. }
  1498. result = negative ? -result : result;
  1499. return return_result;
  1500. }
  1501. template <typename Iterator, typename T>
  1502. static inline bool parse_nan(Iterator& itr, const Iterator end, T& t)
  1503. {
  1504. typedef typename std::iterator_traits<Iterator>::value_type type;
  1505. static const std::size_t nan_length = 3;
  1506. if (std::distance(itr,end) != static_cast<int>(nan_length))
  1507. return false;
  1508. if (static_cast<type>('n') == (*itr))
  1509. {
  1510. if (
  1511. (static_cast<type>('a') != *(itr + 1)) ||
  1512. (static_cast<type>('n') != *(itr + 2))
  1513. )
  1514. {
  1515. return false;
  1516. }
  1517. }
  1518. else if (
  1519. (static_cast<type>('A') != *(itr + 1)) ||
  1520. (static_cast<type>('N') != *(itr + 2))
  1521. )
  1522. {
  1523. return false;
  1524. }
  1525. t = std::numeric_limits<T>::quiet_NaN();
  1526. return true;
  1527. }
  1528. template <typename Iterator, typename T>
  1529. static inline bool parse_inf(Iterator& itr, const Iterator end, T& t, bool negative)
  1530. {
  1531. static const char_t inf_uc[] = "INFINITY";
  1532. static const char_t inf_lc[] = "infinity";
  1533. static const std::size_t inf_length = 8;
  1534. const std::size_t length = static_cast<std::size_t>(std::distance(itr,end));
  1535. if ((3 != length) && (inf_length != length))
  1536. return false;
  1537. char_cptr inf_itr = ('i' == (*itr)) ? inf_lc : inf_uc;
  1538. while (end != itr)
  1539. {
  1540. if (*inf_itr == static_cast<char>(*itr))
  1541. {
  1542. ++itr;
  1543. ++inf_itr;
  1544. continue;
  1545. }
  1546. else
  1547. return false;
  1548. }
  1549. if (negative)
  1550. t = -std::numeric_limits<T>::infinity();
  1551. else
  1552. t = std::numeric_limits<T>::infinity();
  1553. return true;
  1554. }
  1555. template <typename Iterator, typename T>
  1556. inline bool string_to_real(Iterator& itr_external, const Iterator end, T& t, numeric::details::real_type_tag)
  1557. {
  1558. if (end == itr_external) return false;
  1559. Iterator itr = itr_external;
  1560. T d = T(0);
  1561. const bool negative = ('-' == (*itr));
  1562. if (negative || '+' == (*itr))
  1563. {
  1564. if (end == ++itr)
  1565. return false;
  1566. }
  1567. bool instate = false;
  1568. static const char_t zero = static_cast<uchar_t>('0');
  1569. #define parse_digit_1(d) \
  1570. if ((digit = (*itr - zero)) < 10) \
  1571. { d = d * T(10) + digit; } \
  1572. else \
  1573. { break; } \
  1574. if (end == ++itr) break; \
  1575. #define parse_digit_2(d) \
  1576. if ((digit = (*itr - zero)) < 10) \
  1577. { d = d * T(10) + digit; } \
  1578. else { break; } \
  1579. ++itr; \
  1580. if ('.' != (*itr))
  1581. {
  1582. const Iterator curr = itr;
  1583. while ((end != itr) && (zero == (*itr))) ++itr;
  1584. unsigned int digit;
  1585. while (end != itr)
  1586. {
  1587. // Note: For 'physical' superscalar architectures it
  1588. // is advised that the following loop be: 4xPD1 and 1xPD2
  1589. #ifdef exprtk_enable_superscalar
  1590. parse_digit_1(d)
  1591. parse_digit_1(d)
  1592. #endif
  1593. parse_digit_1(d)
  1594. parse_digit_1(d)
  1595. parse_digit_2(d)
  1596. }
  1597. if (curr != itr) instate = true;
  1598. }
  1599. int exponent = 0;
  1600. if (end != itr)
  1601. {
  1602. if ('.' == (*itr))
  1603. {
  1604. const Iterator curr = ++itr;
  1605. unsigned int digit;
  1606. T tmp_d = T(0);
  1607. while (end != itr)
  1608. {
  1609. #ifdef exprtk_enable_superscalar
  1610. parse_digit_1(tmp_d)
  1611. parse_digit_1(tmp_d)
  1612. parse_digit_1(tmp_d)
  1613. #endif
  1614. parse_digit_1(tmp_d)
  1615. parse_digit_1(tmp_d)
  1616. parse_digit_2(tmp_d)
  1617. }
  1618. if (curr != itr)
  1619. {
  1620. instate = true;
  1621. d += compute_pow10(tmp_d,static_cast<int>(-std::distance(curr,itr)));
  1622. }
  1623. #undef parse_digit_1
  1624. #undef parse_digit_2
  1625. }
  1626. if (end != itr)
  1627. {
  1628. typename std::iterator_traits<Iterator>::value_type c = (*itr);
  1629. if (('e' == c) || ('E' == c))
  1630. {
  1631. int exp = 0;
  1632. if (!details::string_to_type_converter_impl_ref(++itr, end, exp))
  1633. {
  1634. if (end == itr)
  1635. return false;
  1636. else
  1637. c = (*itr);
  1638. }
  1639. exponent += exp;
  1640. }
  1641. if (end != itr)
  1642. {
  1643. if (('f' == c) || ('F' == c) || ('l' == c) || ('L' == c))
  1644. ++itr;
  1645. else if ('#' == c)
  1646. {
  1647. if (end == ++itr)
  1648. return false;
  1649. else if (('I' <= (*itr)) && ((*itr) <= 'n'))
  1650. {
  1651. if (('i' == (*itr)) || ('I' == (*itr)))
  1652. {
  1653. return parse_inf(itr, end, t, negative);
  1654. }
  1655. else if (('n' == (*itr)) || ('N' == (*itr)))
  1656. {
  1657. return parse_nan(itr, end, t);
  1658. }
  1659. else
  1660. return false;
  1661. }
  1662. else
  1663. return false;
  1664. }
  1665. else if (('I' <= (*itr)) && ((*itr) <= 'n'))
  1666. {
  1667. if (('i' == (*itr)) || ('I' == (*itr)))
  1668. {
  1669. return parse_inf(itr, end, t, negative);
  1670. }
  1671. else if (('n' == (*itr)) || ('N' == (*itr)))
  1672. {
  1673. return parse_nan(itr, end, t);
  1674. }
  1675. else
  1676. return false;
  1677. }
  1678. else
  1679. return false;
  1680. }
  1681. }
  1682. }
  1683. if ((end != itr) || (!instate))
  1684. return false;
  1685. else if (exponent)
  1686. d = compute_pow10(d,exponent);
  1687. t = static_cast<T>((negative) ? -d : d);
  1688. return true;
  1689. }
  1690. template <typename T>
  1691. inline bool string_to_real(const std::string& s, T& t)
  1692. {
  1693. const typename numeric::details::number_type<T>::type num_type;
  1694. char_cptr begin = s.data();
  1695. char_cptr end = s.data() + s.size();
  1696. return string_to_real(begin, end, t, num_type);
  1697. }
  1698. template <typename T>
  1699. struct functor_t
  1700. {
  1701. /*
  1702. Note: The following definitions for Type, may require tweaking
  1703. based on the compiler and target architecture. The benchmark
  1704. should provide enough information to make the right choice.
  1705. */
  1706. //typedef T Type;
  1707. //typedef const T Type;
  1708. typedef const T& Type;
  1709. typedef T& RefType;
  1710. typedef T (*qfunc_t)(Type t0, Type t1, Type t2, Type t3);
  1711. typedef T (*tfunc_t)(Type t0, Type t1, Type t2);
  1712. typedef T (*bfunc_t)(Type t0, Type t1);
  1713. typedef T (*ufunc_t)(Type t0);
  1714. };
  1715. } // namespace details
  1716. namespace lexer
  1717. {
  1718. struct token
  1719. {
  1720. enum token_type
  1721. {
  1722. e_none = 0, e_error = 1, e_err_symbol = 2,
  1723. e_err_number = 3, e_err_string = 4, e_err_sfunc = 5,
  1724. e_eof = 6, e_number = 7, e_symbol = 8,
  1725. e_string = 9, e_assign = 10, e_addass = 11,
  1726. e_subass = 12, e_mulass = 13, e_divass = 14,
  1727. e_modass = 15, e_shr = 16, e_shl = 17,
  1728. e_lte = 18, e_ne = 19, e_gte = 20,
  1729. e_swap = 21, e_lt = '<', e_gt = '>',
  1730. e_eq = '=', e_rbracket = ')', e_lbracket = '(',
  1731. e_rsqrbracket = ']', e_lsqrbracket = '[', e_rcrlbracket = '}',
  1732. e_lcrlbracket = '{', e_comma = ',', e_add = '+',
  1733. e_sub = '-', e_div = '/', e_mul = '*',
  1734. e_mod = '%', e_pow = '^', e_colon = ':',
  1735. e_ternary = '?'
  1736. };
  1737. token()
  1738. : type(e_none),
  1739. value(""),
  1740. position(std::numeric_limits<std::size_t>::max())
  1741. {}
  1742. void clear()
  1743. {
  1744. type = e_none;
  1745. value = "";
  1746. position = std::numeric_limits<std::size_t>::max();
  1747. }
  1748. template <typename Iterator>
  1749. inline token& set_operator(const token_type tt,
  1750. const Iterator begin, const Iterator end,
  1751. const Iterator base_begin = Iterator(0))
  1752. {
  1753. type = tt;
  1754. value.assign(begin,end);
  1755. if (base_begin)
  1756. position = static_cast<std::size_t>(std::distance(base_begin,begin));
  1757. return (*this);
  1758. }
  1759. template <typename Iterator>
  1760. inline token& set_symbol(const Iterator begin, const Iterator end, const Iterator base_begin = Iterator(0))
  1761. {
  1762. type = e_symbol;
  1763. value.assign(begin,end);
  1764. if (base_begin)
  1765. position = static_cast<std::size_t>(std::distance(base_begin,begin));
  1766. return (*this);
  1767. }
  1768. template <typename Iterator>
  1769. inline token& set_numeric(const Iterator begin, const Iterator end, const Iterator base_begin = Iterator(0))
  1770. {
  1771. type = e_number;
  1772. value.assign(begin,end);
  1773. if (base_begin)
  1774. position = static_cast<std::size_t>(std::distance(base_begin,begin));
  1775. return (*this);
  1776. }
  1777. template <typename Iterator>
  1778. inline token& set_string(const Iterator begin, const Iterator end, const Iterator base_begin = Iterator(0))
  1779. {
  1780. type = e_string;
  1781. value.assign(begin,end);
  1782. if (base_begin)
  1783. position = static_cast<std::size_t>(std::distance(base_begin,begin));
  1784. return (*this);
  1785. }
  1786. inline token& set_string(const std::string& s, const std::size_t p)
  1787. {
  1788. type = e_string;
  1789. value = s;
  1790. position = p;
  1791. return (*this);
  1792. }
  1793. template <typename Iterator>
  1794. inline token& set_error(const token_type et,
  1795. const Iterator begin, const Iterator end,
  1796. const Iterator base_begin = Iterator(0))
  1797. {
  1798. if (
  1799. (e_error == et) ||
  1800. (e_err_symbol == et) ||
  1801. (e_err_number == et) ||
  1802. (e_err_string == et) ||
  1803. (e_err_sfunc == et)
  1804. )
  1805. {
  1806. type = et;
  1807. }
  1808. else
  1809. type = e_error;
  1810. value.assign(begin,end);
  1811. if (base_begin)
  1812. position = static_cast<std::size_t>(std::distance(base_begin,begin));
  1813. return (*this);
  1814. }
  1815. static inline std::string to_str(token_type t)
  1816. {
  1817. switch (t)
  1818. {
  1819. case e_none : return "NONE";
  1820. case e_error : return "ERROR";
  1821. case e_err_symbol : return "ERROR_SYMBOL";
  1822. case e_err_number : return "ERROR_NUMBER";
  1823. case e_err_string : return "ERROR_STRING";
  1824. case e_eof : return "EOF";
  1825. case e_number : return "NUMBER";
  1826. case e_symbol : return "SYMBOL";
  1827. case e_string : return "STRING";
  1828. case e_assign : return ":=";
  1829. case e_addass : return "+=";
  1830. case e_subass : return "-=";
  1831. case e_mulass : return "*=";
  1832. case e_divass : return "/=";
  1833. case e_modass : return "%=";
  1834. case e_shr : return ">>";
  1835. case e_shl : return "<<";
  1836. case e_lte : return "<=";
  1837. case e_ne : return "!=";
  1838. case e_gte : return ">=";
  1839. case e_lt : return "<";
  1840. case e_gt : return ">";
  1841. case e_eq : return "=";
  1842. case e_rbracket : return ")";
  1843. case e_lbracket : return "(";
  1844. case e_rsqrbracket : return "]";
  1845. case e_lsqrbracket : return "[";
  1846. case e_rcrlbracket : return "}";
  1847. case e_lcrlbracket : return "{";
  1848. case e_comma : return ",";
  1849. case e_add : return "+";
  1850. case e_sub : return "-";
  1851. case e_div : return "/";
  1852. case e_mul : return "*";
  1853. case e_mod : return "%";
  1854. case e_pow : return "^";
  1855. case e_colon : return ":";
  1856. case e_ternary : return "?";
  1857. case e_swap : return "<=>";
  1858. default : return "UNKNOWN";
  1859. }
  1860. }
  1861. inline bool is_error() const
  1862. {
  1863. return (
  1864. (e_error == type) ||
  1865. (e_err_symbol == type) ||
  1866. (e_err_number == type) ||
  1867. (e_err_string == type) ||
  1868. (e_err_sfunc == type)
  1869. );
  1870. }
  1871. token_type type;
  1872. std::string value;
  1873. std::size_t position;
  1874. };
  1875. class generator
  1876. {
  1877. public:
  1878. typedef token token_t;
  1879. typedef std::vector<token_t> token_list_t;
  1880. typedef std::vector<token_t>::iterator token_list_itr_t;
  1881. typedef details::char_t char_t;
  1882. generator()
  1883. : base_itr_(0),
  1884. s_itr_ (0),
  1885. s_end_ (0)
  1886. {
  1887. clear();
  1888. }
  1889. inline void clear()
  1890. {
  1891. base_itr_ = 0;
  1892. s_itr_ = 0;
  1893. s_end_ = 0;
  1894. token_list_.clear();
  1895. token_itr_ = token_list_.end();
  1896. store_token_itr_ = token_list_.end();
  1897. }
  1898. inline bool process(const std::string& str)
  1899. {
  1900. base_itr_ = str.data();
  1901. s_itr_ = str.data();
  1902. s_end_ = str.data() + str.size();
  1903. eof_token_.set_operator(token_t::e_eof,s_end_,s_end_,base_itr_);
  1904. token_list_.clear();
  1905. while (!is_end(s_itr_))
  1906. {
  1907. scan_token();
  1908. if (!token_list_.empty() && token_list_.back().is_error())
  1909. return false;
  1910. }
  1911. return true;
  1912. }
  1913. inline bool empty() const
  1914. {
  1915. return token_list_.empty();
  1916. }
  1917. inline std::size_t size() const
  1918. {
  1919. return token_list_.size();
  1920. }
  1921. inline void begin()
  1922. {
  1923. token_itr_ = token_list_.begin();
  1924. store_token_itr_ = token_list_.begin();
  1925. }
  1926. inline void store()
  1927. {
  1928. store_token_itr_ = token_itr_;
  1929. }
  1930. inline void restore()
  1931. {
  1932. token_itr_ = store_token_itr_;
  1933. }
  1934. inline token_t& next_token()
  1935. {
  1936. if (token_list_.end() != token_itr_)
  1937. {
  1938. return *token_itr_++;
  1939. }
  1940. else
  1941. return eof_token_;
  1942. }
  1943. inline token_t& peek_next_token()
  1944. {
  1945. if (token_list_.end() != token_itr_)
  1946. {
  1947. return *token_itr_;
  1948. }
  1949. else
  1950. return eof_token_;
  1951. }
  1952. inline token_t& operator[](const std::size_t& index)
  1953. {
  1954. if (index < token_list_.size())
  1955. return token_list_[index];
  1956. else
  1957. return eof_token_;
  1958. }
  1959. inline token_t operator[](const std::size_t& index) const
  1960. {
  1961. if (index < token_list_.size())
  1962. return token_list_[index];
  1963. else
  1964. return eof_token_;
  1965. }
  1966. inline bool finished() const
  1967. {
  1968. return (token_list_.end() == token_itr_);
  1969. }
  1970. inline void insert_front(token_t::token_type tk_type)
  1971. {
  1972. if (
  1973. !token_list_.empty() &&
  1974. (token_list_.end() != token_itr_)
  1975. )
  1976. {
  1977. token_t t = *token_itr_;
  1978. t.type = tk_type;
  1979. token_itr_ = token_list_.insert(token_itr_,t);
  1980. }
  1981. }
  1982. inline std::string substr(const std::size_t& begin, const std::size_t& end)
  1983. {
  1984. const details::char_cptr begin_itr = ((base_itr_ + begin) < s_end_) ? (base_itr_ + begin) : s_end_;
  1985. const details::char_cptr end_itr = ((base_itr_ + end) < s_end_) ? (base_itr_ + end) : s_end_;
  1986. return std::string(begin_itr,end_itr);
  1987. }
  1988. inline std::string remaining() const
  1989. {
  1990. if (finished())
  1991. return "";
  1992. else if (token_list_.begin() != token_itr_)
  1993. return std::string(base_itr_ + (token_itr_ - 1)->position, s_end_);
  1994. else
  1995. return std::string(base_itr_ + token_itr_->position, s_end_);
  1996. }
  1997. private:
  1998. inline bool is_end(details::char_cptr itr)
  1999. {
  2000. return (s_end_ == itr);
  2001. }
  2002. inline bool is_comment_start(details::char_cptr itr)
  2003. {
  2004. #ifndef exprtk_disable_comments
  2005. const char_t c0 = *(itr + 0);
  2006. const char_t c1 = *(itr + 1);
  2007. if ('#' == c0)
  2008. return true;
  2009. else if (!is_end(itr + 1))
  2010. {
  2011. if (('/' == c0) && ('/' == c1)) return true;
  2012. if (('/' == c0) && ('*' == c1)) return true;
  2013. }
  2014. #endif
  2015. return false;
  2016. }
  2017. inline void skip_whitespace()
  2018. {
  2019. while (!is_end(s_itr_) && details::is_whitespace(*s_itr_))
  2020. {
  2021. ++s_itr_;
  2022. }
  2023. }
  2024. inline void skip_comments()
  2025. {
  2026. #ifndef exprtk_disable_comments
  2027. // The following comment styles are supported:
  2028. // 1. // .... \n
  2029. // 2. # .... \n
  2030. // 3. /* .... */
  2031. struct test
  2032. {
  2033. static inline bool comment_start(const char_t c0, const char_t c1, int& mode, int& incr)
  2034. {
  2035. mode = 0;
  2036. if ('#' == c0) { mode = 1; incr = 1; }
  2037. else if ('/' == c0)
  2038. {
  2039. if ('/' == c1) { mode = 1; incr = 2; }
  2040. else if ('*' == c1) { mode = 2; incr = 2; }
  2041. }
  2042. return (0 != mode);
  2043. }
  2044. static inline bool comment_end(const char_t c0, const char_t c1, int& mode)
  2045. {
  2046. if (
  2047. ((1 == mode) && ('\n' == c0)) ||
  2048. ((2 == mode) && ( '*' == c0) && ('/' == c1))
  2049. )
  2050. {
  2051. mode = 0;
  2052. return true;
  2053. }
  2054. else
  2055. return false;
  2056. }
  2057. };
  2058. int mode = 0;
  2059. int increment = 0;
  2060. if (is_end(s_itr_))
  2061. return;
  2062. else if (!test::comment_start(*s_itr_, *(s_itr_ + 1), mode, increment))
  2063. return;
  2064. details::char_cptr cmt_start = s_itr_;
  2065. s_itr_ += increment;
  2066. while (!is_end(s_itr_))
  2067. {
  2068. if ((1 == mode) && test::comment_end(*s_itr_, 0, mode))
  2069. {
  2070. ++s_itr_;
  2071. return;
  2072. }
  2073. if ((2 == mode))
  2074. {
  2075. if (!is_end((s_itr_ + 1)) && test::comment_end(*s_itr_, *(s_itr_ + 1), mode))
  2076. {
  2077. s_itr_ += 2;
  2078. return;
  2079. }
  2080. }
  2081. ++s_itr_;
  2082. }
  2083. if (2 == mode)
  2084. {
  2085. token_t t;
  2086. t.set_error(token::e_error, cmt_start, cmt_start + mode, base_itr_);
  2087. token_list_.push_back(t);
  2088. }
  2089. #endif
  2090. }
  2091. inline void scan_token()
  2092. {
  2093. if (details::is_whitespace(*s_itr_))
  2094. {
  2095. skip_whitespace();
  2096. return;
  2097. }
  2098. else if (is_comment_start(s_itr_))
  2099. {
  2100. skip_comments();
  2101. return;
  2102. }
  2103. else if (details::is_operator_char(*s_itr_))
  2104. {
  2105. scan_operator();
  2106. return;
  2107. }
  2108. else if (details::is_letter(*s_itr_))
  2109. {
  2110. scan_symbol();
  2111. return;
  2112. }
  2113. else if (details::is_digit((*s_itr_)) || ('.' == (*s_itr_)))
  2114. {
  2115. scan_number();
  2116. return;
  2117. }
  2118. else if ('$' == (*s_itr_))
  2119. {
  2120. scan_special_function();
  2121. return;
  2122. }
  2123. #ifndef exprtk_disable_string_capabilities
  2124. else if ('\'' == (*s_itr_))
  2125. {
  2126. scan_string();
  2127. return;
  2128. }
  2129. #endif
  2130. else if ('~' == (*s_itr_))
  2131. {
  2132. token_t t;
  2133. t.set_symbol(s_itr_, s_itr_ + 1, base_itr_);
  2134. token_list_.push_back(t);
  2135. ++s_itr_;
  2136. return;
  2137. }
  2138. else
  2139. {
  2140. token_t t;
  2141. t.set_error(token::e_error, s_itr_, s_itr_ + 2, base_itr_);
  2142. token_list_.push_back(t);
  2143. ++s_itr_;
  2144. }
  2145. }
  2146. inline void scan_operator()
  2147. {
  2148. token_t t;
  2149. const char_t c0 = s_itr_[0];
  2150. if (!is_end(s_itr_ + 1))
  2151. {
  2152. const char_t c1 = s_itr_[1];
  2153. if (!is_end(s_itr_ + 2))
  2154. {
  2155. const char_t c2 = s_itr_[2];
  2156. if ((c0 == '<') && (c1 == '=') && (c2 == '>'))
  2157. {
  2158. t.set_operator(token_t::e_swap, s_itr_, s_itr_ + 3, base_itr_);
  2159. token_list_.push_back(t);
  2160. s_itr_ += 3;
  2161. return;
  2162. }
  2163. }
  2164. token_t::token_type ttype = token_t::e_none;
  2165. if ((c0 == '<') && (c1 == '=')) ttype = token_t::e_lte;
  2166. else if ((c0 == '>') && (c1 == '=')) ttype = token_t::e_gte;
  2167. else if ((c0 == '<') && (c1 == '>')) ttype = token_t::e_ne;
  2168. else if ((c0 == '!') && (c1 == '=')) ttype = token_t::e_ne;
  2169. else if ((c0 == '=') && (c1 == '=')) ttype = token_t::e_eq;
  2170. else if ((c0 == ':') && (c1 == '=')) ttype = token_t::e_assign;
  2171. else if ((c0 == '<') && (c1 == '<')) ttype = token_t::e_shl;
  2172. else if ((c0 == '>') && (c1 == '>')) ttype = token_t::e_shr;
  2173. else if ((c0 == '+') && (c1 == '=')) ttype = token_t::e_addass;
  2174. else if ((c0 == '-') && (c1 == '=')) ttype = token_t::e_subass;
  2175. else if ((c0 == '*') && (c1 == '=')) ttype = token_t::e_mulass;
  2176. else if ((c0 == '/') && (c1 == '=')) ttype = token_t::e_divass;
  2177. else if ((c0 == '%') && (c1 == '=')) ttype = token_t::e_modass;
  2178. if (token_t::e_none != ttype)
  2179. {
  2180. t.set_operator(ttype, s_itr_, s_itr_ + 2, base_itr_);
  2181. token_list_.push_back(t);
  2182. s_itr_ += 2;
  2183. return;
  2184. }
  2185. }
  2186. if ('<' == c0)
  2187. t.set_operator(token_t::e_lt , s_itr_, s_itr_ + 1, base_itr_);
  2188. else if ('>' == c0)
  2189. t.set_operator(token_t::e_gt , s_itr_, s_itr_ + 1, base_itr_);
  2190. else if (';' == c0)
  2191. t.set_operator(token_t::e_eof, s_itr_, s_itr_ + 1, base_itr_);
  2192. else if ('&' == c0)
  2193. t.set_symbol(s_itr_, s_itr_ + 1, base_itr_);
  2194. else if ('|' == c0)
  2195. t.set_symbol(s_itr_, s_itr_ + 1, base_itr_);
  2196. else
  2197. t.set_operator(token_t::token_type(c0), s_itr_, s_itr_ + 1, base_itr_);
  2198. token_list_.push_back(t);
  2199. ++s_itr_;
  2200. }
  2201. inline void scan_symbol()
  2202. {
  2203. details::char_cptr initial_itr = s_itr_;
  2204. while (!is_end(s_itr_))
  2205. {
  2206. if (!details::is_letter_or_digit(*s_itr_) && ('_' != (*s_itr_)))
  2207. {
  2208. if ('.' != (*s_itr_))
  2209. break;
  2210. /*
  2211. Permit symbols that contain a 'dot'
  2212. Allowed : abc.xyz, a123.xyz, abc.123, abc_.xyz a123_.xyz abc._123
  2213. Disallowed: .abc, abc.<white-space>, abc.<eof>, abc.<operator +,-,*,/...>
  2214. */
  2215. if (
  2216. (s_itr_ != initial_itr) &&
  2217. !is_end(s_itr_ + 1) &&
  2218. !details::is_letter_or_digit(*(s_itr_ + 1)) &&
  2219. ('_' != (*(s_itr_ + 1)))
  2220. )
  2221. break;
  2222. }
  2223. ++s_itr_;
  2224. }
  2225. token_t t;
  2226. t.set_symbol(initial_itr,s_itr_,base_itr_);
  2227. token_list_.push_back(t);
  2228. }
  2229. inline void scan_number()
  2230. {
  2231. /*
  2232. Attempt to match a valid numeric value in one of the following formats:
  2233. (01) 123456
  2234. (02) 123456.
  2235. (03) 123.456
  2236. (04) 123.456e3
  2237. (05) 123.456E3
  2238. (06) 123.456e+3
  2239. (07) 123.456E+3
  2240. (08) 123.456e-3
  2241. (09) 123.456E-3
  2242. (00) .1234
  2243. (11) .1234e3
  2244. (12) .1234E+3
  2245. (13) .1234e+3
  2246. (14) .1234E-3
  2247. (15) .1234e-3
  2248. */
  2249. details::char_cptr initial_itr = s_itr_;
  2250. bool dot_found = false;
  2251. bool e_found = false;
  2252. bool post_e_sign_found = false;
  2253. bool post_e_digit_found = false;
  2254. token_t t;
  2255. while (!is_end(s_itr_))
  2256. {
  2257. if ('.' == (*s_itr_))
  2258. {
  2259. if (dot_found)
  2260. {
  2261. t.set_error(token::e_err_number, initial_itr, s_itr_, base_itr_);
  2262. token_list_.push_back(t);
  2263. return;
  2264. }
  2265. dot_found = true;
  2266. ++s_itr_;
  2267. continue;
  2268. }
  2269. else if ('e' == std::tolower(*s_itr_))
  2270. {
  2271. const char_t& c = *(s_itr_ + 1);
  2272. if (is_end(s_itr_ + 1))
  2273. {
  2274. t.set_error(token::e_err_number, initial_itr, s_itr_, base_itr_);
  2275. token_list_.push_back(t);
  2276. return;
  2277. }
  2278. else if (
  2279. ('+' != c) &&
  2280. ('-' != c) &&
  2281. !details::is_digit(c)
  2282. )
  2283. {
  2284. t.set_error(token::e_err_number, initial_itr, s_itr_, base_itr_);
  2285. token_list_.push_back(t);
  2286. return;
  2287. }
  2288. e_found = true;
  2289. ++s_itr_;
  2290. continue;
  2291. }
  2292. else if (e_found && details::is_sign(*s_itr_) && !post_e_digit_found)
  2293. {
  2294. if (post_e_sign_found)
  2295. {
  2296. t.set_error(token::e_err_number, initial_itr, s_itr_, base_itr_);
  2297. token_list_.push_back(t);
  2298. return;
  2299. }
  2300. post_e_sign_found = true;
  2301. ++s_itr_;
  2302. continue;
  2303. }
  2304. else if (e_found && details::is_digit(*s_itr_))
  2305. {
  2306. post_e_digit_found = true;
  2307. ++s_itr_;
  2308. continue;
  2309. }
  2310. else if (('.' != (*s_itr_)) && !details::is_digit(*s_itr_))
  2311. break;
  2312. else
  2313. ++s_itr_;
  2314. }
  2315. t.set_numeric(initial_itr, s_itr_, base_itr_);
  2316. token_list_.push_back(t);
  2317. return;
  2318. }
  2319. inline void scan_special_function()
  2320. {
  2321. details::char_cptr initial_itr = s_itr_;
  2322. token_t t;
  2323. // $fdd(x,x,x) = at least 11 chars
  2324. if (std::distance(s_itr_,s_end_) < 11)
  2325. {
  2326. t.set_error(token::e_err_sfunc, initial_itr, s_itr_, base_itr_);
  2327. token_list_.push_back(t);
  2328. return;
  2329. }
  2330. if (
  2331. !(('$' == *s_itr_) &&
  2332. (details::imatch ('f',*(s_itr_ + 1))) &&
  2333. (details::is_digit(*(s_itr_ + 2))) &&
  2334. (details::is_digit(*(s_itr_ + 3))))
  2335. )
  2336. {
  2337. t.set_error(token::e_err_sfunc, initial_itr, s_itr_, base_itr_);
  2338. token_list_.push_back(t);
  2339. return;
  2340. }
  2341. s_itr_ += 4; // $fdd = 4chars
  2342. t.set_symbol(initial_itr, s_itr_, base_itr_);
  2343. token_list_.push_back(t);
  2344. return;
  2345. }
  2346. #ifndef exprtk_disable_string_capabilities
  2347. inline void scan_string()
  2348. {
  2349. details::char_cptr initial_itr = s_itr_ + 1;
  2350. token_t t;
  2351. if (std::distance(s_itr_,s_end_) < 2)
  2352. {
  2353. t.set_error(token::e_err_string, s_itr_, s_end_, base_itr_);
  2354. token_list_.push_back(t);
  2355. return;
  2356. }
  2357. ++s_itr_;
  2358. bool escaped_found = false;
  2359. bool escaped = false;
  2360. while (!is_end(s_itr_))
  2361. {
  2362. if (!escaped && ('\\' == *s_itr_))
  2363. {
  2364. escaped_found = true;
  2365. escaped = true;
  2366. ++s_itr_;
  2367. continue;
  2368. }
  2369. else if (!escaped)
  2370. {
  2371. if ('\'' == *s_itr_)
  2372. break;
  2373. }
  2374. else if (escaped)
  2375. {
  2376. if (!is_end(s_itr_) && ('0' == *(s_itr_)))
  2377. {
  2378. /*
  2379. Note: The following 'awkward' conditional is
  2380. due to various broken msvc compilers.
  2381. */
  2382. #if defined(_MSC_VER) && (_MSC_VER == 1600)
  2383. const bool within_range = !is_end(s_itr_ + 2) &&
  2384. !is_end(s_itr_ + 3) ;
  2385. #else
  2386. const bool within_range = !is_end(s_itr_ + 1) &&
  2387. !is_end(s_itr_ + 2) &&
  2388. !is_end(s_itr_ + 3) ;
  2389. #endif
  2390. const bool x_seperator = ('x' == *(s_itr_ + 1)) ||
  2391. ('X' == *(s_itr_ + 1)) ;
  2392. const bool both_digits = details::is_hex_digit(*(s_itr_ + 2)) &&
  2393. details::is_hex_digit(*(s_itr_ + 3)) ;
  2394. if (!within_range || !x_seperator || !both_digits)
  2395. {
  2396. t.set_error(token::e_err_string, initial_itr, s_itr_, base_itr_);
  2397. token_list_.push_back(t);
  2398. return;
  2399. }
  2400. else
  2401. s_itr_ += 3;
  2402. }
  2403. escaped = false;
  2404. }
  2405. ++s_itr_;
  2406. }
  2407. if (is_end(s_itr_))
  2408. {
  2409. t.set_error(token::e_err_string, initial_itr, s_itr_, base_itr_);
  2410. token_list_.push_back(t);
  2411. return;
  2412. }
  2413. if (!escaped_found)
  2414. t.set_string(initial_itr, s_itr_, base_itr_);
  2415. else
  2416. {
  2417. std::string parsed_string(initial_itr,s_itr_);
  2418. details::cleanup_escapes(parsed_string);
  2419. t.set_string(
  2420. parsed_string,
  2421. static_cast<std::size_t>(std::distance(base_itr_,initial_itr)));
  2422. }
  2423. token_list_.push_back(t);
  2424. ++s_itr_;
  2425. return;
  2426. }
  2427. #endif
  2428. private:
  2429. token_list_t token_list_;
  2430. token_list_itr_t token_itr_;
  2431. token_list_itr_t store_token_itr_;
  2432. token_t eof_token_;
  2433. details::char_cptr base_itr_;
  2434. details::char_cptr s_itr_;
  2435. details::char_cptr s_end_;
  2436. friend class token_scanner;
  2437. friend class token_modifier;
  2438. friend class token_inserter;
  2439. friend class token_joiner;
  2440. };
  2441. class helper_interface
  2442. {
  2443. public:
  2444. virtual void init() { }
  2445. virtual void reset() { }
  2446. virtual bool result() { return true; }
  2447. virtual std::size_t process(generator&) { return 0; }
  2448. virtual ~helper_interface() { }
  2449. };
  2450. class token_scanner : public helper_interface
  2451. {
  2452. public:
  2453. virtual ~token_scanner()
  2454. {}
  2455. explicit token_scanner(const std::size_t& stride)
  2456. : stride_(stride)
  2457. {
  2458. if (stride > 4)
  2459. {
  2460. throw std::invalid_argument("token_scanner() - Invalid stride value");
  2461. }
  2462. }
  2463. inline std::size_t process(generator& g)
  2464. {
  2465. if (g.token_list_.size() >= stride_)
  2466. {
  2467. for (std::size_t i = 0; i < (g.token_list_.size() - stride_ + 1); ++i)
  2468. {
  2469. token t;
  2470. switch (stride_)
  2471. {
  2472. case 1 :
  2473. {
  2474. const token& t0 = g.token_list_[i];
  2475. if (!operator()(t0))
  2476. {
  2477. return i;
  2478. }
  2479. }
  2480. break;
  2481. case 2 :
  2482. {
  2483. const token& t0 = g.token_list_[i ];
  2484. const token& t1 = g.token_list_[i + 1];
  2485. if (!operator()(t0, t1))
  2486. {
  2487. return i;
  2488. }
  2489. }
  2490. break;
  2491. case 3 :
  2492. {
  2493. const token& t0 = g.token_list_[i ];
  2494. const token& t1 = g.token_list_[i + 1];
  2495. const token& t2 = g.token_list_[i + 2];
  2496. if (!operator()(t0, t1, t2))
  2497. {
  2498. return i;
  2499. }
  2500. }
  2501. break;
  2502. case 4 :
  2503. {
  2504. const token& t0 = g.token_list_[i ];
  2505. const token& t1 = g.token_list_[i + 1];
  2506. const token& t2 = g.token_list_[i + 2];
  2507. const token& t3 = g.token_list_[i + 3];
  2508. if (!operator()(t0, t1, t2, t3))
  2509. {
  2510. return i;
  2511. }
  2512. }
  2513. break;
  2514. }
  2515. }
  2516. }
  2517. return (g.token_list_.size() - stride_ + 1);
  2518. }
  2519. virtual bool operator() (const token&)
  2520. {
  2521. return false;
  2522. }
  2523. virtual bool operator() (const token&, const token&)
  2524. {
  2525. return false;
  2526. }
  2527. virtual bool operator() (const token&, const token&, const token&)
  2528. {
  2529. return false;
  2530. }
  2531. virtual bool operator() (const token&, const token&, const token&, const token&)
  2532. {
  2533. return false;
  2534. }
  2535. private:
  2536. const std::size_t stride_;
  2537. };
  2538. class token_modifier : public helper_interface
  2539. {
  2540. public:
  2541. inline std::size_t process(generator& g)
  2542. {
  2543. std::size_t changes = 0;
  2544. for (std::size_t i = 0; i < g.token_list_.size(); ++i)
  2545. {
  2546. if (modify(g.token_list_[i])) changes++;
  2547. }
  2548. return changes;
  2549. }
  2550. virtual bool modify(token& t) = 0;
  2551. };
  2552. class token_inserter : public helper_interface
  2553. {
  2554. public:
  2555. explicit token_inserter(const std::size_t& stride)
  2556. : stride_(stride)
  2557. {
  2558. if (stride > 5)
  2559. {
  2560. throw std::invalid_argument("token_inserter() - Invalid stride value");
  2561. }
  2562. }
  2563. inline std::size_t process(generator& g)
  2564. {
  2565. if (g.token_list_.empty())
  2566. return 0;
  2567. else if (g.token_list_.size() < stride_)
  2568. return 0;
  2569. std::size_t changes = 0;
  2570. for (std::size_t i = 0; i < (g.token_list_.size() - stride_ + 1); ++i)
  2571. {
  2572. int insert_index = -1;
  2573. token t;
  2574. switch (stride_)
  2575. {
  2576. case 1 : insert_index = insert(g.token_list_[i],t);
  2577. break;
  2578. case 2 : insert_index = insert(g.token_list_[i], g.token_list_[i + 1], t);
  2579. break;
  2580. case 3 : insert_index = insert(g.token_list_[i], g.token_list_[i + 1], g.token_list_[i + 2], t);
  2581. break;
  2582. case 4 : insert_index = insert(g.token_list_[i], g.token_list_[i + 1], g.token_list_[i + 2], g.token_list_[i + 3], t);
  2583. break;
  2584. case 5 : insert_index = insert(g.token_list_[i], g.token_list_[i + 1], g.token_list_[i + 2], g.token_list_[i + 3], g.token_list_[i + 4], t);
  2585. break;
  2586. }
  2587. typedef std::iterator_traits<generator::token_list_t::iterator>::difference_type diff_t;
  2588. if ((insert_index >= 0) && (insert_index <= (static_cast<int>(stride_) + 1)))
  2589. {
  2590. g.token_list_.insert(
  2591. g.token_list_.begin() + static_cast<diff_t>(i + static_cast<std::size_t>(insert_index)), t);
  2592. changes++;
  2593. }
  2594. }
  2595. return changes;
  2596. }
  2597. #define token_inserter_empty_body \
  2598. { \
  2599. return -1; \
  2600. } \
  2601. inline virtual int insert(const token&, token&)
  2602. token_inserter_empty_body
  2603. inline virtual int insert(const token&, const token&, token&)
  2604. token_inserter_empty_body
  2605. inline virtual int insert(const token&, const token&, const token&, token&)
  2606. token_inserter_empty_body
  2607. inline virtual int insert(const token&, const token&, const token&, const token&, token&)
  2608. token_inserter_empty_body
  2609. inline virtual int insert(const token&, const token&, const token&, const token&, const token&, token&)
  2610. token_inserter_empty_body
  2611. #undef token_inserter_empty_body
  2612. private:
  2613. const std::size_t stride_;
  2614. };
  2615. class token_joiner : public helper_interface
  2616. {
  2617. public:
  2618. explicit token_joiner(const std::size_t& stride)
  2619. : stride_(stride)
  2620. {}
  2621. inline std::size_t process(generator& g)
  2622. {
  2623. if (g.token_list_.empty())
  2624. return 0;
  2625. switch (stride_)
  2626. {
  2627. case 2 : return process_stride_2(g);
  2628. case 3 : return process_stride_3(g);
  2629. default : return 0;
  2630. }
  2631. }
  2632. virtual bool join(const token&, const token&, token&) { return false; }
  2633. virtual bool join(const token&, const token&, const token&, token&) { return false; }
  2634. private:
  2635. inline std::size_t process_stride_2(generator& g)
  2636. {
  2637. typedef std::iterator_traits<generator::token_list_t::iterator>::difference_type diff_t;
  2638. if (g.token_list_.size() < 2)
  2639. return 0;
  2640. std::size_t changes = 0;
  2641. for (int i = 0; i < static_cast<int>(g.token_list_.size() - 1); ++i)
  2642. {
  2643. token t;
  2644. while (join(g[i], g[i + 1], t))
  2645. {
  2646. g.token_list_[i] = t;
  2647. g.token_list_.erase(g.token_list_.begin() + static_cast<diff_t>(i + 1));
  2648. ++changes;
  2649. if (static_cast<std::size_t>(i + 1) >= g.token_list_.size())
  2650. break;
  2651. }
  2652. }
  2653. return changes;
  2654. }
  2655. inline std::size_t process_stride_3(generator& g)
  2656. {
  2657. typedef std::iterator_traits<generator::token_list_t::iterator>::difference_type diff_t;
  2658. if (g.token_list_.size() < 3)
  2659. return 0;
  2660. std::size_t changes = 0;
  2661. for (int i = 0; i < static_cast<int>(g.token_list_.size() - 2); ++i)
  2662. {
  2663. token t;
  2664. while (join(g[i], g[i + 1], g[i + 2], t))
  2665. {
  2666. g.token_list_[i] = t;
  2667. g.token_list_.erase(g.token_list_.begin() + static_cast<diff_t>(i + 1),
  2668. g.token_list_.begin() + static_cast<diff_t>(i + 3));
  2669. ++changes;
  2670. if (static_cast<std::size_t>(i + 2) >= g.token_list_.size())
  2671. break;
  2672. }
  2673. }
  2674. return changes;
  2675. }
  2676. const std::size_t stride_;
  2677. };
  2678. namespace helper
  2679. {
  2680. inline void dump(lexer::generator& generator)
  2681. {
  2682. for (std::size_t i = 0; i < generator.size(); ++i)
  2683. {
  2684. lexer::token t = generator[i];
  2685. printf("Token[%02d] @ %03d %6s --> '%s'\n",
  2686. static_cast<int>(i),
  2687. static_cast<int>(t.position),
  2688. t.to_str(t.type).c_str(),
  2689. t.value.c_str());
  2690. }
  2691. }
  2692. class commutative_inserter : public lexer::token_inserter
  2693. {
  2694. public:
  2695. using lexer::token_inserter::insert;
  2696. commutative_inserter()
  2697. : lexer::token_inserter(2)
  2698. {}
  2699. inline void ignore_symbol(const std::string& symbol)
  2700. {
  2701. ignore_set_.insert(symbol);
  2702. }
  2703. inline int insert(const lexer::token& t0, const lexer::token& t1, lexer::token& new_token)
  2704. {
  2705. bool match = false;
  2706. new_token.type = lexer::token::e_mul;
  2707. new_token.value = "*";
  2708. new_token.position = t1.position;
  2709. if (t0.type == lexer::token::e_symbol)
  2710. {
  2711. if (ignore_set_.end() != ignore_set_.find(t0.value))
  2712. {
  2713. return -1;
  2714. }
  2715. else if (!t0.value.empty() && ('$' == t0.value[0]))
  2716. {
  2717. return -1;
  2718. }
  2719. }
  2720. if (t1.type == lexer::token::e_symbol)
  2721. {
  2722. if (ignore_set_.end() != ignore_set_.find(t1.value))
  2723. {
  2724. return -1;
  2725. }
  2726. }
  2727. if ((t0.type == lexer::token::e_number ) && (t1.type == lexer::token::e_symbol )) match = true;
  2728. else if ((t0.type == lexer::token::e_number ) && (t1.type == lexer::token::e_lbracket )) match = true;
  2729. else if ((t0.type == lexer::token::e_number ) && (t1.type == lexer::token::e_lcrlbracket)) match = true;
  2730. else if ((t0.type == lexer::token::e_number ) && (t1.type == lexer::token::e_lsqrbracket)) match = true;
  2731. else if ((t0.type == lexer::token::e_symbol ) && (t1.type == lexer::token::e_number )) match = true;
  2732. else if ((t0.type == lexer::token::e_rbracket ) && (t1.type == lexer::token::e_number )) match = true;
  2733. else if ((t0.type == lexer::token::e_rcrlbracket) && (t1.type == lexer::token::e_number )) match = true;
  2734. else if ((t0.type == lexer::token::e_rsqrbracket) && (t1.type == lexer::token::e_number )) match = true;
  2735. else if ((t0.type == lexer::token::e_rbracket ) && (t1.type == lexer::token::e_symbol )) match = true;
  2736. else if ((t0.type == lexer::token::e_rcrlbracket) && (t1.type == lexer::token::e_symbol )) match = true;
  2737. else if ((t0.type == lexer::token::e_rsqrbracket) && (t1.type == lexer::token::e_symbol )) match = true;
  2738. else if ((t0.type == lexer::token::e_symbol ) && (t1.type == lexer::token::e_symbol )) match = true;
  2739. return (match) ? 1 : -1;
  2740. }
  2741. private:
  2742. std::set<std::string,details::ilesscompare> ignore_set_;
  2743. };
  2744. class operator_joiner : public token_joiner
  2745. {
  2746. public:
  2747. explicit operator_joiner(const std::size_t& stride)
  2748. : token_joiner(stride)
  2749. {}
  2750. inline bool join(const lexer::token& t0, const lexer::token& t1, lexer::token& t)
  2751. {
  2752. // ': =' --> ':='
  2753. if ((t0.type == lexer::token::e_colon) && (t1.type == lexer::token::e_eq))
  2754. {
  2755. t.type = lexer::token::e_assign;
  2756. t.value = ":=";
  2757. t.position = t0.position;
  2758. return true;
  2759. }
  2760. // '+ =' --> '+='
  2761. else if ((t0.type == lexer::token::e_add) && (t1.type == lexer::token::e_eq))
  2762. {
  2763. t.type = lexer::token::e_addass;
  2764. t.value = "+=";
  2765. t.position = t0.position;
  2766. return true;
  2767. }
  2768. // '- =' --> '-='
  2769. else if ((t0.type == lexer::token::e_sub) && (t1.type == lexer::token::e_eq))
  2770. {
  2771. t.type = lexer::token::e_subass;
  2772. t.value = "-=";
  2773. t.position = t0.position;
  2774. return true;
  2775. }
  2776. // '* =' --> '*='
  2777. else if ((t0.type == lexer::token::e_mul) && (t1.type == lexer::token::e_eq))
  2778. {
  2779. t.type = lexer::token::e_mulass;
  2780. t.value = "*=";
  2781. t.position = t0.position;
  2782. return true;
  2783. }
  2784. // '/ =' --> '/='
  2785. else if ((t0.type == lexer::token::e_div) && (t1.type == lexer::token::e_eq))
  2786. {
  2787. t.type = lexer::token::e_divass;
  2788. t.value = "/=";
  2789. t.position = t0.position;
  2790. return true;
  2791. }
  2792. // '% =' --> '%='
  2793. else if ((t0.type == lexer::token::e_mod) && (t1.type == lexer::token::e_eq))
  2794. {
  2795. t.type = lexer::token::e_modass;
  2796. t.value = "%=";
  2797. t.position = t0.position;
  2798. return true;
  2799. }
  2800. // '> =' --> '>='
  2801. else if ((t0.type == lexer::token::e_gt) && (t1.type == lexer::token::e_eq))
  2802. {
  2803. t.type = lexer::token::e_gte;
  2804. t.value = ">=";
  2805. t.position = t0.position;
  2806. return true;
  2807. }
  2808. // '< =' --> '<='
  2809. else if ((t0.type == lexer::token::e_lt) && (t1.type == lexer::token::e_eq))
  2810. {
  2811. t.type = lexer::token::e_lte;
  2812. t.value = "<=";
  2813. t.position = t0.position;
  2814. return true;
  2815. }
  2816. // '= =' --> '=='
  2817. else if ((t0.type == lexer::token::e_eq) && (t1.type == lexer::token::e_eq))
  2818. {
  2819. t.type = lexer::token::e_eq;
  2820. t.value = "==";
  2821. t.position = t0.position;
  2822. return true;
  2823. }
  2824. // '! =' --> '!='
  2825. else if ((static_cast<char>(t0.type) == '!') && (t1.type == lexer::token::e_eq))
  2826. {
  2827. t.type = lexer::token::e_ne;
  2828. t.value = "!=";
  2829. t.position = t0.position;
  2830. return true;
  2831. }
  2832. // '< >' --> '<>'
  2833. else if ((t0.type == lexer::token::e_lt) && (t1.type == lexer::token::e_gt))
  2834. {
  2835. t.type = lexer::token::e_ne;
  2836. t.value = "<>";
  2837. t.position = t0.position;
  2838. return true;
  2839. }
  2840. // '<= >' --> '<=>'
  2841. else if ((t0.type == lexer::token::e_lte) && (t1.type == lexer::token::e_gt))
  2842. {
  2843. t.type = lexer::token::e_swap;
  2844. t.value = "<=>";
  2845. t.position = t0.position;
  2846. return true;
  2847. }
  2848. // '+ -' --> '-'
  2849. else if ((t0.type == lexer::token::e_add) && (t1.type == lexer::token::e_sub))
  2850. {
  2851. t.type = lexer::token::e_sub;
  2852. t.value = "-";
  2853. t.position = t0.position;
  2854. return true;
  2855. }
  2856. // '- +' --> '-'
  2857. else if ((t0.type == lexer::token::e_sub) && (t1.type == lexer::token::e_add))
  2858. {
  2859. t.type = lexer::token::e_sub;
  2860. t.value = "-";
  2861. t.position = t0.position;
  2862. return true;
  2863. }
  2864. // '- -' --> '+'
  2865. else if ((t0.type == lexer::token::e_sub) && (t1.type == lexer::token::e_sub))
  2866. {
  2867. /*
  2868. Note: May need to reconsider this when wanting to implement
  2869. pre/postfix decrement operator
  2870. */
  2871. t.type = lexer::token::e_add;
  2872. t.value = "+";
  2873. t.position = t0.position;
  2874. return true;
  2875. }
  2876. else
  2877. return false;
  2878. }
  2879. inline bool join(const lexer::token& t0, const lexer::token& t1, const lexer::token& t2, lexer::token& t)
  2880. {
  2881. // '[ * ]' --> '[*]'
  2882. if (
  2883. (t0.type == lexer::token::e_lsqrbracket) &&
  2884. (t1.type == lexer::token::e_mul ) &&
  2885. (t2.type == lexer::token::e_rsqrbracket)
  2886. )
  2887. {
  2888. t.type = lexer::token::e_symbol;
  2889. t.value = "[*]";
  2890. t.position = t0.position;
  2891. return true;
  2892. }
  2893. else
  2894. return false;
  2895. }
  2896. };
  2897. class bracket_checker : public lexer::token_scanner
  2898. {
  2899. public:
  2900. using lexer::token_scanner::operator();
  2901. bracket_checker()
  2902. : token_scanner(1),
  2903. state_(true)
  2904. {}
  2905. bool result()
  2906. {
  2907. if (!stack_.empty())
  2908. {
  2909. lexer::token t;
  2910. t.value = stack_.top().first;
  2911. t.position = stack_.top().second;
  2912. error_token_ = t;
  2913. state_ = false;
  2914. return false;
  2915. }
  2916. else
  2917. return state_;
  2918. }
  2919. lexer::token error_token()
  2920. {
  2921. return error_token_;
  2922. }
  2923. void reset()
  2924. {
  2925. // Why? because msvc doesn't support swap properly.
  2926. stack_ = std::stack<std::pair<char,std::size_t> >();
  2927. state_ = true;
  2928. error_token_.clear();
  2929. }
  2930. bool operator() (const lexer::token& t)
  2931. {
  2932. if (
  2933. !t.value.empty() &&
  2934. (lexer::token::e_string != t.type) &&
  2935. (lexer::token::e_symbol != t.type) &&
  2936. exprtk::details::is_bracket(t.value[0])
  2937. )
  2938. {
  2939. details::char_t c = t.value[0];
  2940. if (t.type == lexer::token::e_lbracket ) stack_.push(std::make_pair(')',t.position));
  2941. else if (t.type == lexer::token::e_lcrlbracket) stack_.push(std::make_pair('}',t.position));
  2942. else if (t.type == lexer::token::e_lsqrbracket) stack_.push(std::make_pair(']',t.position));
  2943. else if (exprtk::details::is_right_bracket(c))
  2944. {
  2945. if (stack_.empty())
  2946. {
  2947. state_ = false;
  2948. error_token_ = t;
  2949. return false;
  2950. }
  2951. else if (c != stack_.top().first)
  2952. {
  2953. state_ = false;
  2954. error_token_ = t;
  2955. return false;
  2956. }
  2957. else
  2958. stack_.pop();
  2959. }
  2960. }
  2961. return true;
  2962. }
  2963. private:
  2964. bool state_;
  2965. std::stack<std::pair<char,std::size_t> > stack_;
  2966. lexer::token error_token_;
  2967. };
  2968. class numeric_checker : public lexer::token_scanner
  2969. {
  2970. public:
  2971. using lexer::token_scanner::operator();
  2972. numeric_checker()
  2973. : token_scanner (1),
  2974. current_index_(0)
  2975. {}
  2976. bool result()
  2977. {
  2978. return error_list_.empty();
  2979. }
  2980. void reset()
  2981. {
  2982. error_list_.clear();
  2983. current_index_ = 0;
  2984. }
  2985. bool operator() (const lexer::token& t)
  2986. {
  2987. if (token::e_number == t.type)
  2988. {
  2989. double v;
  2990. if (!exprtk::details::string_to_real(t.value,v))
  2991. {
  2992. error_list_.push_back(current_index_);
  2993. }
  2994. }
  2995. ++current_index_;
  2996. return true;
  2997. }
  2998. std::size_t error_count() const
  2999. {
  3000. return error_list_.size();
  3001. }
  3002. std::size_t error_index(const std::size_t& i)
  3003. {
  3004. if (i < error_list_.size())
  3005. return error_list_[i];
  3006. else
  3007. return std::numeric_limits<std::size_t>::max();
  3008. }
  3009. void clear_errors()
  3010. {
  3011. error_list_.clear();
  3012. }
  3013. private:
  3014. std::size_t current_index_;
  3015. std::vector<std::size_t> error_list_;
  3016. };
  3017. class symbol_replacer : public lexer::token_modifier
  3018. {
  3019. private:
  3020. typedef std::map<std::string,std::pair<std::string,token::token_type>,details::ilesscompare> replace_map_t;
  3021. public:
  3022. bool remove(const std::string& target_symbol)
  3023. {
  3024. const replace_map_t::iterator itr = replace_map_.find(target_symbol);
  3025. if (replace_map_.end() == itr)
  3026. return false;
  3027. replace_map_.erase(itr);
  3028. return true;
  3029. }
  3030. bool add_replace(const std::string& target_symbol,
  3031. const std::string& replace_symbol,
  3032. const lexer::token::token_type token_type = lexer::token::e_symbol)
  3033. {
  3034. const replace_map_t::iterator itr = replace_map_.find(target_symbol);
  3035. if (replace_map_.end() != itr)
  3036. {
  3037. return false;
  3038. }
  3039. replace_map_[target_symbol] = std::make_pair(replace_symbol,token_type);
  3040. return true;
  3041. }
  3042. void clear()
  3043. {
  3044. replace_map_.clear();
  3045. }
  3046. private:
  3047. bool modify(lexer::token& t)
  3048. {
  3049. if (lexer::token::e_symbol == t.type)
  3050. {
  3051. if (replace_map_.empty())
  3052. return false;
  3053. const replace_map_t::iterator itr = replace_map_.find(t.value);
  3054. if (replace_map_.end() != itr)
  3055. {
  3056. t.value = itr->second.first;
  3057. t.type = itr->second.second;
  3058. return true;
  3059. }
  3060. }
  3061. return false;
  3062. }
  3063. replace_map_t replace_map_;
  3064. };
  3065. class sequence_validator : public lexer::token_scanner
  3066. {
  3067. private:
  3068. typedef std::pair<lexer::token::token_type,lexer::token::token_type> token_pair_t;
  3069. typedef std::set<token_pair_t> set_t;
  3070. public:
  3071. using lexer::token_scanner::operator();
  3072. sequence_validator()
  3073. : lexer::token_scanner(2)
  3074. {
  3075. add_invalid(lexer::token::e_number, lexer::token::e_number);
  3076. add_invalid(lexer::token::e_string, lexer::token::e_string);
  3077. add_invalid(lexer::token::e_number, lexer::token::e_string);
  3078. add_invalid(lexer::token::e_string, lexer::token::e_number);
  3079. add_invalid_set1(lexer::token::e_assign );
  3080. add_invalid_set1(lexer::token::e_shr );
  3081. add_invalid_set1(lexer::token::e_shl );
  3082. add_invalid_set1(lexer::token::e_lte );
  3083. add_invalid_set1(lexer::token::e_ne );
  3084. add_invalid_set1(lexer::token::e_gte );
  3085. add_invalid_set1(lexer::token::e_lt );
  3086. add_invalid_set1(lexer::token::e_gt );
  3087. add_invalid_set1(lexer::token::e_eq );
  3088. add_invalid_set1(lexer::token::e_comma );
  3089. add_invalid_set1(lexer::token::e_add );
  3090. add_invalid_set1(lexer::token::e_sub );
  3091. add_invalid_set1(lexer::token::e_div );
  3092. add_invalid_set1(lexer::token::e_mul );
  3093. add_invalid_set1(lexer::token::e_mod );
  3094. add_invalid_set1(lexer::token::e_pow );
  3095. add_invalid_set1(lexer::token::e_colon );
  3096. add_invalid_set1(lexer::token::e_ternary);
  3097. }
  3098. bool result()
  3099. {
  3100. return error_list_.empty();
  3101. }
  3102. bool operator() (const lexer::token& t0, const lexer::token& t1)
  3103. {
  3104. const set_t::value_type p = std::make_pair(t0.type,t1.type);
  3105. if (invalid_bracket_check(t0.type,t1.type))
  3106. {
  3107. error_list_.push_back(std::make_pair(t0,t1));
  3108. }
  3109. else if (invalid_comb_.find(p) != invalid_comb_.end())
  3110. {
  3111. error_list_.push_back(std::make_pair(t0,t1));
  3112. }
  3113. return true;
  3114. }
  3115. std::size_t error_count() const
  3116. {
  3117. return error_list_.size();
  3118. }
  3119. std::pair<lexer::token,lexer::token> error(const std::size_t index)
  3120. {
  3121. if (index < error_list_.size())
  3122. {
  3123. return error_list_[index];
  3124. }
  3125. else
  3126. {
  3127. static const lexer::token error_token;
  3128. return std::make_pair(error_token,error_token);
  3129. }
  3130. }
  3131. void clear_errors()
  3132. {
  3133. error_list_.clear();
  3134. }
  3135. private:
  3136. void add_invalid(lexer::token::token_type base, lexer::token::token_type t)
  3137. {
  3138. invalid_comb_.insert(std::make_pair(base,t));
  3139. }
  3140. void add_invalid_set1(lexer::token::token_type t)
  3141. {
  3142. add_invalid(t, lexer::token::e_assign);
  3143. add_invalid(t, lexer::token::e_shr );
  3144. add_invalid(t, lexer::token::e_shl );
  3145. add_invalid(t, lexer::token::e_lte );
  3146. add_invalid(t, lexer::token::e_ne );
  3147. add_invalid(t, lexer::token::e_gte );
  3148. add_invalid(t, lexer::token::e_lt );
  3149. add_invalid(t, lexer::token::e_gt );
  3150. add_invalid(t, lexer::token::e_eq );
  3151. add_invalid(t, lexer::token::e_comma );
  3152. add_invalid(t, lexer::token::e_div );
  3153. add_invalid(t, lexer::token::e_mul );
  3154. add_invalid(t, lexer::token::e_mod );
  3155. add_invalid(t, lexer::token::e_pow );
  3156. add_invalid(t, lexer::token::e_colon );
  3157. }
  3158. bool invalid_bracket_check(lexer::token::token_type base, lexer::token::token_type t)
  3159. {
  3160. if (details::is_right_bracket(static_cast<char>(base)))
  3161. {
  3162. switch (t)
  3163. {
  3164. case lexer::token::e_assign : return (']' != base);
  3165. case lexer::token::e_string : return (')' != base);
  3166. default : return false;
  3167. }
  3168. }
  3169. else if (details::is_left_bracket(static_cast<char>(base)))
  3170. {
  3171. if (details::is_right_bracket(static_cast<char>(t)))
  3172. return false;
  3173. else if (details::is_left_bracket(static_cast<char>(t)))
  3174. return false;
  3175. else
  3176. {
  3177. switch (t)
  3178. {
  3179. case lexer::token::e_number : return false;
  3180. case lexer::token::e_symbol : return false;
  3181. case lexer::token::e_string : return false;
  3182. case lexer::token::e_add : return false;
  3183. case lexer::token::e_sub : return false;
  3184. case lexer::token::e_colon : return false;
  3185. case lexer::token::e_ternary : return false;
  3186. default : return true ;
  3187. }
  3188. }
  3189. }
  3190. else if (details::is_right_bracket(static_cast<char>(t)))
  3191. {
  3192. switch (base)
  3193. {
  3194. case lexer::token::e_number : return false;
  3195. case lexer::token::e_symbol : return false;
  3196. case lexer::token::e_string : return false;
  3197. case lexer::token::e_eof : return false;
  3198. case lexer::token::e_colon : return false;
  3199. case lexer::token::e_ternary : return false;
  3200. default : return true ;
  3201. }
  3202. }
  3203. else if (details::is_left_bracket(static_cast<char>(t)))
  3204. {
  3205. switch (base)
  3206. {
  3207. case lexer::token::e_rbracket : return true;
  3208. case lexer::token::e_rsqrbracket : return true;
  3209. case lexer::token::e_rcrlbracket : return true;
  3210. default : return false;
  3211. }
  3212. }
  3213. return false;
  3214. }
  3215. set_t invalid_comb_;
  3216. std::vector<std::pair<lexer::token,lexer::token> > error_list_;
  3217. };
  3218. class sequence_validator_3tokens : public lexer::token_scanner
  3219. {
  3220. private:
  3221. typedef lexer::token::token_type token_t;
  3222. typedef std::pair<token_t,std::pair<token_t,token_t> > token_triplet_t;
  3223. typedef std::set<token_triplet_t> set_t;
  3224. public:
  3225. using lexer::token_scanner::operator();
  3226. sequence_validator_3tokens()
  3227. : lexer::token_scanner(3)
  3228. {
  3229. add_invalid(lexer::token::e_number, lexer::token::e_number, lexer::token::e_number);
  3230. add_invalid(lexer::token::e_string, lexer::token::e_string, lexer::token::e_string);
  3231. add_invalid(lexer::token::e_comma , lexer::token::e_comma , lexer::token::e_comma );
  3232. add_invalid(lexer::token::e_add , lexer::token::e_add , lexer::token::e_add );
  3233. add_invalid(lexer::token::e_sub , lexer::token::e_sub , lexer::token::e_sub );
  3234. add_invalid(lexer::token::e_div , lexer::token::e_div , lexer::token::e_div );
  3235. add_invalid(lexer::token::e_mul , lexer::token::e_mul , lexer::token::e_mul );
  3236. add_invalid(lexer::token::e_mod , lexer::token::e_mod , lexer::token::e_mod );
  3237. add_invalid(lexer::token::e_pow , lexer::token::e_pow , lexer::token::e_pow );
  3238. add_invalid(lexer::token::e_add , lexer::token::e_sub , lexer::token::e_add );
  3239. add_invalid(lexer::token::e_sub , lexer::token::e_add , lexer::token::e_sub );
  3240. add_invalid(lexer::token::e_div , lexer::token::e_mul , lexer::token::e_div );
  3241. add_invalid(lexer::token::e_mul , lexer::token::e_div , lexer::token::e_mul );
  3242. add_invalid(lexer::token::e_mod , lexer::token::e_pow , lexer::token::e_mod );
  3243. add_invalid(lexer::token::e_pow , lexer::token::e_mod , lexer::token::e_pow );
  3244. }
  3245. bool result()
  3246. {
  3247. return error_list_.empty();
  3248. }
  3249. bool operator() (const lexer::token& t0, const lexer::token& t1, const lexer::token& t2)
  3250. {
  3251. const set_t::value_type p = std::make_pair(t0.type,std::make_pair(t1.type,t2.type));
  3252. if (invalid_comb_.find(p) != invalid_comb_.end())
  3253. {
  3254. error_list_.push_back(std::make_pair(t0,t1));
  3255. }
  3256. return true;
  3257. }
  3258. std::size_t error_count() const
  3259. {
  3260. return error_list_.size();
  3261. }
  3262. std::pair<lexer::token,lexer::token> error(const std::size_t index)
  3263. {
  3264. if (index < error_list_.size())
  3265. {
  3266. return error_list_[index];
  3267. }
  3268. else
  3269. {
  3270. static const lexer::token error_token;
  3271. return std::make_pair(error_token,error_token);
  3272. }
  3273. }
  3274. void clear_errors()
  3275. {
  3276. error_list_.clear();
  3277. }
  3278. private:
  3279. void add_invalid(token_t t0, token_t t1, token_t t2)
  3280. {
  3281. invalid_comb_.insert(std::make_pair(t0,std::make_pair(t1,t2)));
  3282. }
  3283. set_t invalid_comb_;
  3284. std::vector<std::pair<lexer::token,lexer::token> > error_list_;
  3285. };
  3286. struct helper_assembly
  3287. {
  3288. inline bool register_scanner(lexer::token_scanner* scanner)
  3289. {
  3290. if (token_scanner_list.end() != std::find(token_scanner_list.begin(),
  3291. token_scanner_list.end (),
  3292. scanner))
  3293. {
  3294. return false;
  3295. }
  3296. token_scanner_list.push_back(scanner);
  3297. return true;
  3298. }
  3299. inline bool register_modifier(lexer::token_modifier* modifier)
  3300. {
  3301. if (token_modifier_list.end() != std::find(token_modifier_list.begin(),
  3302. token_modifier_list.end (),
  3303. modifier))
  3304. {
  3305. return false;
  3306. }
  3307. token_modifier_list.push_back(modifier);
  3308. return true;
  3309. }
  3310. inline bool register_joiner(lexer::token_joiner* joiner)
  3311. {
  3312. if (token_joiner_list.end() != std::find(token_joiner_list.begin(),
  3313. token_joiner_list.end (),
  3314. joiner))
  3315. {
  3316. return false;
  3317. }
  3318. token_joiner_list.push_back(joiner);
  3319. return true;
  3320. }
  3321. inline bool register_inserter(lexer::token_inserter* inserter)
  3322. {
  3323. if (token_inserter_list.end() != std::find(token_inserter_list.begin(),
  3324. token_inserter_list.end (),
  3325. inserter))
  3326. {
  3327. return false;
  3328. }
  3329. token_inserter_list.push_back(inserter);
  3330. return true;
  3331. }
  3332. inline bool run_modifiers(lexer::generator& g)
  3333. {
  3334. error_token_modifier = reinterpret_cast<lexer::token_modifier*>(0);
  3335. for (std::size_t i = 0; i < token_modifier_list.size(); ++i)
  3336. {
  3337. lexer::token_modifier& modifier = (*token_modifier_list[i]);
  3338. modifier.reset();
  3339. modifier.process(g);
  3340. if (!modifier.result())
  3341. {
  3342. error_token_modifier = token_modifier_list[i];
  3343. return false;
  3344. }
  3345. }
  3346. return true;
  3347. }
  3348. inline bool run_joiners(lexer::generator& g)
  3349. {
  3350. error_token_joiner = reinterpret_cast<lexer::token_joiner*>(0);
  3351. for (std::size_t i = 0; i < token_joiner_list.size(); ++i)
  3352. {
  3353. lexer::token_joiner& joiner = (*token_joiner_list[i]);
  3354. joiner.reset();
  3355. joiner.process(g);
  3356. if (!joiner.result())
  3357. {
  3358. error_token_joiner = token_joiner_list[i];
  3359. return false;
  3360. }
  3361. }
  3362. return true;
  3363. }
  3364. inline bool run_inserters(lexer::generator& g)
  3365. {
  3366. error_token_inserter = reinterpret_cast<lexer::token_inserter*>(0);
  3367. for (std::size_t i = 0; i < token_inserter_list.size(); ++i)
  3368. {
  3369. lexer::token_inserter& inserter = (*token_inserter_list[i]);
  3370. inserter.reset();
  3371. inserter.process(g);
  3372. if (!inserter.result())
  3373. {
  3374. error_token_inserter = token_inserter_list[i];
  3375. return false;
  3376. }
  3377. }
  3378. return true;
  3379. }
  3380. inline bool run_scanners(lexer::generator& g)
  3381. {
  3382. error_token_scanner = reinterpret_cast<lexer::token_scanner*>(0);
  3383. for (std::size_t i = 0; i < token_scanner_list.size(); ++i)
  3384. {
  3385. lexer::token_scanner& scanner = (*token_scanner_list[i]);
  3386. scanner.reset();
  3387. scanner.process(g);
  3388. if (!scanner.result())
  3389. {
  3390. error_token_scanner = token_scanner_list[i];
  3391. return false;
  3392. }
  3393. }
  3394. return true;
  3395. }
  3396. std::vector<lexer::token_scanner*> token_scanner_list;
  3397. std::vector<lexer::token_modifier*> token_modifier_list;
  3398. std::vector<lexer::token_joiner*> token_joiner_list;
  3399. std::vector<lexer::token_inserter*> token_inserter_list;
  3400. lexer::token_scanner* error_token_scanner;
  3401. lexer::token_modifier* error_token_modifier;
  3402. lexer::token_joiner* error_token_joiner;
  3403. lexer::token_inserter* error_token_inserter;
  3404. };
  3405. }
  3406. class parser_helper
  3407. {
  3408. public:
  3409. typedef token token_t;
  3410. typedef generator generator_t;
  3411. inline bool init(const std::string& str)
  3412. {
  3413. if (!lexer_.process(str))
  3414. {
  3415. return false;
  3416. }
  3417. lexer_.begin();
  3418. next_token();
  3419. return true;
  3420. }
  3421. inline generator_t& lexer()
  3422. {
  3423. return lexer_;
  3424. }
  3425. inline const generator_t& lexer() const
  3426. {
  3427. return lexer_;
  3428. }
  3429. inline void store_token()
  3430. {
  3431. lexer_.store();
  3432. store_current_token_ = current_token_;
  3433. }
  3434. inline void restore_token()
  3435. {
  3436. lexer_.restore();
  3437. current_token_ = store_current_token_;
  3438. }
  3439. inline void next_token()
  3440. {
  3441. current_token_ = lexer_.next_token();
  3442. }
  3443. inline const token_t& current_token() const
  3444. {
  3445. return current_token_;
  3446. }
  3447. enum token_advance_mode
  3448. {
  3449. e_hold = 0,
  3450. e_advance = 1
  3451. };
  3452. inline void advance_token(const token_advance_mode mode)
  3453. {
  3454. if (e_advance == mode)
  3455. {
  3456. next_token();
  3457. }
  3458. }
  3459. inline bool token_is(const token_t::token_type& ttype, const token_advance_mode mode = e_advance)
  3460. {
  3461. if (current_token().type != ttype)
  3462. {
  3463. return false;
  3464. }
  3465. advance_token(mode);
  3466. return true;
  3467. }
  3468. inline bool token_is(const token_t::token_type& ttype,
  3469. const std::string& value,
  3470. const token_advance_mode mode = e_advance)
  3471. {
  3472. if (
  3473. (current_token().type != ttype) ||
  3474. !exprtk::details::imatch(value,current_token().value)
  3475. )
  3476. {
  3477. return false;
  3478. }
  3479. advance_token(mode);
  3480. return true;
  3481. }
  3482. inline bool peek_token_is(const token_t::token_type& ttype)
  3483. {
  3484. return (lexer_.peek_next_token().type == ttype);
  3485. }
  3486. inline bool peek_token_is(const std::string& s)
  3487. {
  3488. return (exprtk::details::imatch(lexer_.peek_next_token().value,s));
  3489. }
  3490. private:
  3491. generator_t lexer_;
  3492. token_t current_token_;
  3493. token_t store_current_token_;
  3494. };
  3495. }
  3496. template <typename T>
  3497. class vector_view
  3498. {
  3499. public:
  3500. typedef T* data_ptr_t;
  3501. vector_view(data_ptr_t data, const std::size_t& size)
  3502. : size_(size),
  3503. data_(data),
  3504. data_ref_(0)
  3505. {}
  3506. vector_view(const vector_view<T>& vv)
  3507. : size_(vv.size_),
  3508. data_(vv.data_),
  3509. data_ref_(0)
  3510. {}
  3511. inline void rebase(data_ptr_t data)
  3512. {
  3513. data_ = data;
  3514. if (!data_ref_.empty())
  3515. {
  3516. for (std::size_t i = 0; i < data_ref_.size(); ++i)
  3517. {
  3518. (*data_ref_[i]) = data;
  3519. }
  3520. }
  3521. }
  3522. inline data_ptr_t data() const
  3523. {
  3524. return data_;
  3525. }
  3526. inline std::size_t size() const
  3527. {
  3528. return size_;
  3529. }
  3530. inline const T& operator[](const std::size_t index) const
  3531. {
  3532. return data_[index];
  3533. }
  3534. inline T& operator[](const std::size_t index)
  3535. {
  3536. return data_[index];
  3537. }
  3538. void set_ref(data_ptr_t* data_ref)
  3539. {
  3540. data_ref_.push_back(data_ref);
  3541. }
  3542. private:
  3543. const std::size_t size_;
  3544. data_ptr_t data_;
  3545. std::vector<data_ptr_t*> data_ref_;
  3546. };
  3547. template <typename T>
  3548. inline vector_view<T> make_vector_view(T* data,
  3549. const std::size_t size, const std::size_t offset = 0)
  3550. {
  3551. return vector_view<T>(data + offset, size);
  3552. }
  3553. template <typename T>
  3554. inline vector_view<T> make_vector_view(std::vector<T>& v,
  3555. const std::size_t size, const std::size_t offset = 0)
  3556. {
  3557. return vector_view<T>(v.data() + offset, size);
  3558. }
  3559. template <typename T> class results_context;
  3560. template <typename T>
  3561. struct type_store
  3562. {
  3563. enum store_type
  3564. {
  3565. e_unknown,
  3566. e_scalar ,
  3567. e_vector ,
  3568. e_string
  3569. };
  3570. type_store()
  3571. : data(0),
  3572. size(0),
  3573. type(e_unknown)
  3574. {}
  3575. union
  3576. {
  3577. void* data;
  3578. T* vec_data;
  3579. };
  3580. std::size_t size;
  3581. store_type type;
  3582. class parameter_list
  3583. {
  3584. public:
  3585. parameter_list(std::vector<type_store>& pl)
  3586. : parameter_list_(pl)
  3587. {}
  3588. inline bool empty() const
  3589. {
  3590. return parameter_list_.empty();
  3591. }
  3592. inline std::size_t size() const
  3593. {
  3594. return parameter_list_.size();
  3595. }
  3596. inline type_store& operator[](const std::size_t& index)
  3597. {
  3598. return parameter_list_[index];
  3599. }
  3600. inline const type_store& operator[](const std::size_t& index) const
  3601. {
  3602. return parameter_list_[index];
  3603. }
  3604. inline type_store& front()
  3605. {
  3606. return parameter_list_[0];
  3607. }
  3608. inline const type_store& front() const
  3609. {
  3610. return parameter_list_[0];
  3611. }
  3612. inline type_store& back()
  3613. {
  3614. return parameter_list_.back();
  3615. }
  3616. inline const type_store& back() const
  3617. {
  3618. return parameter_list_.back();
  3619. }
  3620. private:
  3621. std::vector<type_store>& parameter_list_;
  3622. friend class results_context<T>;
  3623. };
  3624. template <typename ViewType>
  3625. struct type_view
  3626. {
  3627. typedef type_store<T> type_store_t;
  3628. typedef ViewType value_t;
  3629. type_view(type_store_t& ts)
  3630. : ts_(ts),
  3631. data_(reinterpret_cast<value_t*>(ts_.data))
  3632. {}
  3633. type_view(const type_store_t& ts)
  3634. : ts_(const_cast<type_store_t&>(ts)),
  3635. data_(reinterpret_cast<value_t*>(ts_.data))
  3636. {}
  3637. inline std::size_t size() const
  3638. {
  3639. return ts_.size;
  3640. }
  3641. inline value_t& operator[](const std::size_t& i)
  3642. {
  3643. return data_[i];
  3644. }
  3645. inline const value_t& operator[](const std::size_t& i) const
  3646. {
  3647. return data_[i];
  3648. }
  3649. inline const value_t* begin() const { return data_; }
  3650. inline value_t* begin() { return data_; }
  3651. inline const value_t* end() const
  3652. {
  3653. return static_cast<value_t*>(data_ + ts_.size);
  3654. }
  3655. inline value_t* end()
  3656. {
  3657. return static_cast<value_t*>(data_ + ts_.size);
  3658. }
  3659. type_store_t& ts_;
  3660. value_t* data_;
  3661. };
  3662. typedef type_view<T> vector_view;
  3663. typedef type_view<char> string_view;
  3664. struct scalar_view
  3665. {
  3666. typedef type_store<T> type_store_t;
  3667. typedef T value_t;
  3668. scalar_view(type_store_t& ts)
  3669. : v_(*reinterpret_cast<value_t*>(ts.data))
  3670. {}
  3671. scalar_view(const type_store_t& ts)
  3672. : v_(*reinterpret_cast<value_t*>(const_cast<type_store_t&>(ts).data))
  3673. {}
  3674. inline value_t& operator() ()
  3675. {
  3676. return v_;
  3677. }
  3678. inline const value_t& operator() () const
  3679. {
  3680. return v_;
  3681. }
  3682. template <typename IntType>
  3683. inline bool to_int(IntType& i) const
  3684. {
  3685. if (!exprtk::details::numeric::is_integer(v_))
  3686. return false;
  3687. i = static_cast<IntType>(v_);
  3688. return true;
  3689. }
  3690. template <typename UIntType>
  3691. inline bool to_uint(UIntType& u) const
  3692. {
  3693. if (v_ < T(0))
  3694. return false;
  3695. else if (!exprtk::details::numeric::is_integer(v_))
  3696. return false;
  3697. u = static_cast<UIntType>(v_);
  3698. return true;
  3699. }
  3700. T& v_;
  3701. };
  3702. };
  3703. template <typename StringView>
  3704. inline std::string to_str(const StringView& view)
  3705. {
  3706. return std::string(view.begin(),view.size());
  3707. }
  3708. #ifndef exprtk_disable_return_statement
  3709. namespace details
  3710. {
  3711. template <typename T> class return_node;
  3712. template <typename T> class return_envelope_node;
  3713. }
  3714. #endif
  3715. template <typename T>
  3716. class results_context
  3717. {
  3718. public:
  3719. typedef type_store<T> type_store_t;
  3720. results_context()
  3721. : results_available_(false)
  3722. {}
  3723. inline std::size_t count() const
  3724. {
  3725. if (results_available_)
  3726. return parameter_list_.size();
  3727. else
  3728. return 0;
  3729. }
  3730. inline type_store_t& operator[](const std::size_t& index)
  3731. {
  3732. return parameter_list_[index];
  3733. }
  3734. inline const type_store_t& operator[](const std::size_t& index) const
  3735. {
  3736. return parameter_list_[index];
  3737. }
  3738. private:
  3739. inline void clear()
  3740. {
  3741. results_available_ = false;
  3742. }
  3743. typedef std::vector<type_store_t> ts_list_t;
  3744. typedef typename type_store_t::parameter_list parameter_list_t;
  3745. inline void assign(const parameter_list_t& pl)
  3746. {
  3747. parameter_list_ = pl.parameter_list_;
  3748. results_available_ = true;
  3749. }
  3750. bool results_available_;
  3751. ts_list_t parameter_list_;
  3752. #ifndef exprtk_disable_return_statement
  3753. friend class details::return_node<T>;
  3754. friend class details::return_envelope_node<T>;
  3755. #endif
  3756. };
  3757. namespace details
  3758. {
  3759. enum operator_type
  3760. {
  3761. e_default , e_null , e_add , e_sub ,
  3762. e_mul , e_div , e_mod , e_pow ,
  3763. e_atan2 , e_min , e_max , e_avg ,
  3764. e_sum , e_prod , e_lt , e_lte ,
  3765. e_eq , e_equal , e_ne , e_nequal ,
  3766. e_gte , e_gt , e_and , e_nand ,
  3767. e_or , e_nor , e_xor , e_xnor ,
  3768. e_mand , e_mor , e_scand , e_scor ,
  3769. e_shr , e_shl , e_abs , e_acos ,
  3770. e_acosh , e_asin , e_asinh , e_atan ,
  3771. e_atanh , e_ceil , e_cos , e_cosh ,
  3772. e_exp , e_expm1 , e_floor , e_log ,
  3773. e_log10 , e_log2 , e_log1p , e_logn ,
  3774. e_neg , e_pos , e_round , e_roundn ,
  3775. e_root , e_sqrt , e_sin , e_sinc ,
  3776. e_sinh , e_sec , e_csc , e_tan ,
  3777. e_tanh , e_cot , e_clamp , e_iclamp ,
  3778. e_inrange , e_sgn , e_r2d , e_d2r ,
  3779. e_d2g , e_g2d , e_hypot , e_notl ,
  3780. e_erf , e_erfc , e_ncdf , e_frac ,
  3781. e_trunc , e_assign , e_addass , e_subass ,
  3782. e_mulass , e_divass , e_modass , e_in ,
  3783. e_like , e_ilike , e_multi , e_smulti ,
  3784. e_swap ,
  3785. // Do not add new functions/operators after this point.
  3786. e_sf00 = 1000, e_sf01 = 1001, e_sf02 = 1002, e_sf03 = 1003,
  3787. e_sf04 = 1004, e_sf05 = 1005, e_sf06 = 1006, e_sf07 = 1007,
  3788. e_sf08 = 1008, e_sf09 = 1009, e_sf10 = 1010, e_sf11 = 1011,
  3789. e_sf12 = 1012, e_sf13 = 1013, e_sf14 = 1014, e_sf15 = 1015,
  3790. e_sf16 = 1016, e_sf17 = 1017, e_sf18 = 1018, e_sf19 = 1019,
  3791. e_sf20 = 1020, e_sf21 = 1021, e_sf22 = 1022, e_sf23 = 1023,
  3792. e_sf24 = 1024, e_sf25 = 1025, e_sf26 = 1026, e_sf27 = 1027,
  3793. e_sf28 = 1028, e_sf29 = 1029, e_sf30 = 1030, e_sf31 = 1031,
  3794. e_sf32 = 1032, e_sf33 = 1033, e_sf34 = 1034, e_sf35 = 1035,
  3795. e_sf36 = 1036, e_sf37 = 1037, e_sf38 = 1038, e_sf39 = 1039,
  3796. e_sf40 = 1040, e_sf41 = 1041, e_sf42 = 1042, e_sf43 = 1043,
  3797. e_sf44 = 1044, e_sf45 = 1045, e_sf46 = 1046, e_sf47 = 1047,
  3798. e_sf48 = 1048, e_sf49 = 1049, e_sf50 = 1050, e_sf51 = 1051,
  3799. e_sf52 = 1052, e_sf53 = 1053, e_sf54 = 1054, e_sf55 = 1055,
  3800. e_sf56 = 1056, e_sf57 = 1057, e_sf58 = 1058, e_sf59 = 1059,
  3801. e_sf60 = 1060, e_sf61 = 1061, e_sf62 = 1062, e_sf63 = 1063,
  3802. e_sf64 = 1064, e_sf65 = 1065, e_sf66 = 1066, e_sf67 = 1067,
  3803. e_sf68 = 1068, e_sf69 = 1069, e_sf70 = 1070, e_sf71 = 1071,
  3804. e_sf72 = 1072, e_sf73 = 1073, e_sf74 = 1074, e_sf75 = 1075,
  3805. e_sf76 = 1076, e_sf77 = 1077, e_sf78 = 1078, e_sf79 = 1079,
  3806. e_sf80 = 1080, e_sf81 = 1081, e_sf82 = 1082, e_sf83 = 1083,
  3807. e_sf84 = 1084, e_sf85 = 1085, e_sf86 = 1086, e_sf87 = 1087,
  3808. e_sf88 = 1088, e_sf89 = 1089, e_sf90 = 1090, e_sf91 = 1091,
  3809. e_sf92 = 1092, e_sf93 = 1093, e_sf94 = 1094, e_sf95 = 1095,
  3810. e_sf96 = 1096, e_sf97 = 1097, e_sf98 = 1098, e_sf99 = 1099,
  3811. e_sffinal = 1100,
  3812. e_sf4ext00 = 2000, e_sf4ext01 = 2001, e_sf4ext02 = 2002, e_sf4ext03 = 2003,
  3813. e_sf4ext04 = 2004, e_sf4ext05 = 2005, e_sf4ext06 = 2006, e_sf4ext07 = 2007,
  3814. e_sf4ext08 = 2008, e_sf4ext09 = 2009, e_sf4ext10 = 2010, e_sf4ext11 = 2011,
  3815. e_sf4ext12 = 2012, e_sf4ext13 = 2013, e_sf4ext14 = 2014, e_sf4ext15 = 2015,
  3816. e_sf4ext16 = 2016, e_sf4ext17 = 2017, e_sf4ext18 = 2018, e_sf4ext19 = 2019,
  3817. e_sf4ext20 = 2020, e_sf4ext21 = 2021, e_sf4ext22 = 2022, e_sf4ext23 = 2023,
  3818. e_sf4ext24 = 2024, e_sf4ext25 = 2025, e_sf4ext26 = 2026, e_sf4ext27 = 2027,
  3819. e_sf4ext28 = 2028, e_sf4ext29 = 2029, e_sf4ext30 = 2030, e_sf4ext31 = 2031,
  3820. e_sf4ext32 = 2032, e_sf4ext33 = 2033, e_sf4ext34 = 2034, e_sf4ext35 = 2035,
  3821. e_sf4ext36 = 2036, e_sf4ext37 = 2037, e_sf4ext38 = 2038, e_sf4ext39 = 2039,
  3822. e_sf4ext40 = 2040, e_sf4ext41 = 2041, e_sf4ext42 = 2042, e_sf4ext43 = 2043,
  3823. e_sf4ext44 = 2044, e_sf4ext45 = 2045, e_sf4ext46 = 2046, e_sf4ext47 = 2047,
  3824. e_sf4ext48 = 2048, e_sf4ext49 = 2049, e_sf4ext50 = 2050, e_sf4ext51 = 2051,
  3825. e_sf4ext52 = 2052, e_sf4ext53 = 2053, e_sf4ext54 = 2054, e_sf4ext55 = 2055,
  3826. e_sf4ext56 = 2056, e_sf4ext57 = 2057, e_sf4ext58 = 2058, e_sf4ext59 = 2059,
  3827. e_sf4ext60 = 2060, e_sf4ext61 = 2061
  3828. };
  3829. inline std::string to_str(const operator_type opr)
  3830. {
  3831. switch (opr)
  3832. {
  3833. case e_add : return "+" ;
  3834. case e_sub : return "-" ;
  3835. case e_mul : return "*" ;
  3836. case e_div : return "/" ;
  3837. case e_mod : return "%" ;
  3838. case e_pow : return "^" ;
  3839. case e_assign : return ":=" ;
  3840. case e_addass : return "+=" ;
  3841. case e_subass : return "-=" ;
  3842. case e_mulass : return "*=" ;
  3843. case e_divass : return "/=" ;
  3844. case e_modass : return "%=" ;
  3845. case e_lt : return "<" ;
  3846. case e_lte : return "<=" ;
  3847. case e_eq : return "==" ;
  3848. case e_equal : return "=" ;
  3849. case e_ne : return "!=" ;
  3850. case e_nequal : return "<>" ;
  3851. case e_gte : return ">=" ;
  3852. case e_gt : return ">" ;
  3853. case e_and : return "and" ;
  3854. case e_or : return "or" ;
  3855. case e_xor : return "xor" ;
  3856. case e_nand : return "nand";
  3857. case e_nor : return "nor" ;
  3858. case e_xnor : return "xnor";
  3859. default : return "N/A" ;
  3860. }
  3861. }
  3862. struct base_operation_t
  3863. {
  3864. base_operation_t(const operator_type t, const unsigned int& np)
  3865. : type(t),
  3866. num_params(np)
  3867. {}
  3868. operator_type type;
  3869. unsigned int num_params;
  3870. };
  3871. namespace loop_unroll
  3872. {
  3873. #ifndef exprtk_disable_superscalar_unroll
  3874. const unsigned int global_loop_batch_size = 16;
  3875. #else
  3876. const unsigned int global_loop_batch_size = 4;
  3877. #endif
  3878. struct details
  3879. {
  3880. details(const std::size_t& vsize,
  3881. const unsigned int loop_batch_size = global_loop_batch_size)
  3882. : batch_size(loop_batch_size ),
  3883. remainder (vsize % batch_size),
  3884. upper_bound(static_cast<int>(vsize - (remainder ? loop_batch_size : 0)))
  3885. {}
  3886. unsigned int batch_size;
  3887. int remainder;
  3888. int upper_bound;
  3889. };
  3890. }
  3891. #ifdef exprtk_enable_debugging
  3892. inline void dump_ptr(const std::string& s, const void* ptr, const std::size_t size = 0)
  3893. {
  3894. if (size)
  3895. exprtk_debug(("%s - addr: %p\n",s.c_str(),ptr));
  3896. else
  3897. exprtk_debug(("%s - addr: %p size: %d\n",
  3898. s.c_str(),
  3899. ptr,
  3900. static_cast<unsigned int>(size)));
  3901. }
  3902. #else
  3903. inline void dump_ptr(const std::string&, const void*) {}
  3904. inline void dump_ptr(const std::string&, const void*, const std::size_t) {}
  3905. #endif
  3906. template <typename T>
  3907. class vec_data_store
  3908. {
  3909. public:
  3910. typedef vec_data_store<T> type;
  3911. typedef T* data_t;
  3912. private:
  3913. struct control_block
  3914. {
  3915. control_block()
  3916. : ref_count(1),
  3917. size (0),
  3918. data (0),
  3919. destruct (true)
  3920. {}
  3921. control_block(const std::size_t& dsize)
  3922. : ref_count(1 ),
  3923. size (dsize),
  3924. data (0 ),
  3925. destruct (true )
  3926. { create_data(); }
  3927. control_block(const std::size_t& dsize, data_t dptr, bool dstrct = false)
  3928. : ref_count(1 ),
  3929. size (dsize ),
  3930. data (dptr ),
  3931. destruct (dstrct)
  3932. {}
  3933. ~control_block()
  3934. {
  3935. if (data && destruct && (0 == ref_count))
  3936. {
  3937. dump_ptr("~control_block() data",data);
  3938. delete[] data;
  3939. data = reinterpret_cast<data_t>(0);
  3940. }
  3941. }
  3942. static inline control_block* create(const std::size_t& dsize, data_t data_ptr = data_t(0), bool dstrct = false)
  3943. {
  3944. if (dsize)
  3945. {
  3946. if (0 == data_ptr)
  3947. return (new control_block(dsize));
  3948. else
  3949. return (new control_block(dsize, data_ptr, dstrct));
  3950. }
  3951. else
  3952. return (new control_block);
  3953. }
  3954. static inline void destroy(control_block*& cntrl_blck)
  3955. {
  3956. if (cntrl_blck)
  3957. {
  3958. if (
  3959. (0 != cntrl_blck->ref_count) &&
  3960. (0 == --cntrl_blck->ref_count)
  3961. )
  3962. {
  3963. delete cntrl_blck;
  3964. }
  3965. cntrl_blck = 0;
  3966. }
  3967. }
  3968. std::size_t ref_count;
  3969. std::size_t size;
  3970. data_t data;
  3971. bool destruct;
  3972. private:
  3973. control_block(const control_block&);
  3974. control_block& operator=(const control_block&);
  3975. inline void create_data()
  3976. {
  3977. destruct = true;
  3978. data = new T[size];
  3979. std::fill_n(data,size,T(0));
  3980. dump_ptr("control_block::create_data() - data",data,size);
  3981. }
  3982. };
  3983. public:
  3984. vec_data_store()
  3985. : control_block_(control_block::create(0))
  3986. {}
  3987. vec_data_store(const std::size_t& size)
  3988. : control_block_(control_block::create(size,(data_t)(0),true))
  3989. {}
  3990. vec_data_store(const std::size_t& size, data_t data, bool dstrct = false)
  3991. : control_block_(control_block::create(size, data, dstrct))
  3992. {}
  3993. vec_data_store(const type& vds)
  3994. {
  3995. control_block_ = vds.control_block_;
  3996. control_block_->ref_count++;
  3997. }
  3998. ~vec_data_store()
  3999. {
  4000. control_block::destroy(control_block_);
  4001. }
  4002. type& operator=(const type& vds)
  4003. {
  4004. if (this != &vds)
  4005. {
  4006. std::size_t final_size = min_size(control_block_, vds.control_block_);
  4007. vds.control_block_->size = final_size;
  4008. control_block_->size = final_size;
  4009. if (control_block_->destruct || (0 == control_block_->data))
  4010. {
  4011. control_block::destroy(control_block_);
  4012. control_block_ = vds.control_block_;
  4013. control_block_->ref_count++;
  4014. }
  4015. }
  4016. return (*this);
  4017. }
  4018. inline data_t data()
  4019. {
  4020. return control_block_->data;
  4021. }
  4022. inline data_t data() const
  4023. {
  4024. return control_block_->data;
  4025. }
  4026. inline std::size_t size()
  4027. {
  4028. return control_block_->size;
  4029. }
  4030. inline std::size_t size() const
  4031. {
  4032. return control_block_->size;
  4033. }
  4034. inline data_t& ref()
  4035. {
  4036. return control_block_->data;
  4037. }
  4038. inline void dump() const
  4039. {
  4040. #ifdef exprtk_enable_debugging
  4041. exprtk_debug(("size: %d\taddress:%p\tdestruct:%c\n",
  4042. size(),
  4043. data(),
  4044. (control_block_->destruct ? 'T' : 'F')));
  4045. for (std::size_t i = 0; i < size(); ++i)
  4046. {
  4047. if (5 == i)
  4048. exprtk_debug(("\n"));
  4049. exprtk_debug(("%15.10f ",data()[i]));
  4050. }
  4051. exprtk_debug(("\n"));
  4052. #endif
  4053. }
  4054. static inline void match_sizes(type& vds0, type& vds1)
  4055. {
  4056. std::size_t size = min_size(vds0.control_block_,vds1.control_block_);
  4057. vds0.control_block_->size = size;
  4058. vds1.control_block_->size = size;
  4059. }
  4060. private:
  4061. static inline std::size_t min_size(control_block* cb0, control_block* cb1)
  4062. {
  4063. const std::size_t size0 = cb0->size;
  4064. const std::size_t size1 = cb1->size;
  4065. if (size0 && size1)
  4066. return std::min(size0,size1);
  4067. else
  4068. return (size0) ? size0 : size1;
  4069. }
  4070. control_block* control_block_;
  4071. };
  4072. namespace numeric
  4073. {
  4074. namespace details
  4075. {
  4076. template <typename T>
  4077. inline T process_impl(const operator_type operation, const T arg)
  4078. {
  4079. switch (operation)
  4080. {
  4081. case e_abs : return numeric::abs (arg);
  4082. case e_acos : return numeric::acos (arg);
  4083. case e_acosh : return numeric::acosh(arg);
  4084. case e_asin : return numeric::asin (arg);
  4085. case e_asinh : return numeric::asinh(arg);
  4086. case e_atan : return numeric::atan (arg);
  4087. case e_atanh : return numeric::atanh(arg);
  4088. case e_ceil : return numeric::ceil (arg);
  4089. case e_cos : return numeric::cos (arg);
  4090. case e_cosh : return numeric::cosh (arg);
  4091. case e_exp : return numeric::exp (arg);
  4092. case e_expm1 : return numeric::expm1(arg);
  4093. case e_floor : return numeric::floor(arg);
  4094. case e_log : return numeric::log (arg);
  4095. case e_log10 : return numeric::log10(arg);
  4096. case e_log2 : return numeric::log2 (arg);
  4097. case e_log1p : return numeric::log1p(arg);
  4098. case e_neg : return numeric::neg (arg);
  4099. case e_pos : return numeric::pos (arg);
  4100. case e_round : return numeric::round(arg);
  4101. case e_sin : return numeric::sin (arg);
  4102. case e_sinc : return numeric::sinc (arg);
  4103. case e_sinh : return numeric::sinh (arg);
  4104. case e_sqrt : return numeric::sqrt (arg);
  4105. case e_tan : return numeric::tan (arg);
  4106. case e_tanh : return numeric::tanh (arg);
  4107. case e_cot : return numeric::cot (arg);
  4108. case e_sec : return numeric::sec (arg);
  4109. case e_csc : return numeric::csc (arg);
  4110. case e_r2d : return numeric::r2d (arg);
  4111. case e_d2r : return numeric::d2r (arg);
  4112. case e_d2g : return numeric::d2g (arg);
  4113. case e_g2d : return numeric::g2d (arg);
  4114. case e_notl : return numeric::notl (arg);
  4115. case e_sgn : return numeric::sgn (arg);
  4116. case e_erf : return numeric::erf (arg);
  4117. case e_erfc : return numeric::erfc (arg);
  4118. case e_ncdf : return numeric::ncdf (arg);
  4119. case e_frac : return numeric::frac (arg);
  4120. case e_trunc : return numeric::trunc(arg);
  4121. default : exprtk_debug(("numeric::details::process_impl<T> - Invalid unary operation.\n"));
  4122. return std::numeric_limits<T>::quiet_NaN();
  4123. }
  4124. }
  4125. template <typename T>
  4126. inline T process_impl(const operator_type operation, const T arg0, const T arg1)
  4127. {
  4128. switch (operation)
  4129. {
  4130. case e_add : return (arg0 + arg1);
  4131. case e_sub : return (arg0 - arg1);
  4132. case e_mul : return (arg0 * arg1);
  4133. case e_div : return (arg0 / arg1);
  4134. case e_mod : return modulus<T>(arg0,arg1);
  4135. case e_pow : return pow<T>(arg0,arg1);
  4136. case e_atan2 : return atan2<T>(arg0,arg1);
  4137. case e_min : return std::min<T>(arg0,arg1);
  4138. case e_max : return std::max<T>(arg0,arg1);
  4139. case e_logn : return logn<T>(arg0,arg1);
  4140. case e_lt : return (arg0 < arg1) ? T(1) : T(0);
  4141. case e_lte : return (arg0 <= arg1) ? T(1) : T(0);
  4142. case e_eq : return std::equal_to<T>()(arg0,arg1) ? T(1) : T(0);
  4143. case e_ne : return std::not_equal_to<T>()(arg0,arg1) ? T(1) : T(0);
  4144. case e_gte : return (arg0 >= arg1) ? T(1) : T(0);
  4145. case e_gt : return (arg0 > arg1) ? T(1) : T(0);
  4146. case e_and : return and_opr <T>(arg0,arg1);
  4147. case e_nand : return nand_opr<T>(arg0,arg1);
  4148. case e_or : return or_opr <T>(arg0,arg1);
  4149. case e_nor : return nor_opr <T>(arg0,arg1);
  4150. case e_xor : return xor_opr <T>(arg0,arg1);
  4151. case e_xnor : return xnor_opr<T>(arg0,arg1);
  4152. case e_root : return root <T>(arg0,arg1);
  4153. case e_roundn : return roundn <T>(arg0,arg1);
  4154. case e_equal : return equal (arg0,arg1);
  4155. case e_nequal : return nequal (arg0,arg1);
  4156. case e_hypot : return hypot <T>(arg0,arg1);
  4157. case e_shr : return shr <T>(arg0,arg1);
  4158. case e_shl : return shl <T>(arg0,arg1);
  4159. default : exprtk_debug(("numeric::details::process_impl<T> - Invalid binary operation.\n"));
  4160. return std::numeric_limits<T>::quiet_NaN();
  4161. }
  4162. }
  4163. template <typename T>
  4164. inline T process_impl(const operator_type operation, const T arg0, const T arg1, int_type_tag)
  4165. {
  4166. switch (operation)
  4167. {
  4168. case e_add : return (arg0 + arg1);
  4169. case e_sub : return (arg0 - arg1);
  4170. case e_mul : return (arg0 * arg1);
  4171. case e_div : return (arg0 / arg1);
  4172. case e_mod : return arg0 % arg1;
  4173. case e_pow : return pow<T>(arg0,arg1);
  4174. case e_min : return std::min<T>(arg0,arg1);
  4175. case e_max : return std::max<T>(arg0,arg1);
  4176. case e_logn : return logn<T>(arg0,arg1);
  4177. case e_lt : return (arg0 < arg1) ? T(1) : T(0);
  4178. case e_lte : return (arg0 <= arg1) ? T(1) : T(0);
  4179. case e_eq : return (arg0 == arg1) ? T(1) : T(0);
  4180. case e_ne : return (arg0 != arg1) ? T(1) : T(0);
  4181. case e_gte : return (arg0 >= arg1) ? T(1) : T(0);
  4182. case e_gt : return (arg0 > arg1) ? T(1) : T(0);
  4183. case e_and : return ((arg0 != T(0)) && (arg1 != T(0))) ? T(1) : T(0);
  4184. case e_nand : return ((arg0 != T(0)) && (arg1 != T(0))) ? T(0) : T(1);
  4185. case e_or : return ((arg0 != T(0)) || (arg1 != T(0))) ? T(1) : T(0);
  4186. case e_nor : return ((arg0 != T(0)) || (arg1 != T(0))) ? T(0) : T(1);
  4187. case e_xor : return arg0 ^ arg1;
  4188. case e_xnor : return !(arg0 ^ arg1);
  4189. case e_root : return root<T>(arg0,arg1);
  4190. case e_equal : return arg0 == arg1;
  4191. case e_nequal : return arg0 != arg1;
  4192. case e_hypot : return hypot<T>(arg0,arg1);
  4193. case e_shr : return arg0 >> arg1;
  4194. case e_shl : return arg0 << arg1;
  4195. default : exprtk_debug(("numeric::details::process_impl<IntType> - Invalid binary operation.\n"));
  4196. return std::numeric_limits<T>::quiet_NaN();
  4197. }
  4198. }
  4199. }
  4200. template <typename T>
  4201. inline T process(const operator_type operation, const T arg)
  4202. {
  4203. return exprtk::details::numeric::details::process_impl(operation,arg);
  4204. }
  4205. template <typename T>
  4206. inline T process(const operator_type operation, const T arg0, const T arg1)
  4207. {
  4208. return exprtk::details::numeric::details::process_impl(operation, arg0, arg1);
  4209. }
  4210. }
  4211. template <typename T>
  4212. class expression_node
  4213. {
  4214. public:
  4215. enum node_type
  4216. {
  4217. e_none , e_null , e_constant , e_unary ,
  4218. e_binary , e_binary_ext , e_trinary , e_quaternary ,
  4219. e_vararg , e_conditional , e_while , e_repeat ,
  4220. e_for , e_switch , e_mswitch , e_return ,
  4221. e_retenv , e_variable , e_stringvar , e_stringconst ,
  4222. e_stringvarrng , e_cstringvarrng , e_strgenrange , e_strconcat ,
  4223. e_stringvarsize , e_strswap , e_stringsize , e_stringvararg ,
  4224. e_function , e_vafunction , e_genfunction , e_strfunction ,
  4225. e_strcondition , e_strccondition , e_add , e_sub ,
  4226. e_mul , e_div , e_mod , e_pow ,
  4227. e_lt , e_lte , e_gt , e_gte ,
  4228. e_eq , e_ne , e_and , e_nand ,
  4229. e_or , e_nor , e_xor , e_xnor ,
  4230. e_in , e_like , e_ilike , e_inranges ,
  4231. e_ipow , e_ipowinv , e_abs , e_acos ,
  4232. e_acosh , e_asin , e_asinh , e_atan ,
  4233. e_atanh , e_ceil , e_cos , e_cosh ,
  4234. e_exp , e_expm1 , e_floor , e_log ,
  4235. e_log10 , e_log2 , e_log1p , e_neg ,
  4236. e_pos , e_round , e_sin , e_sinc ,
  4237. e_sinh , e_sqrt , e_tan , e_tanh ,
  4238. e_cot , e_sec , e_csc , e_r2d ,
  4239. e_d2r , e_d2g , e_g2d , e_notl ,
  4240. e_sgn , e_erf , e_erfc , e_ncdf ,
  4241. e_frac , e_trunc , e_uvouv , e_vov ,
  4242. e_cov , e_voc , e_vob , e_bov ,
  4243. e_cob , e_boc , e_vovov , e_vovoc ,
  4244. e_vocov , e_covov , e_covoc , e_vovovov ,
  4245. e_vovovoc , e_vovocov , e_vocovov , e_covovov ,
  4246. e_covocov , e_vocovoc , e_covovoc , e_vococov ,
  4247. e_sf3ext , e_sf4ext , e_nulleq , e_strass ,
  4248. e_vector , e_vecelem , e_rbvecelem , e_rbveccelem ,
  4249. e_vecdefass , e_vecvalass , e_vecvecass , e_vecopvalass ,
  4250. e_vecopvecass , e_vecfunc , e_vecvecswap , e_vecvecineq ,
  4251. e_vecvalineq , e_valvecineq , e_vecvecarith , e_vecvalarith ,
  4252. e_valvecarith , e_vecunaryop , e_break , e_continue ,
  4253. e_swap
  4254. };
  4255. typedef T value_type;
  4256. typedef expression_node<T>* expression_ptr;
  4257. virtual ~expression_node()
  4258. {}
  4259. inline virtual T value() const
  4260. {
  4261. return std::numeric_limits<T>::quiet_NaN();
  4262. }
  4263. inline virtual expression_node<T>* branch(const std::size_t& index = 0) const
  4264. {
  4265. return reinterpret_cast<expression_ptr>(index * 0);
  4266. }
  4267. inline virtual node_type type() const
  4268. {
  4269. return e_none;
  4270. }
  4271. };
  4272. template <typename T>
  4273. inline bool is_generally_string_node(const expression_node<T>* node);
  4274. inline bool is_true(const double v)
  4275. {
  4276. return std::not_equal_to<double>()(0.0,v);
  4277. }
  4278. inline bool is_true(const long double v)
  4279. {
  4280. return std::not_equal_to<long double>()(0.0L,v);
  4281. }
  4282. inline bool is_true(const float v)
  4283. {
  4284. return std::not_equal_to<float>()(0.0f,v);
  4285. }
  4286. template <typename T>
  4287. inline bool is_true(const std::complex<T>& v)
  4288. {
  4289. return std::not_equal_to<std::complex<T> >()(std::complex<T>(0),v);
  4290. }
  4291. template <typename T>
  4292. inline bool is_true(const expression_node<T>* node)
  4293. {
  4294. return std::not_equal_to<T>()(T(0),node->value());
  4295. }
  4296. template <typename T>
  4297. inline bool is_false(const expression_node<T>* node)
  4298. {
  4299. return std::equal_to<T>()(T(0),node->value());
  4300. }
  4301. template <typename T>
  4302. inline bool is_unary_node(const expression_node<T>* node)
  4303. {
  4304. return node && (details::expression_node<T>::e_unary == node->type());
  4305. }
  4306. template <typename T>
  4307. inline bool is_neg_unary_node(const expression_node<T>* node)
  4308. {
  4309. return node && (details::expression_node<T>::e_neg == node->type());
  4310. }
  4311. template <typename T>
  4312. inline bool is_binary_node(const expression_node<T>* node)
  4313. {
  4314. return node && (details::expression_node<T>::e_binary == node->type());
  4315. }
  4316. template <typename T>
  4317. inline bool is_variable_node(const expression_node<T>* node)
  4318. {
  4319. return node && (details::expression_node<T>::e_variable == node->type());
  4320. }
  4321. template <typename T>
  4322. inline bool is_ivariable_node(const expression_node<T>* node)
  4323. {
  4324. return node &&
  4325. (
  4326. details::expression_node<T>::e_variable == node->type() ||
  4327. details::expression_node<T>::e_vecelem == node->type() ||
  4328. details::expression_node<T>::e_rbvecelem == node->type() ||
  4329. details::expression_node<T>::e_rbveccelem == node->type()
  4330. );
  4331. }
  4332. template <typename T>
  4333. inline bool is_vector_elem_node(const expression_node<T>* node)
  4334. {
  4335. return node && (details::expression_node<T>::e_vecelem == node->type());
  4336. }
  4337. template <typename T>
  4338. inline bool is_rebasevector_elem_node(const expression_node<T>* node)
  4339. {
  4340. return node && (details::expression_node<T>::e_rbvecelem == node->type());
  4341. }
  4342. template <typename T>
  4343. inline bool is_rebasevector_celem_node(const expression_node<T>* node)
  4344. {
  4345. return node && (details::expression_node<T>::e_rbveccelem == node->type());
  4346. }
  4347. template <typename T>
  4348. inline bool is_vector_node(const expression_node<T>* node)
  4349. {
  4350. return node && (details::expression_node<T>::e_vector == node->type());
  4351. }
  4352. template <typename T>
  4353. inline bool is_ivector_node(const expression_node<T>* node)
  4354. {
  4355. if (node)
  4356. {
  4357. switch (node->type())
  4358. {
  4359. case details::expression_node<T>::e_vector :
  4360. case details::expression_node<T>::e_vecvalass :
  4361. case details::expression_node<T>::e_vecvecass :
  4362. case details::expression_node<T>::e_vecopvalass :
  4363. case details::expression_node<T>::e_vecopvecass :
  4364. case details::expression_node<T>::e_vecvecswap :
  4365. case details::expression_node<T>::e_vecvecarith :
  4366. case details::expression_node<T>::e_vecvalarith :
  4367. case details::expression_node<T>::e_valvecarith :
  4368. case details::expression_node<T>::e_vecunaryop : return true;
  4369. default : return false;
  4370. }
  4371. }
  4372. else
  4373. return false;
  4374. }
  4375. template <typename T>
  4376. inline bool is_constant_node(const expression_node<T>* node)
  4377. {
  4378. return node && (details::expression_node<T>::e_constant == node->type());
  4379. }
  4380. template <typename T>
  4381. inline bool is_null_node(const expression_node<T>* node)
  4382. {
  4383. return node && (details::expression_node<T>::e_null == node->type());
  4384. }
  4385. template <typename T>
  4386. inline bool is_break_node(const expression_node<T>* node)
  4387. {
  4388. return node && (details::expression_node<T>::e_break == node->type());
  4389. }
  4390. template <typename T>
  4391. inline bool is_continue_node(const expression_node<T>* node)
  4392. {
  4393. return node && (details::expression_node<T>::e_continue == node->type());
  4394. }
  4395. template <typename T>
  4396. inline bool is_swap_node(const expression_node<T>* node)
  4397. {
  4398. return node && (details::expression_node<T>::e_swap == node->type());
  4399. }
  4400. template <typename T>
  4401. inline bool is_function(const expression_node<T>* node)
  4402. {
  4403. return node && (details::expression_node<T>::e_function == node->type());
  4404. }
  4405. template <typename T>
  4406. inline bool is_return_node(const expression_node<T>* node)
  4407. {
  4408. return node && (details::expression_node<T>::e_return == node->type());
  4409. }
  4410. template <typename T> class unary_node;
  4411. template <typename T>
  4412. inline bool is_negate_node(const expression_node<T>* node)
  4413. {
  4414. if (node && is_unary_node(node))
  4415. {
  4416. return (details::e_neg == static_cast<const unary_node<T>*>(node)->operation());
  4417. }
  4418. else
  4419. return false;
  4420. }
  4421. template <typename T>
  4422. inline bool branch_deletable(expression_node<T>* node)
  4423. {
  4424. return !is_variable_node(node) &&
  4425. !is_string_node (node) ;
  4426. }
  4427. template <std::size_t N, typename T>
  4428. inline bool all_nodes_valid(expression_node<T>* (&b)[N])
  4429. {
  4430. for (std::size_t i = 0; i < N; ++i)
  4431. {
  4432. if (0 == b[i]) return false;
  4433. }
  4434. return true;
  4435. }
  4436. template <typename T,
  4437. typename Allocator,
  4438. template <typename, typename> class Sequence>
  4439. inline bool all_nodes_valid(const Sequence<expression_node<T>*,Allocator>& b)
  4440. {
  4441. for (std::size_t i = 0; i < b.size(); ++i)
  4442. {
  4443. if (0 == b[i]) return false;
  4444. }
  4445. return true;
  4446. }
  4447. template <std::size_t N, typename T>
  4448. inline bool all_nodes_variables(expression_node<T>* (&b)[N])
  4449. {
  4450. for (std::size_t i = 0; i < N; ++i)
  4451. {
  4452. if (0 == b[i])
  4453. return false;
  4454. else if (!is_variable_node(b[i]))
  4455. return false;
  4456. }
  4457. return true;
  4458. }
  4459. template <typename T,
  4460. typename Allocator,
  4461. template <typename, typename> class Sequence>
  4462. inline bool all_nodes_variables(Sequence<expression_node<T>*,Allocator>& b)
  4463. {
  4464. for (std::size_t i = 0; i < b.size(); ++i)
  4465. {
  4466. if (0 == b[i])
  4467. return false;
  4468. else if (!is_variable_node(b[i]))
  4469. return false;
  4470. }
  4471. return true;
  4472. }
  4473. template <typename NodeAllocator, typename T, std::size_t N>
  4474. inline void free_all_nodes(NodeAllocator& node_allocator, expression_node<T>* (&b)[N])
  4475. {
  4476. for (std::size_t i = 0; i < N; ++i)
  4477. {
  4478. free_node(node_allocator,b[i]);
  4479. }
  4480. }
  4481. template <typename NodeAllocator,
  4482. typename T,
  4483. typename Allocator,
  4484. template <typename, typename> class Sequence>
  4485. inline void free_all_nodes(NodeAllocator& node_allocator, Sequence<expression_node<T>*,Allocator>& b)
  4486. {
  4487. for (std::size_t i = 0; i < b.size(); ++i)
  4488. {
  4489. free_node(node_allocator,b[i]);
  4490. }
  4491. b.clear();
  4492. }
  4493. template <typename NodeAllocator, typename T>
  4494. inline void free_node(NodeAllocator& node_allocator, expression_node<T>*& node, const bool force_delete = false)
  4495. {
  4496. if (0 != node)
  4497. {
  4498. if (
  4499. (is_variable_node(node) || is_string_node(node)) ||
  4500. force_delete
  4501. )
  4502. return;
  4503. node_allocator.free(node);
  4504. node = reinterpret_cast<expression_node<T>*>(0);
  4505. }
  4506. }
  4507. template <typename T>
  4508. inline void destroy_node(expression_node<T>*& node)
  4509. {
  4510. delete node;
  4511. node = reinterpret_cast<expression_node<T>*>(0);
  4512. }
  4513. template <typename Type>
  4514. class vector_holder
  4515. {
  4516. private:
  4517. typedef Type value_type;
  4518. typedef value_type* value_ptr;
  4519. typedef const value_ptr const_value_ptr;
  4520. class vector_holder_base
  4521. {
  4522. public:
  4523. virtual ~vector_holder_base() {}
  4524. inline value_ptr operator[](const std::size_t& index) const
  4525. {
  4526. return value_at(index);
  4527. }
  4528. inline std::size_t size() const
  4529. {
  4530. return vector_size();
  4531. }
  4532. inline value_ptr data() const
  4533. {
  4534. return value_at(0);
  4535. }
  4536. virtual inline bool rebaseable() const
  4537. {
  4538. return false;
  4539. }
  4540. virtual void set_ref(value_ptr*) {}
  4541. protected:
  4542. virtual value_ptr value_at(const std::size_t&) const = 0;
  4543. virtual std::size_t vector_size() const = 0;
  4544. };
  4545. class array_vector_impl : public vector_holder_base
  4546. {
  4547. public:
  4548. array_vector_impl(const Type* vec, const std::size_t& vec_size)
  4549. : vec_(vec),
  4550. size_(vec_size)
  4551. {}
  4552. protected:
  4553. value_ptr value_at(const std::size_t& index) const
  4554. {
  4555. if (index < size_)
  4556. return const_cast<const_value_ptr>(vec_ + index);
  4557. else
  4558. return const_value_ptr(0);
  4559. }
  4560. std::size_t vector_size() const
  4561. {
  4562. return size_;
  4563. }
  4564. private:
  4565. array_vector_impl operator=(const array_vector_impl&);
  4566. const Type* vec_;
  4567. const std::size_t size_;
  4568. };
  4569. template <typename Allocator,
  4570. template <typename, typename> class Sequence>
  4571. class sequence_vector_impl : public vector_holder_base
  4572. {
  4573. public:
  4574. typedef Sequence<Type,Allocator> sequence_t;
  4575. sequence_vector_impl(sequence_t& seq)
  4576. : sequence_(seq)
  4577. {}
  4578. protected:
  4579. value_ptr value_at(const std::size_t& index) const
  4580. {
  4581. return (index < sequence_.size()) ? (&sequence_[index]) : const_value_ptr(0);
  4582. }
  4583. std::size_t vector_size() const
  4584. {
  4585. return sequence_.size();
  4586. }
  4587. private:
  4588. sequence_vector_impl operator=(const sequence_vector_impl&);
  4589. sequence_t& sequence_;
  4590. };
  4591. class vector_view_impl : public vector_holder_base
  4592. {
  4593. public:
  4594. typedef exprtk::vector_view<Type> vector_view_t;
  4595. vector_view_impl(vector_view_t& vec_view)
  4596. : vec_view_(vec_view)
  4597. {}
  4598. void set_ref(value_ptr* ref)
  4599. {
  4600. vec_view_.set_ref(ref);
  4601. }
  4602. virtual inline bool rebaseable() const
  4603. {
  4604. return true;
  4605. }
  4606. protected:
  4607. value_ptr value_at(const std::size_t& index) const
  4608. {
  4609. return (index < vec_view_.size()) ? (&vec_view_[index]) : const_value_ptr(0);
  4610. }
  4611. std::size_t vector_size() const
  4612. {
  4613. return vec_view_.size();
  4614. }
  4615. private:
  4616. vector_view_impl operator=(const vector_view_impl&);
  4617. vector_view_t& vec_view_;
  4618. };
  4619. public:
  4620. typedef typename details::vec_data_store<Type> vds_t;
  4621. vector_holder(Type* vec, const std::size_t& vec_size)
  4622. : vector_holder_base_(new(buffer)array_vector_impl(vec,vec_size))
  4623. {}
  4624. vector_holder(const vds_t& vds)
  4625. : vector_holder_base_(new(buffer)array_vector_impl(vds.data(),vds.size()))
  4626. {}
  4627. template <typename Allocator>
  4628. vector_holder(std::vector<Type,Allocator>& vec)
  4629. : vector_holder_base_(new(buffer)sequence_vector_impl<Allocator,std::vector>(vec))
  4630. {}
  4631. vector_holder(exprtk::vector_view<Type>& vec)
  4632. : vector_holder_base_(new(buffer)vector_view_impl(vec))
  4633. {}
  4634. inline value_ptr operator[](const std::size_t& index) const
  4635. {
  4636. return (*vector_holder_base_)[index];
  4637. }
  4638. inline std::size_t size() const
  4639. {
  4640. return vector_holder_base_->size();
  4641. }
  4642. inline value_ptr data() const
  4643. {
  4644. return vector_holder_base_->data();
  4645. }
  4646. void set_ref(value_ptr* ref)
  4647. {
  4648. vector_holder_base_->set_ref(ref);
  4649. }
  4650. bool rebaseable() const
  4651. {
  4652. return vector_holder_base_->rebaseable();
  4653. }
  4654. private:
  4655. mutable vector_holder_base* vector_holder_base_;
  4656. uchar_t buffer[64];
  4657. };
  4658. template <typename T>
  4659. class null_node : public expression_node<T>
  4660. {
  4661. public:
  4662. inline T value() const
  4663. {
  4664. return std::numeric_limits<T>::quiet_NaN();
  4665. }
  4666. inline typename expression_node<T>::node_type type() const
  4667. {
  4668. return expression_node<T>::e_null;
  4669. }
  4670. };
  4671. template <typename T>
  4672. class null_eq_node : public expression_node<T>
  4673. {
  4674. public:
  4675. typedef expression_node<T>* expression_ptr;
  4676. null_eq_node(expression_ptr brnch, const bool equality = true)
  4677. : branch_(brnch),
  4678. branch_deletable_(branch_deletable(branch_)),
  4679. equality_(equality)
  4680. {}
  4681. ~null_eq_node()
  4682. {
  4683. if (branch_ && branch_deletable_)
  4684. {
  4685. destroy_node(branch_);
  4686. }
  4687. }
  4688. inline T value() const
  4689. {
  4690. const T v = branch_->value();
  4691. const bool result = details::numeric::is_nan(v);
  4692. if (result)
  4693. return (equality_) ? T(1) : T(0);
  4694. else
  4695. return (equality_) ? T(0) : T(1);
  4696. }
  4697. inline typename expression_node<T>::node_type type() const
  4698. {
  4699. return expression_node<T>::e_nulleq;
  4700. }
  4701. inline operator_type operation() const
  4702. {
  4703. return details::e_eq;
  4704. }
  4705. inline expression_node<T>* branch(const std::size_t&) const
  4706. {
  4707. return branch_;
  4708. }
  4709. private:
  4710. expression_ptr branch_;
  4711. const bool branch_deletable_;
  4712. bool equality_;
  4713. };
  4714. template <typename T>
  4715. class literal_node : public expression_node<T>
  4716. {
  4717. public:
  4718. explicit literal_node(const T& v)
  4719. : value_(v)
  4720. {}
  4721. inline T value() const
  4722. {
  4723. return value_;
  4724. }
  4725. inline typename expression_node<T>::node_type type() const
  4726. {
  4727. return expression_node<T>::e_constant;
  4728. }
  4729. inline expression_node<T>* branch(const std::size_t&) const
  4730. {
  4731. return reinterpret_cast<expression_node<T>*>(0);
  4732. }
  4733. private:
  4734. literal_node(literal_node<T>&) {}
  4735. literal_node<T>& operator=(literal_node<T>&) { return (*this); }
  4736. const T value_;
  4737. };
  4738. template <typename T>
  4739. struct range_pack;
  4740. template <typename T>
  4741. struct range_data_type;
  4742. template <typename T>
  4743. class range_interface
  4744. {
  4745. public:
  4746. typedef range_pack<T> range_t;
  4747. virtual ~range_interface()
  4748. {}
  4749. virtual range_t& range_ref() = 0;
  4750. virtual const range_t& range_ref() const = 0;
  4751. };
  4752. #ifndef exprtk_disable_string_capabilities
  4753. template <typename T>
  4754. class string_base_node
  4755. {
  4756. public:
  4757. typedef range_data_type<T> range_data_type_t;
  4758. virtual ~string_base_node()
  4759. {}
  4760. virtual std::string str () const = 0;
  4761. virtual char_cptr base() const = 0;
  4762. virtual std::size_t size() const = 0;
  4763. };
  4764. template <typename T>
  4765. class string_literal_node : public expression_node <T>,
  4766. public string_base_node<T>,
  4767. public range_interface <T>
  4768. {
  4769. public:
  4770. typedef range_pack<T> range_t;
  4771. explicit string_literal_node(const std::string& v)
  4772. : value_(v)
  4773. {
  4774. rp_.n0_c = std::make_pair<bool,std::size_t>(true,0);
  4775. rp_.n1_c = std::make_pair<bool,std::size_t>(true,v.size() - 1);
  4776. rp_.cache.first = rp_.n0_c.second;
  4777. rp_.cache.second = rp_.n1_c.second;
  4778. }
  4779. inline T value() const
  4780. {
  4781. return std::numeric_limits<T>::quiet_NaN();
  4782. }
  4783. inline typename expression_node<T>::node_type type() const
  4784. {
  4785. return expression_node<T>::e_stringconst;
  4786. }
  4787. inline expression_node<T>* branch(const std::size_t&) const
  4788. {
  4789. return reinterpret_cast<expression_node<T>*>(0);
  4790. }
  4791. std::string str() const
  4792. {
  4793. return value_;
  4794. }
  4795. char_cptr base() const
  4796. {
  4797. return value_.data();
  4798. }
  4799. std::size_t size() const
  4800. {
  4801. return value_.size();
  4802. }
  4803. range_t& range_ref()
  4804. {
  4805. return rp_;
  4806. }
  4807. const range_t& range_ref() const
  4808. {
  4809. return rp_;
  4810. }
  4811. private:
  4812. string_literal_node(const string_literal_node<T>&);
  4813. string_literal_node<T>& operator=(const string_literal_node<T>&);
  4814. const std::string value_;
  4815. range_t rp_;
  4816. };
  4817. #endif
  4818. template <typename T>
  4819. class unary_node : public expression_node<T>
  4820. {
  4821. public:
  4822. typedef expression_node<T>* expression_ptr;
  4823. unary_node(const operator_type& opr,
  4824. expression_ptr brnch)
  4825. : operation_(opr),
  4826. branch_(brnch),
  4827. branch_deletable_(branch_deletable(branch_))
  4828. {}
  4829. ~unary_node()
  4830. {
  4831. if (branch_ && branch_deletable_)
  4832. {
  4833. destroy_node(branch_);
  4834. }
  4835. }
  4836. inline T value() const
  4837. {
  4838. const T arg = branch_->value();
  4839. return numeric::process<T>(operation_,arg);
  4840. }
  4841. inline typename expression_node<T>::node_type type() const
  4842. {
  4843. return expression_node<T>::e_unary;
  4844. }
  4845. inline operator_type operation() const
  4846. {
  4847. return operation_;
  4848. }
  4849. inline expression_node<T>* branch(const std::size_t&) const
  4850. {
  4851. return branch_;
  4852. }
  4853. inline void release()
  4854. {
  4855. branch_deletable_ = false;
  4856. }
  4857. protected:
  4858. operator_type operation_;
  4859. expression_ptr branch_;
  4860. bool branch_deletable_;
  4861. };
  4862. template <typename T, std::size_t D, bool B>
  4863. struct construct_branch_pair
  4864. {
  4865. template <std::size_t N>
  4866. static inline void process(std::pair<expression_node<T>*,bool> (&)[N], expression_node<T>*)
  4867. {}
  4868. };
  4869. template <typename T, std::size_t D>
  4870. struct construct_branch_pair<T,D,true>
  4871. {
  4872. template <std::size_t N>
  4873. static inline void process(std::pair<expression_node<T>*,bool> (&branch)[N], expression_node<T>* b)
  4874. {
  4875. if (b)
  4876. {
  4877. branch[D] = std::make_pair(b,branch_deletable(b));
  4878. }
  4879. }
  4880. };
  4881. template <std::size_t N, typename T>
  4882. inline void init_branches(std::pair<expression_node<T>*,bool> (&branch)[N],
  4883. expression_node<T>* b0,
  4884. expression_node<T>* b1 = reinterpret_cast<expression_node<T>*>(0),
  4885. expression_node<T>* b2 = reinterpret_cast<expression_node<T>*>(0),
  4886. expression_node<T>* b3 = reinterpret_cast<expression_node<T>*>(0),
  4887. expression_node<T>* b4 = reinterpret_cast<expression_node<T>*>(0),
  4888. expression_node<T>* b5 = reinterpret_cast<expression_node<T>*>(0),
  4889. expression_node<T>* b6 = reinterpret_cast<expression_node<T>*>(0),
  4890. expression_node<T>* b7 = reinterpret_cast<expression_node<T>*>(0),
  4891. expression_node<T>* b8 = reinterpret_cast<expression_node<T>*>(0),
  4892. expression_node<T>* b9 = reinterpret_cast<expression_node<T>*>(0))
  4893. {
  4894. construct_branch_pair<T,0,(N > 0)>::process(branch,b0);
  4895. construct_branch_pair<T,1,(N > 1)>::process(branch,b1);
  4896. construct_branch_pair<T,2,(N > 2)>::process(branch,b2);
  4897. construct_branch_pair<T,3,(N > 3)>::process(branch,b3);
  4898. construct_branch_pair<T,4,(N > 4)>::process(branch,b4);
  4899. construct_branch_pair<T,5,(N > 5)>::process(branch,b5);
  4900. construct_branch_pair<T,6,(N > 6)>::process(branch,b6);
  4901. construct_branch_pair<T,7,(N > 7)>::process(branch,b7);
  4902. construct_branch_pair<T,8,(N > 8)>::process(branch,b8);
  4903. construct_branch_pair<T,9,(N > 9)>::process(branch,b9);
  4904. }
  4905. struct cleanup_branches
  4906. {
  4907. template <typename T, std::size_t N>
  4908. static inline void execute(std::pair<expression_node<T>*,bool> (&branch)[N])
  4909. {
  4910. for (std::size_t i = 0; i < N; ++i)
  4911. {
  4912. if (branch[i].first && branch[i].second)
  4913. {
  4914. destroy_node(branch[i].first);
  4915. }
  4916. }
  4917. }
  4918. template <typename T,
  4919. typename Allocator,
  4920. template <typename, typename> class Sequence>
  4921. static inline void execute(Sequence<std::pair<expression_node<T>*,bool>,Allocator>& branch)
  4922. {
  4923. for (std::size_t i = 0; i < branch.size(); ++i)
  4924. {
  4925. if (branch[i].first && branch[i].second)
  4926. {
  4927. destroy_node(branch[i].first);
  4928. }
  4929. }
  4930. }
  4931. };
  4932. template <typename T>
  4933. class binary_node : public expression_node<T>
  4934. {
  4935. public:
  4936. typedef expression_node<T>* expression_ptr;
  4937. typedef std::pair<expression_ptr,bool> branch_t;
  4938. binary_node(const operator_type& opr,
  4939. expression_ptr branch0,
  4940. expression_ptr branch1)
  4941. : operation_(opr)
  4942. {
  4943. init_branches<2>(branch_, branch0, branch1);
  4944. }
  4945. ~binary_node()
  4946. {
  4947. cleanup_branches::execute<T,2>(branch_);
  4948. }
  4949. inline T value() const
  4950. {
  4951. const T arg0 = branch_[0].first->value();
  4952. const T arg1 = branch_[1].first->value();
  4953. return numeric::process<T>(operation_,arg0,arg1);
  4954. }
  4955. inline typename expression_node<T>::node_type type() const
  4956. {
  4957. return expression_node<T>::e_binary;
  4958. }
  4959. inline operator_type operation()
  4960. {
  4961. return operation_;
  4962. }
  4963. inline expression_node<T>* branch(const std::size_t& index = 0) const
  4964. {
  4965. if (0 == index)
  4966. return branch_[0].first;
  4967. else if (1 == index)
  4968. return branch_[1].first;
  4969. else
  4970. return reinterpret_cast<expression_ptr>(0);
  4971. }
  4972. protected:
  4973. operator_type operation_;
  4974. branch_t branch_[2];
  4975. };
  4976. template <typename T, typename Operation>
  4977. class binary_ext_node : public expression_node<T>
  4978. {
  4979. public:
  4980. typedef expression_node<T>* expression_ptr;
  4981. typedef std::pair<expression_ptr,bool> branch_t;
  4982. binary_ext_node(expression_ptr branch0, expression_ptr branch1)
  4983. {
  4984. init_branches<2>(branch_, branch0, branch1);
  4985. }
  4986. ~binary_ext_node()
  4987. {
  4988. cleanup_branches::execute<T,2>(branch_);
  4989. }
  4990. inline T value() const
  4991. {
  4992. const T arg0 = branch_[0].first->value();
  4993. const T arg1 = branch_[1].first->value();
  4994. return Operation::process(arg0,arg1);
  4995. }
  4996. inline typename expression_node<T>::node_type type() const
  4997. {
  4998. return expression_node<T>::e_binary_ext;
  4999. }
  5000. inline operator_type operation()
  5001. {
  5002. return Operation::operation();
  5003. }
  5004. inline expression_node<T>* branch(const std::size_t& index = 0) const
  5005. {
  5006. if (0 == index)
  5007. return branch_[0].first;
  5008. else if (1 == index)
  5009. return branch_[1].first;
  5010. else
  5011. return reinterpret_cast<expression_ptr>(0);
  5012. }
  5013. protected:
  5014. branch_t branch_[2];
  5015. };
  5016. template <typename T>
  5017. class trinary_node : public expression_node<T>
  5018. {
  5019. public:
  5020. typedef expression_node<T>* expression_ptr;
  5021. typedef std::pair<expression_ptr,bool> branch_t;
  5022. trinary_node(const operator_type& opr,
  5023. expression_ptr branch0,
  5024. expression_ptr branch1,
  5025. expression_ptr branch2)
  5026. : operation_(opr)
  5027. {
  5028. init_branches<3>(branch_, branch0, branch1, branch2);
  5029. }
  5030. ~trinary_node()
  5031. {
  5032. cleanup_branches::execute<T,3>(branch_);
  5033. }
  5034. inline T value() const
  5035. {
  5036. const T arg0 = branch_[0].first->value();
  5037. const T arg1 = branch_[1].first->value();
  5038. const T arg2 = branch_[2].first->value();
  5039. switch (operation_)
  5040. {
  5041. case e_inrange : return (arg1 < arg0) ? T(0) : ((arg1 > arg2) ? T(0) : T(1));
  5042. case e_clamp : return (arg1 < arg0) ? arg0 : (arg1 > arg2 ? arg2 : arg1);
  5043. case e_iclamp : if ((arg1 <= arg0) || (arg1 >= arg2))
  5044. return arg1;
  5045. else
  5046. return ((T(2) * arg1 <= (arg2 + arg0)) ? arg0 : arg2);
  5047. default : exprtk_debug(("trinary_node::value() - Error: Invalid operation\n"));
  5048. return std::numeric_limits<T>::quiet_NaN();
  5049. }
  5050. }
  5051. inline typename expression_node<T>::node_type type() const
  5052. {
  5053. return expression_node<T>::e_trinary;
  5054. }
  5055. protected:
  5056. operator_type operation_;
  5057. branch_t branch_[3];
  5058. };
  5059. template <typename T>
  5060. class quaternary_node : public expression_node<T>
  5061. {
  5062. public:
  5063. typedef expression_node<T>* expression_ptr;
  5064. typedef std::pair<expression_ptr,bool> branch_t;
  5065. quaternary_node(const operator_type& opr,
  5066. expression_ptr branch0,
  5067. expression_ptr branch1,
  5068. expression_ptr branch2,
  5069. expression_ptr branch3)
  5070. : operation_(opr)
  5071. {
  5072. init_branches<4>(branch_, branch0, branch1, branch2, branch3);
  5073. }
  5074. ~quaternary_node()
  5075. {
  5076. cleanup_branches::execute<T,4>(branch_);
  5077. }
  5078. inline T value() const
  5079. {
  5080. return std::numeric_limits<T>::quiet_NaN();
  5081. }
  5082. inline typename expression_node<T>::node_type type() const
  5083. {
  5084. return expression_node<T>::e_quaternary;
  5085. }
  5086. protected:
  5087. operator_type operation_;
  5088. branch_t branch_[4];
  5089. };
  5090. template <typename T>
  5091. class conditional_node : public expression_node<T>
  5092. {
  5093. public:
  5094. typedef expression_node<T>* expression_ptr;
  5095. conditional_node(expression_ptr test,
  5096. expression_ptr consequent,
  5097. expression_ptr alternative)
  5098. : test_(test),
  5099. consequent_(consequent),
  5100. alternative_(alternative),
  5101. test_deletable_(branch_deletable(test_)),
  5102. consequent_deletable_(branch_deletable(consequent_)),
  5103. alternative_deletable_(branch_deletable(alternative_))
  5104. {}
  5105. ~conditional_node()
  5106. {
  5107. if (test_ && test_deletable_)
  5108. {
  5109. destroy_node(test_);
  5110. }
  5111. if (consequent_ && consequent_deletable_ )
  5112. {
  5113. destroy_node(consequent_);
  5114. }
  5115. if (alternative_ && alternative_deletable_)
  5116. {
  5117. destroy_node(alternative_);
  5118. }
  5119. }
  5120. inline T value() const
  5121. {
  5122. if (is_true(test_))
  5123. return consequent_->value();
  5124. else
  5125. return alternative_->value();
  5126. }
  5127. inline typename expression_node<T>::node_type type() const
  5128. {
  5129. return expression_node<T>::e_conditional;
  5130. }
  5131. private:
  5132. expression_ptr test_;
  5133. expression_ptr consequent_;
  5134. expression_ptr alternative_;
  5135. const bool test_deletable_;
  5136. const bool consequent_deletable_;
  5137. const bool alternative_deletable_;
  5138. };
  5139. template <typename T>
  5140. class cons_conditional_node : public expression_node<T>
  5141. {
  5142. public:
  5143. // Consequent only conditional statement node
  5144. typedef expression_node<T>* expression_ptr;
  5145. cons_conditional_node(expression_ptr test,
  5146. expression_ptr consequent)
  5147. : test_(test),
  5148. consequent_(consequent),
  5149. test_deletable_(branch_deletable(test_)),
  5150. consequent_deletable_(branch_deletable(consequent_))
  5151. {}
  5152. ~cons_conditional_node()
  5153. {
  5154. if (test_ && test_deletable_)
  5155. {
  5156. destroy_node(test_);
  5157. }
  5158. if (consequent_ && consequent_deletable_)
  5159. {
  5160. destroy_node(consequent_);
  5161. }
  5162. }
  5163. inline T value() const
  5164. {
  5165. if (is_true(test_))
  5166. return consequent_->value();
  5167. else
  5168. return std::numeric_limits<T>::quiet_NaN();
  5169. }
  5170. inline typename expression_node<T>::node_type type() const
  5171. {
  5172. return expression_node<T>::e_conditional;
  5173. }
  5174. private:
  5175. expression_ptr test_;
  5176. expression_ptr consequent_;
  5177. const bool test_deletable_;
  5178. const bool consequent_deletable_;
  5179. };
  5180. #ifndef exprtk_disable_break_continue
  5181. template <typename T>
  5182. class break_exception
  5183. {
  5184. public:
  5185. break_exception(const T& v)
  5186. : value(v)
  5187. {}
  5188. T value;
  5189. };
  5190. class continue_exception
  5191. {};
  5192. template <typename T>
  5193. class break_node : public expression_node<T>
  5194. {
  5195. public:
  5196. typedef expression_node<T>* expression_ptr;
  5197. break_node(expression_ptr ret = expression_ptr(0))
  5198. : return_(ret),
  5199. return_deletable_(branch_deletable(return_))
  5200. {}
  5201. ~break_node()
  5202. {
  5203. if (return_deletable_)
  5204. {
  5205. destroy_node(return_);
  5206. }
  5207. }
  5208. inline T value() const
  5209. {
  5210. throw break_exception<T>(return_ ? return_->value() : std::numeric_limits<T>::quiet_NaN());
  5211. #ifndef _MSC_VER
  5212. return std::numeric_limits<T>::quiet_NaN();
  5213. #endif
  5214. }
  5215. inline typename expression_node<T>::node_type type() const
  5216. {
  5217. return expression_node<T>::e_break;
  5218. }
  5219. private:
  5220. expression_ptr return_;
  5221. const bool return_deletable_;
  5222. };
  5223. template <typename T>
  5224. class continue_node : public expression_node<T>
  5225. {
  5226. public:
  5227. inline T value() const
  5228. {
  5229. throw continue_exception();
  5230. #ifndef _MSC_VER
  5231. return std::numeric_limits<T>::quiet_NaN();
  5232. #endif
  5233. }
  5234. inline typename expression_node<T>::node_type type() const
  5235. {
  5236. return expression_node<T>::e_break;
  5237. }
  5238. };
  5239. #endif
  5240. template <typename T>
  5241. class while_loop_node : public expression_node<T>
  5242. {
  5243. public:
  5244. typedef expression_node<T>* expression_ptr;
  5245. while_loop_node(expression_ptr condition, expression_ptr loop_body)
  5246. : condition_(condition),
  5247. loop_body_(loop_body),
  5248. condition_deletable_(branch_deletable(condition_)),
  5249. loop_body_deletable_(branch_deletable(loop_body_))
  5250. {}
  5251. ~while_loop_node()
  5252. {
  5253. if (condition_ && condition_deletable_)
  5254. {
  5255. destroy_node(condition_);
  5256. }
  5257. if (loop_body_ && loop_body_deletable_)
  5258. {
  5259. destroy_node(loop_body_);
  5260. }
  5261. }
  5262. inline T value() const
  5263. {
  5264. T result = T(0);
  5265. while (is_true(condition_))
  5266. {
  5267. result = loop_body_->value();
  5268. }
  5269. return result;
  5270. }
  5271. inline typename expression_node<T>::node_type type() const
  5272. {
  5273. return expression_node<T>::e_while;
  5274. }
  5275. private:
  5276. expression_ptr condition_;
  5277. expression_ptr loop_body_;
  5278. const bool condition_deletable_;
  5279. const bool loop_body_deletable_;
  5280. };
  5281. template <typename T>
  5282. class repeat_until_loop_node : public expression_node<T>
  5283. {
  5284. public:
  5285. typedef expression_node<T>* expression_ptr;
  5286. repeat_until_loop_node(expression_ptr condition, expression_ptr loop_body)
  5287. : condition_(condition),
  5288. loop_body_(loop_body),
  5289. condition_deletable_(branch_deletable(condition_)),
  5290. loop_body_deletable_(branch_deletable(loop_body_))
  5291. {}
  5292. ~repeat_until_loop_node()
  5293. {
  5294. if (condition_ && condition_deletable_)
  5295. {
  5296. destroy_node(condition_);
  5297. }
  5298. if (loop_body_ && loop_body_deletable_)
  5299. {
  5300. destroy_node(loop_body_);
  5301. }
  5302. }
  5303. inline T value() const
  5304. {
  5305. T result = T(0);
  5306. do
  5307. {
  5308. result = loop_body_->value();
  5309. }
  5310. while (is_false(condition_));
  5311. return result;
  5312. }
  5313. inline typename expression_node<T>::node_type type() const
  5314. {
  5315. return expression_node<T>::e_repeat;
  5316. }
  5317. private:
  5318. expression_ptr condition_;
  5319. expression_ptr loop_body_;
  5320. const bool condition_deletable_;
  5321. const bool loop_body_deletable_;
  5322. };
  5323. template <typename T>
  5324. class for_loop_node : public expression_node<T>
  5325. {
  5326. public:
  5327. typedef expression_node<T>* expression_ptr;
  5328. for_loop_node(expression_ptr initialiser,
  5329. expression_ptr condition,
  5330. expression_ptr incrementor,
  5331. expression_ptr loop_body)
  5332. : initialiser_(initialiser),
  5333. condition_ (condition ),
  5334. incrementor_(incrementor),
  5335. loop_body_ (loop_body ),
  5336. initialiser_deletable_(branch_deletable(initialiser_)),
  5337. condition_deletable_ (branch_deletable(condition_ )),
  5338. incrementor_deletable_(branch_deletable(incrementor_)),
  5339. loop_body_deletable_ (branch_deletable(loop_body_ ))
  5340. {}
  5341. ~for_loop_node()
  5342. {
  5343. if (initialiser_ && initialiser_deletable_)
  5344. {
  5345. destroy_node(initialiser_);
  5346. }
  5347. if (condition_ && condition_deletable_)
  5348. {
  5349. destroy_node(condition_);
  5350. }
  5351. if (incrementor_ && incrementor_deletable_)
  5352. {
  5353. destroy_node(incrementor_);
  5354. }
  5355. if (loop_body_ && loop_body_deletable_)
  5356. {
  5357. destroy_node(loop_body_);
  5358. }
  5359. }
  5360. inline T value() const
  5361. {
  5362. T result = T(0);
  5363. if (initialiser_)
  5364. initialiser_->value();
  5365. if (incrementor_)
  5366. {
  5367. while (is_true(condition_))
  5368. {
  5369. result = loop_body_->value();
  5370. incrementor_->value();
  5371. }
  5372. }
  5373. else
  5374. {
  5375. while (is_true(condition_))
  5376. {
  5377. result = loop_body_->value();
  5378. }
  5379. }
  5380. return result;
  5381. }
  5382. inline typename expression_node<T>::node_type type() const
  5383. {
  5384. return expression_node<T>::e_for;
  5385. }
  5386. private:
  5387. expression_ptr initialiser_ ;
  5388. expression_ptr condition_ ;
  5389. expression_ptr incrementor_ ;
  5390. expression_ptr loop_body_ ;
  5391. const bool initialiser_deletable_;
  5392. const bool condition_deletable_ ;
  5393. const bool incrementor_deletable_;
  5394. const bool loop_body_deletable_ ;
  5395. };
  5396. #ifndef exprtk_disable_break_continue
  5397. template <typename T>
  5398. class while_loop_bc_node : public expression_node<T>
  5399. {
  5400. public:
  5401. typedef expression_node<T>* expression_ptr;
  5402. while_loop_bc_node(expression_ptr condition, expression_ptr loop_body)
  5403. : condition_(condition),
  5404. loop_body_(loop_body),
  5405. condition_deletable_(branch_deletable(condition_)),
  5406. loop_body_deletable_(branch_deletable(loop_body_))
  5407. {}
  5408. ~while_loop_bc_node()
  5409. {
  5410. if (condition_ && condition_deletable_)
  5411. {
  5412. destroy_node(condition_);
  5413. }
  5414. if (loop_body_ && loop_body_deletable_)
  5415. {
  5416. destroy_node(loop_body_);
  5417. }
  5418. }
  5419. inline T value() const
  5420. {
  5421. T result = T(0);
  5422. while (is_true(condition_))
  5423. {
  5424. try
  5425. {
  5426. result = loop_body_->value();
  5427. }
  5428. catch(const break_exception<T>& e)
  5429. {
  5430. return e.value;
  5431. }
  5432. catch(const continue_exception&)
  5433. {}
  5434. }
  5435. return result;
  5436. }
  5437. inline typename expression_node<T>::node_type type() const
  5438. {
  5439. return expression_node<T>::e_while;
  5440. }
  5441. private:
  5442. expression_ptr condition_;
  5443. expression_ptr loop_body_;
  5444. const bool condition_deletable_;
  5445. const bool loop_body_deletable_;
  5446. };
  5447. template <typename T>
  5448. class repeat_until_loop_bc_node : public expression_node<T>
  5449. {
  5450. public:
  5451. typedef expression_node<T>* expression_ptr;
  5452. repeat_until_loop_bc_node(expression_ptr condition, expression_ptr loop_body)
  5453. : condition_(condition),
  5454. loop_body_(loop_body),
  5455. condition_deletable_(branch_deletable(condition_)),
  5456. loop_body_deletable_(branch_deletable(loop_body_))
  5457. {}
  5458. ~repeat_until_loop_bc_node()
  5459. {
  5460. if (condition_ && condition_deletable_)
  5461. {
  5462. destroy_node(condition_);
  5463. }
  5464. if (loop_body_ && loop_body_deletable_)
  5465. {
  5466. destroy_node(loop_body_);
  5467. }
  5468. }
  5469. inline T value() const
  5470. {
  5471. T result = T(0);
  5472. do
  5473. {
  5474. try
  5475. {
  5476. result = loop_body_->value();
  5477. }
  5478. catch(const break_exception<T>& e)
  5479. {
  5480. return e.value;
  5481. }
  5482. catch(const continue_exception&)
  5483. {}
  5484. }
  5485. while (is_false(condition_));
  5486. return result;
  5487. }
  5488. inline typename expression_node<T>::node_type type() const
  5489. {
  5490. return expression_node<T>::e_repeat;
  5491. }
  5492. private:
  5493. expression_ptr condition_;
  5494. expression_ptr loop_body_;
  5495. const bool condition_deletable_;
  5496. const bool loop_body_deletable_;
  5497. };
  5498. template <typename T>
  5499. class for_loop_bc_node : public expression_node<T>
  5500. {
  5501. public:
  5502. typedef expression_node<T>* expression_ptr;
  5503. for_loop_bc_node(expression_ptr initialiser,
  5504. expression_ptr condition,
  5505. expression_ptr incrementor,
  5506. expression_ptr loop_body)
  5507. : initialiser_(initialiser),
  5508. condition_ (condition ),
  5509. incrementor_(incrementor),
  5510. loop_body_ (loop_body ),
  5511. initialiser_deletable_(branch_deletable(initialiser_)),
  5512. condition_deletable_ (branch_deletable(condition_ )),
  5513. incrementor_deletable_(branch_deletable(incrementor_)),
  5514. loop_body_deletable_ (branch_deletable(loop_body_ ))
  5515. {}
  5516. ~for_loop_bc_node()
  5517. {
  5518. if (initialiser_ && initialiser_deletable_)
  5519. {
  5520. destroy_node(initialiser_);
  5521. }
  5522. if (condition_ && condition_deletable_)
  5523. {
  5524. destroy_node(condition_);
  5525. }
  5526. if (incrementor_ && incrementor_deletable_)
  5527. {
  5528. destroy_node(incrementor_);
  5529. }
  5530. if (loop_body_ && loop_body_deletable_)
  5531. {
  5532. destroy_node(loop_body_);
  5533. }
  5534. }
  5535. inline T value() const
  5536. {
  5537. T result = T(0);
  5538. if (initialiser_)
  5539. initialiser_->value();
  5540. if (incrementor_)
  5541. {
  5542. while (is_true(condition_))
  5543. {
  5544. try
  5545. {
  5546. result = loop_body_->value();
  5547. }
  5548. catch(const break_exception<T>& e)
  5549. {
  5550. return e.value;
  5551. }
  5552. catch(const continue_exception&)
  5553. {}
  5554. incrementor_->value();
  5555. }
  5556. }
  5557. else
  5558. {
  5559. while (is_true(condition_))
  5560. {
  5561. try
  5562. {
  5563. result = loop_body_->value();
  5564. }
  5565. catch(const break_exception<T>& e)
  5566. {
  5567. return e.value;
  5568. }
  5569. catch(const continue_exception&)
  5570. {}
  5571. }
  5572. }
  5573. return result;
  5574. }
  5575. inline typename expression_node<T>::node_type type() const
  5576. {
  5577. return expression_node<T>::e_for;
  5578. }
  5579. private:
  5580. expression_ptr initialiser_;
  5581. expression_ptr condition_ ;
  5582. expression_ptr incrementor_;
  5583. expression_ptr loop_body_ ;
  5584. const bool initialiser_deletable_;
  5585. const bool condition_deletable_ ;
  5586. const bool incrementor_deletable_;
  5587. const bool loop_body_deletable_ ;
  5588. };
  5589. #endif
  5590. template <typename T>
  5591. class switch_node : public expression_node<T>
  5592. {
  5593. public:
  5594. typedef expression_node<T>* expression_ptr;
  5595. template <typename Allocator,
  5596. template <typename, typename> class Sequence>
  5597. explicit switch_node(const Sequence<expression_ptr,Allocator>& arg_list)
  5598. {
  5599. if (1 != (arg_list.size() & 1))
  5600. return;
  5601. arg_list_.resize(arg_list.size());
  5602. delete_branch_.resize(arg_list.size());
  5603. for (std::size_t i = 0; i < arg_list.size(); ++i)
  5604. {
  5605. if (arg_list[i])
  5606. {
  5607. arg_list_[i] = arg_list[i];
  5608. delete_branch_[i] = static_cast<unsigned char>(branch_deletable(arg_list_[i]) ? 1 : 0);
  5609. }
  5610. else
  5611. {
  5612. arg_list_.clear();
  5613. delete_branch_.clear();
  5614. return;
  5615. }
  5616. }
  5617. }
  5618. ~switch_node()
  5619. {
  5620. for (std::size_t i = 0; i < arg_list_.size(); ++i)
  5621. {
  5622. if (arg_list_[i] && delete_branch_[i])
  5623. {
  5624. destroy_node(arg_list_[i]);
  5625. }
  5626. }
  5627. }
  5628. inline T value() const
  5629. {
  5630. if (!arg_list_.empty())
  5631. {
  5632. const std::size_t upper_bound = (arg_list_.size() - 1);
  5633. for (std::size_t i = 0; i < upper_bound; i += 2)
  5634. {
  5635. expression_ptr condition = arg_list_[i ];
  5636. expression_ptr consequent = arg_list_[i + 1];
  5637. if (is_true(condition))
  5638. {
  5639. return consequent->value();
  5640. }
  5641. }
  5642. return arg_list_[upper_bound]->value();
  5643. }
  5644. else
  5645. return std::numeric_limits<T>::quiet_NaN();
  5646. }
  5647. inline typename expression_node<T>::node_type type() const
  5648. {
  5649. return expression_node<T>::e_switch;
  5650. }
  5651. protected:
  5652. std::vector<expression_ptr> arg_list_;
  5653. std::vector<unsigned char> delete_branch_;
  5654. };
  5655. template <typename T, typename Switch_N>
  5656. class switch_n_node : public switch_node<T>
  5657. {
  5658. public:
  5659. typedef expression_node<T>* expression_ptr;
  5660. template <typename Allocator,
  5661. template <typename, typename> class Sequence>
  5662. explicit switch_n_node(const Sequence<expression_ptr,Allocator>& arg_list)
  5663. : switch_node<T>(arg_list)
  5664. {}
  5665. inline T value() const
  5666. {
  5667. return Switch_N::process(switch_node<T>::arg_list_);
  5668. }
  5669. };
  5670. template <typename T>
  5671. class multi_switch_node : public expression_node<T>
  5672. {
  5673. public:
  5674. typedef expression_node<T>* expression_ptr;
  5675. template <typename Allocator,
  5676. template <typename, typename> class Sequence>
  5677. explicit multi_switch_node(const Sequence<expression_ptr,Allocator>& arg_list)
  5678. {
  5679. if (0 != (arg_list.size() & 1))
  5680. return;
  5681. arg_list_.resize(arg_list.size());
  5682. delete_branch_.resize(arg_list.size());
  5683. for (std::size_t i = 0; i < arg_list.size(); ++i)
  5684. {
  5685. if (arg_list[i])
  5686. {
  5687. arg_list_[i] = arg_list[i];
  5688. delete_branch_[i] = static_cast<unsigned char>(branch_deletable(arg_list_[i]) ? 1 : 0);
  5689. }
  5690. else
  5691. {
  5692. arg_list_.clear();
  5693. delete_branch_.clear();
  5694. return;
  5695. }
  5696. }
  5697. }
  5698. ~multi_switch_node()
  5699. {
  5700. for (std::size_t i = 0; i < arg_list_.size(); ++i)
  5701. {
  5702. if (arg_list_[i] && delete_branch_[i])
  5703. {
  5704. destroy_node(arg_list_[i]);
  5705. }
  5706. }
  5707. }
  5708. inline T value() const
  5709. {
  5710. T result = T(0);
  5711. if (arg_list_.empty())
  5712. {
  5713. return std::numeric_limits<T>::quiet_NaN();
  5714. }
  5715. const std::size_t upper_bound = (arg_list_.size() - 1);
  5716. for (std::size_t i = 0; i < upper_bound; i += 2)
  5717. {
  5718. expression_ptr condition = arg_list_[i ];
  5719. expression_ptr consequent = arg_list_[i + 1];
  5720. if (is_true(condition))
  5721. {
  5722. result = consequent->value();
  5723. }
  5724. }
  5725. return result;
  5726. }
  5727. inline typename expression_node<T>::node_type type() const
  5728. {
  5729. return expression_node<T>::e_mswitch;
  5730. }
  5731. private:
  5732. std::vector<expression_ptr> arg_list_;
  5733. std::vector<unsigned char> delete_branch_;
  5734. };
  5735. template <typename T>
  5736. class ivariable
  5737. {
  5738. public:
  5739. virtual ~ivariable()
  5740. {}
  5741. virtual T& ref() = 0;
  5742. virtual const T& ref() const = 0;
  5743. };
  5744. template <typename T>
  5745. class variable_node : public expression_node<T>,
  5746. public ivariable <T>
  5747. {
  5748. public:
  5749. static T null_value;
  5750. explicit variable_node()
  5751. : value_(&null_value)
  5752. {}
  5753. explicit variable_node(T& v)
  5754. : value_(&v)
  5755. {}
  5756. inline bool operator <(const variable_node<T>& v) const
  5757. {
  5758. return this < (&v);
  5759. }
  5760. inline T value() const
  5761. {
  5762. return (*value_);
  5763. }
  5764. inline T& ref()
  5765. {
  5766. return (*value_);
  5767. }
  5768. inline const T& ref() const
  5769. {
  5770. return (*value_);
  5771. }
  5772. inline typename expression_node<T>::node_type type() const
  5773. {
  5774. return expression_node<T>::e_variable;
  5775. }
  5776. private:
  5777. T* value_;
  5778. };
  5779. template <typename T>
  5780. T variable_node<T>::null_value = T(std::numeric_limits<T>::quiet_NaN());
  5781. template <typename T>
  5782. struct range_pack
  5783. {
  5784. typedef expression_node<T>* expression_node_ptr;
  5785. typedef std::pair<std::size_t,std::size_t> cached_range_t;
  5786. range_pack()
  5787. : n0_e (std::make_pair(false,expression_node_ptr(0))),
  5788. n1_e (std::make_pair(false,expression_node_ptr(0))),
  5789. n0_c (std::make_pair(false,0)),
  5790. n1_c (std::make_pair(false,0)),
  5791. cache(std::make_pair(0,0))
  5792. {}
  5793. void clear()
  5794. {
  5795. n0_e = std::make_pair(false,expression_node_ptr(0));
  5796. n1_e = std::make_pair(false,expression_node_ptr(0));
  5797. n0_c = std::make_pair(false,0);
  5798. n1_c = std::make_pair(false,0);
  5799. cache = std::make_pair(0,0);
  5800. }
  5801. void free()
  5802. {
  5803. if (n0_e.first && n0_e.second)
  5804. {
  5805. n0_e.first = false;
  5806. if (
  5807. !is_variable_node(n0_e.second) &&
  5808. !is_string_node (n0_e.second)
  5809. )
  5810. {
  5811. destroy_node(n0_e.second);
  5812. }
  5813. }
  5814. if (n1_e.first && n1_e.second)
  5815. {
  5816. n1_e.first = false;
  5817. if (
  5818. !is_variable_node(n1_e.second) &&
  5819. !is_string_node (n1_e.second)
  5820. )
  5821. {
  5822. destroy_node(n1_e.second);
  5823. }
  5824. }
  5825. }
  5826. bool const_range()
  5827. {
  5828. return ( n0_c.first && n1_c.first) &&
  5829. (!n0_e.first && !n1_e.first);
  5830. }
  5831. bool var_range()
  5832. {
  5833. return ( n0_e.first && n1_e.first) &&
  5834. (!n0_c.first && !n1_c.first);
  5835. }
  5836. bool operator() (std::size_t& r0, std::size_t& r1,
  5837. const std::size_t& size = std::numeric_limits<std::size_t>::max()) const
  5838. {
  5839. if (n0_c.first)
  5840. r0 = n0_c.second;
  5841. else if (n0_e.first)
  5842. {
  5843. const T r0_value = n0_e.second->value();
  5844. if (r0_value < 0)
  5845. return false;
  5846. else
  5847. r0 = static_cast<std::size_t>(details::numeric::to_int64(r0_value));
  5848. }
  5849. else
  5850. return false;
  5851. if (n1_c.first)
  5852. r1 = n1_c.second;
  5853. else if (n1_e.first)
  5854. {
  5855. const T r1_value = n1_e.second->value();
  5856. if (r1_value < 0)
  5857. return false;
  5858. else
  5859. r1 = static_cast<std::size_t>(details::numeric::to_int64(r1_value));
  5860. }
  5861. else
  5862. return false;
  5863. if (
  5864. (std::numeric_limits<std::size_t>::max() != size) &&
  5865. (std::numeric_limits<std::size_t>::max() == r1 )
  5866. )
  5867. {
  5868. r1 = size - 1;
  5869. }
  5870. cache.first = r0;
  5871. cache.second = r1;
  5872. return (r0 <= r1);
  5873. }
  5874. inline std::size_t const_size() const
  5875. {
  5876. return (n1_c.second - n0_c.second + 1);
  5877. }
  5878. inline std::size_t cache_size() const
  5879. {
  5880. return (cache.second - cache.first + 1);
  5881. }
  5882. std::pair<bool,expression_node_ptr> n0_e;
  5883. std::pair<bool,expression_node_ptr> n1_e;
  5884. std::pair<bool,std::size_t > n0_c;
  5885. std::pair<bool,std::size_t > n1_c;
  5886. mutable cached_range_t cache;
  5887. };
  5888. template <typename T>
  5889. class string_base_node;
  5890. template <typename T>
  5891. struct range_data_type
  5892. {
  5893. typedef range_pack<T> range_t;
  5894. typedef string_base_node<T>* strbase_ptr_t;
  5895. range_data_type()
  5896. : range(0),
  5897. data (0),
  5898. size (0),
  5899. type_size(0),
  5900. str_node (0)
  5901. {}
  5902. range_t* range;
  5903. void* data;
  5904. std::size_t size;
  5905. std::size_t type_size;
  5906. strbase_ptr_t str_node;
  5907. };
  5908. template <typename T> class vector_node;
  5909. template <typename T>
  5910. class vector_interface
  5911. {
  5912. public:
  5913. typedef vector_node<T>* vector_node_ptr;
  5914. typedef vec_data_store<T> vds_t;
  5915. virtual ~vector_interface()
  5916. {}
  5917. virtual std::size_t size () const = 0;
  5918. virtual vector_node_ptr vec() const = 0;
  5919. virtual vector_node_ptr vec() = 0;
  5920. virtual vds_t& vds () = 0;
  5921. virtual const vds_t& vds () const = 0;
  5922. virtual bool side_effect () const { return false; }
  5923. };
  5924. template <typename T>
  5925. class vector_node : public expression_node <T>,
  5926. public vector_interface<T>
  5927. {
  5928. public:
  5929. typedef expression_node<T>* expression_ptr;
  5930. typedef vector_holder<T> vector_holder_t;
  5931. typedef vector_node<T>* vector_node_ptr;
  5932. typedef vec_data_store<T> vds_t;
  5933. explicit vector_node(vector_holder_t* vh)
  5934. : vector_holder_(vh),
  5935. vds_((*vector_holder_).size(),(*vector_holder_)[0])
  5936. {
  5937. vector_holder_->set_ref(&vds_.ref());
  5938. }
  5939. vector_node(const vds_t& vds, vector_holder_t* vh)
  5940. : vector_holder_(vh),
  5941. vds_(vds)
  5942. {}
  5943. inline T value() const
  5944. {
  5945. return vds().data()[0];
  5946. }
  5947. vector_node_ptr vec() const
  5948. {
  5949. return const_cast<vector_node_ptr>(this);
  5950. }
  5951. vector_node_ptr vec()
  5952. {
  5953. return this;
  5954. }
  5955. inline typename expression_node<T>::node_type type() const
  5956. {
  5957. return expression_node<T>::e_vector;
  5958. }
  5959. std::size_t size() const
  5960. {
  5961. return vds().size();
  5962. }
  5963. vds_t& vds()
  5964. {
  5965. return vds_;
  5966. }
  5967. const vds_t& vds() const
  5968. {
  5969. return vds_;
  5970. }
  5971. inline vector_holder_t& vec_holder()
  5972. {
  5973. return (*vector_holder_);
  5974. }
  5975. private:
  5976. vector_holder_t* vector_holder_;
  5977. vds_t vds_;
  5978. };
  5979. template <typename T>
  5980. class vector_elem_node : public expression_node<T>,
  5981. public ivariable <T>
  5982. {
  5983. public:
  5984. typedef expression_node<T>* expression_ptr;
  5985. typedef vector_holder<T> vector_holder_t;
  5986. typedef vector_holder_t* vector_holder_ptr;
  5987. vector_elem_node(expression_ptr index, vector_holder_ptr vec_holder)
  5988. : index_(index),
  5989. vec_holder_(vec_holder),
  5990. vector_base_((*vec_holder)[0]),
  5991. index_deletable_(branch_deletable(index_))
  5992. {}
  5993. ~vector_elem_node()
  5994. {
  5995. if (index_ && index_deletable_)
  5996. {
  5997. destroy_node(index_);
  5998. }
  5999. }
  6000. inline T value() const
  6001. {
  6002. return *(vector_base_ + static_cast<std::size_t>(details::numeric::to_int64(index_->value())));
  6003. }
  6004. inline T& ref()
  6005. {
  6006. return *(vector_base_ + static_cast<std::size_t>(details::numeric::to_int64(index_->value())));
  6007. }
  6008. inline const T& ref() const
  6009. {
  6010. return *(vector_base_ + static_cast<std::size_t>(details::numeric::to_int64(index_->value())));
  6011. }
  6012. inline typename expression_node<T>::node_type type() const
  6013. {
  6014. return expression_node<T>::e_vecelem;
  6015. }
  6016. inline vector_holder_t& vec_holder()
  6017. {
  6018. return (*vec_holder_);
  6019. }
  6020. private:
  6021. expression_ptr index_;
  6022. vector_holder_ptr vec_holder_;
  6023. T* vector_base_;
  6024. const bool index_deletable_;
  6025. };
  6026. template <typename T>
  6027. class rebasevector_elem_node : public expression_node<T>,
  6028. public ivariable <T>
  6029. {
  6030. public:
  6031. typedef expression_node<T>* expression_ptr;
  6032. typedef vector_holder<T> vector_holder_t;
  6033. typedef vector_holder_t* vector_holder_ptr;
  6034. typedef vec_data_store<T> vds_t;
  6035. rebasevector_elem_node(expression_ptr index, vector_holder_ptr vec_holder)
  6036. : index_(index),
  6037. index_deletable_(branch_deletable(index_)),
  6038. vector_holder_(vec_holder),
  6039. vds_((*vector_holder_).size(),(*vector_holder_)[0])
  6040. {
  6041. vector_holder_->set_ref(&vds_.ref());
  6042. }
  6043. ~rebasevector_elem_node()
  6044. {
  6045. if (index_ && index_deletable_)
  6046. {
  6047. destroy_node(index_);
  6048. }
  6049. }
  6050. inline T value() const
  6051. {
  6052. return *(vds_.data() + static_cast<std::size_t>(details::numeric::to_int64(index_->value())));
  6053. }
  6054. inline T& ref()
  6055. {
  6056. return *(vds_.data() + static_cast<std::size_t>(details::numeric::to_int64(index_->value())));
  6057. }
  6058. inline const T& ref() const
  6059. {
  6060. return *(vds_.data() + static_cast<std::size_t>(details::numeric::to_int64(index_->value())));
  6061. }
  6062. inline typename expression_node<T>::node_type type() const
  6063. {
  6064. return expression_node<T>::e_rbvecelem;
  6065. }
  6066. inline vector_holder_t& vec_holder()
  6067. {
  6068. return (*vector_holder_);
  6069. }
  6070. private:
  6071. expression_ptr index_;
  6072. const bool index_deletable_;
  6073. vector_holder_ptr vector_holder_;
  6074. vds_t vds_;
  6075. };
  6076. template <typename T>
  6077. class rebasevector_celem_node : public expression_node<T>,
  6078. public ivariable <T>
  6079. {
  6080. public:
  6081. typedef expression_node<T>* expression_ptr;
  6082. typedef vector_holder<T> vector_holder_t;
  6083. typedef vector_holder_t* vector_holder_ptr;
  6084. typedef vec_data_store<T> vds_t;
  6085. rebasevector_celem_node(const std::size_t index, vector_holder_ptr vec_holder)
  6086. : index_(index),
  6087. vector_holder_(vec_holder),
  6088. vds_((*vector_holder_).size(),(*vector_holder_)[0])
  6089. {
  6090. vector_holder_->set_ref(&vds_.ref());
  6091. }
  6092. inline T value() const
  6093. {
  6094. return *(vds_.data() + index_);
  6095. }
  6096. inline T& ref()
  6097. {
  6098. return *(vds_.data() + index_);
  6099. }
  6100. inline const T& ref() const
  6101. {
  6102. return *(vds_.data() + index_);
  6103. }
  6104. inline typename expression_node<T>::node_type type() const
  6105. {
  6106. return expression_node<T>::e_rbveccelem;
  6107. }
  6108. inline vector_holder_t& vec_holder()
  6109. {
  6110. return (*vector_holder_);
  6111. }
  6112. private:
  6113. const std::size_t index_;
  6114. vector_holder_ptr vector_holder_;
  6115. vds_t vds_;
  6116. };
  6117. template <typename T>
  6118. class vector_assignment_node : public expression_node<T>
  6119. {
  6120. public:
  6121. typedef expression_node<T>* expression_ptr;
  6122. vector_assignment_node(T* vector_base,
  6123. const std::size_t& size,
  6124. const std::vector<expression_ptr>& initialiser_list,
  6125. const bool single_value_initialse)
  6126. : vector_base_(vector_base),
  6127. initialiser_list_(initialiser_list),
  6128. size_(size),
  6129. single_value_initialse_(single_value_initialse)
  6130. {}
  6131. ~vector_assignment_node()
  6132. {
  6133. for (std::size_t i = 0; i < initialiser_list_.size(); ++i)
  6134. {
  6135. if (branch_deletable(initialiser_list_[i]))
  6136. {
  6137. destroy_node(initialiser_list_[i]);
  6138. }
  6139. }
  6140. }
  6141. inline T value() const
  6142. {
  6143. if (single_value_initialse_)
  6144. {
  6145. for (std::size_t i = 0; i < size_; ++i)
  6146. {
  6147. *(vector_base_ + i) = initialiser_list_[0]->value();
  6148. }
  6149. }
  6150. else
  6151. {
  6152. std::size_t il_size = initialiser_list_.size();
  6153. for (std::size_t i = 0; i < il_size; ++i)
  6154. {
  6155. *(vector_base_ + i) = initialiser_list_[i]->value();
  6156. }
  6157. if (il_size < size_)
  6158. {
  6159. for (std::size_t i = il_size; i < size_; ++i)
  6160. {
  6161. *(vector_base_ + i) = T(0);
  6162. }
  6163. }
  6164. }
  6165. return *(vector_base_);
  6166. }
  6167. inline typename expression_node<T>::node_type type() const
  6168. {
  6169. return expression_node<T>::e_vecdefass;
  6170. }
  6171. private:
  6172. vector_assignment_node<T>& operator=(const vector_assignment_node<T>&);
  6173. mutable T* vector_base_;
  6174. std::vector<expression_ptr> initialiser_list_;
  6175. const std::size_t size_;
  6176. const bool single_value_initialse_;
  6177. };
  6178. template <typename T>
  6179. class swap_node : public expression_node<T>
  6180. {
  6181. public:
  6182. typedef expression_node<T>* expression_ptr;
  6183. typedef variable_node<T>* variable_node_ptr;
  6184. swap_node(variable_node_ptr var0, variable_node_ptr var1)
  6185. : var0_(var0),
  6186. var1_(var1)
  6187. {}
  6188. inline T value() const
  6189. {
  6190. std::swap(var0_->ref(),var1_->ref());
  6191. return var1_->ref();
  6192. }
  6193. inline typename expression_node<T>::node_type type() const
  6194. {
  6195. return expression_node<T>::e_swap;
  6196. }
  6197. private:
  6198. variable_node_ptr var0_;
  6199. variable_node_ptr var1_;
  6200. };
  6201. template <typename T>
  6202. class swap_generic_node : public binary_node<T>
  6203. {
  6204. public:
  6205. typedef expression_node<T>* expression_ptr;
  6206. typedef ivariable<T>* ivariable_ptr;
  6207. swap_generic_node(expression_ptr var0, expression_ptr var1)
  6208. : binary_node<T>(details::e_swap, var0, var1),
  6209. var0_(dynamic_cast<ivariable_ptr>(var0)),
  6210. var1_(dynamic_cast<ivariable_ptr>(var1))
  6211. {}
  6212. inline T value() const
  6213. {
  6214. std::swap(var0_->ref(),var1_->ref());
  6215. return var1_->ref();
  6216. }
  6217. inline typename expression_node<T>::node_type type() const
  6218. {
  6219. return expression_node<T>::e_swap;
  6220. }
  6221. private:
  6222. ivariable_ptr var0_;
  6223. ivariable_ptr var1_;
  6224. };
  6225. template <typename T>
  6226. class swap_vecvec_node : public binary_node <T>,
  6227. public vector_interface<T>
  6228. {
  6229. public:
  6230. typedef expression_node<T>* expression_ptr;
  6231. typedef vector_node<T>* vector_node_ptr;
  6232. typedef vec_data_store<T> vds_t;
  6233. swap_vecvec_node(expression_ptr branch0,
  6234. expression_ptr branch1)
  6235. : binary_node<T>(details::e_swap, branch0, branch1),
  6236. vec0_node_ptr_(0),
  6237. vec1_node_ptr_(0),
  6238. vec_size_ (0),
  6239. initialised_ (false)
  6240. {
  6241. if (is_ivector_node(binary_node<T>::branch_[0].first))
  6242. {
  6243. vector_interface<T>* vi = reinterpret_cast<vector_interface<T>*>(0);
  6244. if (0 != (vi = dynamic_cast<vector_interface<T>*>(binary_node<T>::branch_[0].first)))
  6245. {
  6246. vec0_node_ptr_ = vi->vec();
  6247. vds() = vi->vds();
  6248. }
  6249. }
  6250. if (is_ivector_node(binary_node<T>::branch_[1].first))
  6251. {
  6252. vector_interface<T>* vi = reinterpret_cast<vector_interface<T>*>(0);
  6253. if (0 != (vi = dynamic_cast<vector_interface<T>*>(binary_node<T>::branch_[1].first)))
  6254. {
  6255. vec1_node_ptr_ = vi->vec();
  6256. }
  6257. }
  6258. if (vec0_node_ptr_ && vec1_node_ptr_)
  6259. {
  6260. vec_size_ = std::min(vec0_node_ptr_->vds().size(),
  6261. vec1_node_ptr_->vds().size());
  6262. initialised_ = true;
  6263. }
  6264. }
  6265. inline T value() const
  6266. {
  6267. if (initialised_)
  6268. {
  6269. binary_node<T>::branch_[0].first->value();
  6270. binary_node<T>::branch_[1].first->value();
  6271. T* vec0 = vec0_node_ptr_->vds().data();
  6272. T* vec1 = vec1_node_ptr_->vds().data();
  6273. for (std::size_t i = 0; i < vec_size_; ++i)
  6274. {
  6275. std::swap(vec0[i],vec1[i]);
  6276. }
  6277. return vec1_node_ptr_->value();
  6278. }
  6279. else
  6280. return std::numeric_limits<T>::quiet_NaN();
  6281. }
  6282. vector_node_ptr vec() const
  6283. {
  6284. return vec0_node_ptr_;
  6285. }
  6286. vector_node_ptr vec()
  6287. {
  6288. return vec0_node_ptr_;
  6289. }
  6290. inline typename expression_node<T>::node_type type() const
  6291. {
  6292. return expression_node<T>::e_vecvecswap;
  6293. }
  6294. std::size_t size() const
  6295. {
  6296. return vec_size_;
  6297. }
  6298. vds_t& vds()
  6299. {
  6300. return vds_;
  6301. }
  6302. const vds_t& vds() const
  6303. {
  6304. return vds_;
  6305. }
  6306. private:
  6307. vector_node<T>* vec0_node_ptr_;
  6308. vector_node<T>* vec1_node_ptr_;
  6309. std::size_t vec_size_;
  6310. bool initialised_;
  6311. vds_t vds_;
  6312. };
  6313. #ifndef exprtk_disable_string_capabilities
  6314. template <typename T>
  6315. class stringvar_node : public expression_node <T>,
  6316. public string_base_node<T>,
  6317. public range_interface <T>
  6318. {
  6319. public:
  6320. typedef range_pack<T> range_t;
  6321. static std::string null_value;
  6322. explicit stringvar_node()
  6323. : value_(&null_value)
  6324. {}
  6325. explicit stringvar_node(std::string& v)
  6326. : value_(&v)
  6327. {
  6328. rp_.n0_c = std::make_pair<bool,std::size_t>(true,0);
  6329. rp_.n1_c = std::make_pair<bool,std::size_t>(true,v.size() - 1);
  6330. rp_.cache.first = rp_.n0_c.second;
  6331. rp_.cache.second = rp_.n1_c.second;
  6332. }
  6333. inline bool operator <(const stringvar_node<T>& v) const
  6334. {
  6335. return this < (&v);
  6336. }
  6337. inline T value() const
  6338. {
  6339. rp_.n1_c.second = (*value_).size() - 1;
  6340. rp_.cache.second = rp_.n1_c.second;
  6341. return std::numeric_limits<T>::quiet_NaN();
  6342. }
  6343. std::string str() const
  6344. {
  6345. return ref();
  6346. }
  6347. char_cptr base() const
  6348. {
  6349. return &(*value_)[0];
  6350. }
  6351. std::size_t size() const
  6352. {
  6353. return ref().size();
  6354. }
  6355. std::string& ref()
  6356. {
  6357. return (*value_);
  6358. }
  6359. const std::string& ref() const
  6360. {
  6361. return (*value_);
  6362. }
  6363. range_t& range_ref()
  6364. {
  6365. return rp_;
  6366. }
  6367. const range_t& range_ref() const
  6368. {
  6369. return rp_;
  6370. }
  6371. inline typename expression_node<T>::node_type type() const
  6372. {
  6373. return expression_node<T>::e_stringvar;
  6374. }
  6375. private:
  6376. std::string* value_;
  6377. mutable range_t rp_;
  6378. };
  6379. template <typename T>
  6380. std::string stringvar_node<T>::null_value = std::string("");
  6381. template <typename T>
  6382. class string_range_node : public expression_node <T>,
  6383. public string_base_node<T>,
  6384. public range_interface <T>
  6385. {
  6386. public:
  6387. typedef range_pack<T> range_t;
  6388. static std::string null_value;
  6389. explicit string_range_node(std::string& v, const range_t& rp)
  6390. : value_(&v),
  6391. rp_(rp)
  6392. {}
  6393. virtual ~string_range_node()
  6394. {
  6395. rp_.free();
  6396. }
  6397. inline bool operator <(const string_range_node<T>& v) const
  6398. {
  6399. return this < (&v);
  6400. }
  6401. inline T value() const
  6402. {
  6403. return std::numeric_limits<T>::quiet_NaN();
  6404. }
  6405. inline std::string str() const
  6406. {
  6407. return (*value_);
  6408. }
  6409. char_cptr base() const
  6410. {
  6411. return &(*value_)[0];
  6412. }
  6413. std::size_t size() const
  6414. {
  6415. return ref().size();
  6416. }
  6417. inline range_t range() const
  6418. {
  6419. return rp_;
  6420. }
  6421. inline virtual std::string& ref()
  6422. {
  6423. return (*value_);
  6424. }
  6425. inline virtual const std::string& ref() const
  6426. {
  6427. return (*value_);
  6428. }
  6429. inline range_t& range_ref()
  6430. {
  6431. return rp_;
  6432. }
  6433. inline const range_t& range_ref() const
  6434. {
  6435. return rp_;
  6436. }
  6437. inline typename expression_node<T>::node_type type() const
  6438. {
  6439. return expression_node<T>::e_stringvarrng;
  6440. }
  6441. private:
  6442. std::string* value_;
  6443. range_t rp_;
  6444. };
  6445. template <typename T>
  6446. std::string string_range_node<T>::null_value = std::string("");
  6447. template <typename T>
  6448. class const_string_range_node : public expression_node <T>,
  6449. public string_base_node<T>,
  6450. public range_interface <T>
  6451. {
  6452. public:
  6453. typedef range_pack<T> range_t;
  6454. explicit const_string_range_node(const std::string& v, const range_t& rp)
  6455. : value_(v),
  6456. rp_(rp)
  6457. {}
  6458. ~const_string_range_node()
  6459. {
  6460. rp_.free();
  6461. }
  6462. inline T value() const
  6463. {
  6464. return std::numeric_limits<T>::quiet_NaN();
  6465. }
  6466. std::string str() const
  6467. {
  6468. return value_;
  6469. }
  6470. char_cptr base() const
  6471. {
  6472. return value_.data();
  6473. }
  6474. std::size_t size() const
  6475. {
  6476. return value_.size();
  6477. }
  6478. range_t range() const
  6479. {
  6480. return rp_;
  6481. }
  6482. range_t& range_ref()
  6483. {
  6484. return rp_;
  6485. }
  6486. const range_t& range_ref() const
  6487. {
  6488. return rp_;
  6489. }
  6490. inline typename expression_node<T>::node_type type() const
  6491. {
  6492. return expression_node<T>::e_cstringvarrng;
  6493. }
  6494. private:
  6495. const_string_range_node<T>& operator=(const const_string_range_node<T>&);
  6496. const std::string value_;
  6497. range_t rp_;
  6498. };
  6499. template <typename T>
  6500. class generic_string_range_node : public expression_node <T>,
  6501. public string_base_node<T>,
  6502. public range_interface <T>
  6503. {
  6504. public:
  6505. typedef expression_node <T>* expression_ptr;
  6506. typedef stringvar_node <T>* strvar_node_ptr;
  6507. typedef string_base_node<T>* str_base_ptr;
  6508. typedef range_pack <T> range_t;
  6509. typedef range_t* range_ptr;
  6510. typedef range_interface<T> irange_t;
  6511. typedef irange_t* irange_ptr;
  6512. generic_string_range_node(expression_ptr str_branch, const range_t& brange)
  6513. : initialised_(false),
  6514. branch_(str_branch),
  6515. branch_deletable_(branch_deletable(branch_)),
  6516. str_base_ptr_ (0),
  6517. str_range_ptr_(0),
  6518. base_range_(brange)
  6519. {
  6520. range_.n0_c = std::make_pair<bool,std::size_t>(true,0);
  6521. range_.n1_c = std::make_pair<bool,std::size_t>(true,0);
  6522. range_.cache.first = range_.n0_c.second;
  6523. range_.cache.second = range_.n1_c.second;
  6524. if (is_generally_string_node(branch_))
  6525. {
  6526. str_base_ptr_ = dynamic_cast<str_base_ptr>(branch_);
  6527. if (0 == str_base_ptr_)
  6528. return;
  6529. str_range_ptr_ = dynamic_cast<irange_ptr>(branch_);
  6530. if (0 == str_range_ptr_)
  6531. return;
  6532. }
  6533. initialised_ = (str_base_ptr_ && str_range_ptr_);
  6534. }
  6535. ~generic_string_range_node()
  6536. {
  6537. base_range_.free();
  6538. if (branch_ && branch_deletable_)
  6539. {
  6540. destroy_node(branch_);
  6541. }
  6542. }
  6543. inline T value() const
  6544. {
  6545. if (initialised_)
  6546. {
  6547. branch_->value();
  6548. std::size_t str_r0 = 0;
  6549. std::size_t str_r1 = 0;
  6550. std::size_t r0 = 0;
  6551. std::size_t r1 = 0;
  6552. range_t& range = str_range_ptr_->range_ref();
  6553. const std::size_t base_str_size = str_base_ptr_->size();
  6554. if (
  6555. range (str_r0, str_r1, base_str_size) &&
  6556. base_range_( r0, r1, base_str_size)
  6557. )
  6558. {
  6559. const std::size_t size = (r1 - r0) + 1;
  6560. range_.n1_c.second = size - 1;
  6561. range_.cache.second = range_.n1_c.second;
  6562. value_.assign(str_base_ptr_->base() + str_r0 + r0, size);
  6563. }
  6564. }
  6565. return std::numeric_limits<T>::quiet_NaN();
  6566. }
  6567. std::string str() const
  6568. {
  6569. return value_;
  6570. }
  6571. char_cptr base() const
  6572. {
  6573. return &value_[0];
  6574. }
  6575. std::size_t size() const
  6576. {
  6577. return value_.size();
  6578. }
  6579. range_t& range_ref()
  6580. {
  6581. return range_;
  6582. }
  6583. const range_t& range_ref() const
  6584. {
  6585. return range_;
  6586. }
  6587. inline typename expression_node<T>::node_type type() const
  6588. {
  6589. return expression_node<T>::e_strgenrange;
  6590. }
  6591. private:
  6592. bool initialised_;
  6593. expression_ptr branch_;
  6594. const bool branch_deletable_;
  6595. str_base_ptr str_base_ptr_;
  6596. irange_ptr str_range_ptr_;
  6597. mutable range_t base_range_;
  6598. mutable range_t range_;
  6599. mutable std::string value_;
  6600. };
  6601. template <typename T>
  6602. class string_concat_node : public binary_node <T>,
  6603. public string_base_node<T>,
  6604. public range_interface <T>
  6605. {
  6606. public:
  6607. typedef expression_node <T>* expression_ptr;
  6608. typedef string_base_node<T>* str_base_ptr;
  6609. typedef range_pack <T> range_t;
  6610. typedef range_t* range_ptr;
  6611. typedef range_interface<T> irange_t;
  6612. typedef irange_t* irange_ptr;
  6613. string_concat_node(const operator_type& opr,
  6614. expression_ptr branch0,
  6615. expression_ptr branch1)
  6616. : binary_node<T>(opr, branch0, branch1),
  6617. initialised_(false),
  6618. str0_base_ptr_ (0),
  6619. str1_base_ptr_ (0),
  6620. str0_range_ptr_(0),
  6621. str1_range_ptr_(0)
  6622. {
  6623. range_.n0_c = std::make_pair<bool,std::size_t>(true,0);
  6624. range_.n1_c = std::make_pair<bool,std::size_t>(true,0);
  6625. range_.cache.first = range_.n0_c.second;
  6626. range_.cache.second = range_.n1_c.second;
  6627. if (is_generally_string_node(binary_node<T>::branch_[0].first))
  6628. {
  6629. str0_base_ptr_ = dynamic_cast<str_base_ptr>(binary_node<T>::branch_[0].first);
  6630. if (0 == str0_base_ptr_)
  6631. return;
  6632. str0_range_ptr_ = dynamic_cast<irange_ptr>(binary_node<T>::branch_[0].first);
  6633. if (0 == str0_range_ptr_)
  6634. return;
  6635. }
  6636. if (is_generally_string_node(binary_node<T>::branch_[1].first))
  6637. {
  6638. str1_base_ptr_ = dynamic_cast<str_base_ptr>(binary_node<T>::branch_[1].first);
  6639. if (0 == str1_base_ptr_)
  6640. return;
  6641. str1_range_ptr_ = dynamic_cast<irange_ptr>(binary_node<T>::branch_[1].first);
  6642. if (0 == str1_range_ptr_)
  6643. return;
  6644. }
  6645. initialised_ = str0_base_ptr_ &&
  6646. str1_base_ptr_ &&
  6647. str0_range_ptr_ &&
  6648. str1_range_ptr_ ;
  6649. }
  6650. inline T value() const
  6651. {
  6652. if (initialised_)
  6653. {
  6654. binary_node<T>::branch_[0].first->value();
  6655. binary_node<T>::branch_[1].first->value();
  6656. std::size_t str0_r0 = 0;
  6657. std::size_t str0_r1 = 0;
  6658. std::size_t str1_r0 = 0;
  6659. std::size_t str1_r1 = 0;
  6660. range_t& range0 = str0_range_ptr_->range_ref();
  6661. range_t& range1 = str1_range_ptr_->range_ref();
  6662. if (
  6663. range0(str0_r0, str0_r1, str0_base_ptr_->size()) &&
  6664. range1(str1_r0, str1_r1, str1_base_ptr_->size())
  6665. )
  6666. {
  6667. const std::size_t size0 = (str0_r1 - str0_r0) + 1;
  6668. const std::size_t size1 = (str1_r1 - str1_r0) + 1;
  6669. value_.assign(str0_base_ptr_->base() + str0_r0, size0);
  6670. value_.append(str1_base_ptr_->base() + str1_r0, size1);
  6671. range_.n1_c.second = value_.size() - 1;
  6672. range_.cache.second = range_.n1_c.second;
  6673. }
  6674. }
  6675. return std::numeric_limits<T>::quiet_NaN();
  6676. }
  6677. std::string str() const
  6678. {
  6679. return value_;
  6680. }
  6681. char_cptr base() const
  6682. {
  6683. return &value_[0];
  6684. }
  6685. std::size_t size() const
  6686. {
  6687. return value_.size();
  6688. }
  6689. range_t& range_ref()
  6690. {
  6691. return range_;
  6692. }
  6693. const range_t& range_ref() const
  6694. {
  6695. return range_;
  6696. }
  6697. inline typename expression_node<T>::node_type type() const
  6698. {
  6699. return expression_node<T>::e_strconcat;
  6700. }
  6701. private:
  6702. bool initialised_;
  6703. str_base_ptr str0_base_ptr_;
  6704. str_base_ptr str1_base_ptr_;
  6705. irange_ptr str0_range_ptr_;
  6706. irange_ptr str1_range_ptr_;
  6707. mutable range_t range_;
  6708. mutable std::string value_;
  6709. };
  6710. template <typename T>
  6711. class swap_string_node : public binary_node <T>,
  6712. public string_base_node<T>,
  6713. public range_interface <T>
  6714. {
  6715. public:
  6716. typedef expression_node <T>* expression_ptr;
  6717. typedef stringvar_node <T>* strvar_node_ptr;
  6718. typedef string_base_node<T>* str_base_ptr;
  6719. typedef range_pack <T> range_t;
  6720. typedef range_t* range_ptr;
  6721. typedef range_interface<T> irange_t;
  6722. typedef irange_t* irange_ptr;
  6723. swap_string_node(expression_ptr branch0, expression_ptr branch1)
  6724. : binary_node<T>(details::e_swap, branch0, branch1),
  6725. initialised_(false),
  6726. str0_node_ptr_(0),
  6727. str1_node_ptr_(0)
  6728. {
  6729. if (is_string_node(binary_node<T>::branch_[0].first))
  6730. {
  6731. str0_node_ptr_ = static_cast<strvar_node_ptr>(binary_node<T>::branch_[0].first);
  6732. }
  6733. if (is_string_node(binary_node<T>::branch_[1].first))
  6734. {
  6735. str1_node_ptr_ = static_cast<strvar_node_ptr>(binary_node<T>::branch_[1].first);
  6736. }
  6737. initialised_ = (str0_node_ptr_ && str1_node_ptr_);
  6738. }
  6739. inline T value() const
  6740. {
  6741. if (initialised_)
  6742. {
  6743. binary_node<T>::branch_[0].first->value();
  6744. binary_node<T>::branch_[1].first->value();
  6745. std::swap(str0_node_ptr_->ref(), str1_node_ptr_->ref());
  6746. }
  6747. return std::numeric_limits<T>::quiet_NaN();
  6748. }
  6749. std::string str() const
  6750. {
  6751. return str0_node_ptr_->str();
  6752. }
  6753. char_cptr base() const
  6754. {
  6755. return str0_node_ptr_->base();
  6756. }
  6757. std::size_t size() const
  6758. {
  6759. return str0_node_ptr_->size();
  6760. }
  6761. range_t& range_ref()
  6762. {
  6763. return str0_node_ptr_->range_ref();
  6764. }
  6765. const range_t& range_ref() const
  6766. {
  6767. return str0_node_ptr_->range_ref();
  6768. }
  6769. inline typename expression_node<T>::node_type type() const
  6770. {
  6771. return expression_node<T>::e_strswap;
  6772. }
  6773. private:
  6774. bool initialised_;
  6775. strvar_node_ptr str0_node_ptr_;
  6776. strvar_node_ptr str1_node_ptr_;
  6777. };
  6778. template <typename T>
  6779. class swap_genstrings_node : public binary_node<T>
  6780. {
  6781. public:
  6782. typedef expression_node <T>* expression_ptr;
  6783. typedef string_base_node<T>* str_base_ptr;
  6784. typedef range_pack <T> range_t;
  6785. typedef range_t* range_ptr;
  6786. typedef range_interface<T> irange_t;
  6787. typedef irange_t* irange_ptr;
  6788. swap_genstrings_node(expression_ptr branch0,
  6789. expression_ptr branch1)
  6790. : binary_node<T>(details::e_default, branch0, branch1),
  6791. str0_base_ptr_ (0),
  6792. str1_base_ptr_ (0),
  6793. str0_range_ptr_(0),
  6794. str1_range_ptr_(0),
  6795. initialised_(false)
  6796. {
  6797. if (is_generally_string_node(binary_node<T>::branch_[0].first))
  6798. {
  6799. str0_base_ptr_ = dynamic_cast<str_base_ptr>(binary_node<T>::branch_[0].first);
  6800. if (0 == str0_base_ptr_)
  6801. return;
  6802. irange_ptr range = dynamic_cast<irange_ptr>(binary_node<T>::branch_[0].first);
  6803. if (0 == range)
  6804. return;
  6805. str0_range_ptr_ = &(range->range_ref());
  6806. }
  6807. if (is_generally_string_node(binary_node<T>::branch_[1].first))
  6808. {
  6809. str1_base_ptr_ = dynamic_cast<str_base_ptr>(binary_node<T>::branch_[1].first);
  6810. if (0 == str1_base_ptr_)
  6811. return;
  6812. irange_ptr range = dynamic_cast<irange_ptr>(binary_node<T>::branch_[1].first);
  6813. if (0 == range)
  6814. return;
  6815. str1_range_ptr_ = &(range->range_ref());
  6816. }
  6817. initialised_ = str0_base_ptr_ &&
  6818. str1_base_ptr_ &&
  6819. str0_range_ptr_ &&
  6820. str1_range_ptr_ ;
  6821. }
  6822. inline T value() const
  6823. {
  6824. if (initialised_)
  6825. {
  6826. binary_node<T>::branch_[0].first->value();
  6827. binary_node<T>::branch_[1].first->value();
  6828. std::size_t str0_r0 = 0;
  6829. std::size_t str0_r1 = 0;
  6830. std::size_t str1_r0 = 0;
  6831. std::size_t str1_r1 = 0;
  6832. range_t& range0 = (*str0_range_ptr_);
  6833. range_t& range1 = (*str1_range_ptr_);
  6834. if (
  6835. range0(str0_r0, str0_r1, str0_base_ptr_->size()) &&
  6836. range1(str1_r0, str1_r1, str1_base_ptr_->size())
  6837. )
  6838. {
  6839. const std::size_t size0 = range0.cache_size();
  6840. const std::size_t size1 = range1.cache_size();
  6841. const std::size_t max_size = std::min(size0,size1);
  6842. char_ptr s0 = const_cast<char_ptr>(str0_base_ptr_->base() + str0_r0);
  6843. char_ptr s1 = const_cast<char_ptr>(str1_base_ptr_->base() + str1_r0);
  6844. loop_unroll::details lud(max_size);
  6845. char_cptr upper_bound = s0 + lud.upper_bound;
  6846. while (s0 < upper_bound)
  6847. {
  6848. #define exprtk_loop(N) \
  6849. std::swap(s0[N], s1[N]); \
  6850. exprtk_loop( 0) exprtk_loop( 1)
  6851. exprtk_loop( 2) exprtk_loop( 3)
  6852. #ifndef exprtk_disable_superscalar_unroll
  6853. exprtk_loop( 4) exprtk_loop( 5)
  6854. exprtk_loop( 6) exprtk_loop( 7)
  6855. exprtk_loop( 8) exprtk_loop( 9)
  6856. exprtk_loop(10) exprtk_loop(11)
  6857. exprtk_loop(12) exprtk_loop(13)
  6858. exprtk_loop(14) exprtk_loop(15)
  6859. #endif
  6860. s0 += lud.batch_size;
  6861. s1 += lud.batch_size;
  6862. }
  6863. int i = 0;
  6864. exprtk_disable_fallthrough_begin
  6865. switch (lud.remainder)
  6866. {
  6867. #define case_stmt(N) \
  6868. case N : { std::swap(s0[i], s1[i]); ++i; } \
  6869. #ifndef exprtk_disable_superscalar_unroll
  6870. case_stmt(15) case_stmt(14)
  6871. case_stmt(13) case_stmt(12)
  6872. case_stmt(11) case_stmt(10)
  6873. case_stmt( 9) case_stmt( 8)
  6874. case_stmt( 7) case_stmt( 6)
  6875. case_stmt( 5) case_stmt( 4)
  6876. #endif
  6877. case_stmt( 3) case_stmt( 2)
  6878. case_stmt( 1)
  6879. }
  6880. exprtk_disable_fallthrough_end
  6881. #undef exprtk_loop
  6882. #undef case_stmt
  6883. }
  6884. }
  6885. return std::numeric_limits<T>::quiet_NaN();
  6886. }
  6887. inline typename expression_node<T>::node_type type() const
  6888. {
  6889. return expression_node<T>::e_strswap;
  6890. }
  6891. private:
  6892. swap_genstrings_node(swap_genstrings_node<T>&);
  6893. swap_genstrings_node<T>& operator=(swap_genstrings_node<T>&);
  6894. str_base_ptr str0_base_ptr_;
  6895. str_base_ptr str1_base_ptr_;
  6896. range_ptr str0_range_ptr_;
  6897. range_ptr str1_range_ptr_;
  6898. bool initialised_;
  6899. };
  6900. template <typename T>
  6901. class stringvar_size_node : public expression_node<T>
  6902. {
  6903. public:
  6904. static std::string null_value;
  6905. explicit stringvar_size_node()
  6906. : value_(&null_value)
  6907. {}
  6908. explicit stringvar_size_node(std::string& v)
  6909. : value_(&v)
  6910. {}
  6911. inline T value() const
  6912. {
  6913. return T((*value_).size());
  6914. }
  6915. inline typename expression_node<T>::node_type type() const
  6916. {
  6917. return expression_node<T>::e_stringvarsize;
  6918. }
  6919. private:
  6920. std::string* value_;
  6921. };
  6922. template <typename T>
  6923. std::string stringvar_size_node<T>::null_value = std::string("");
  6924. template <typename T>
  6925. class string_size_node : public expression_node<T>
  6926. {
  6927. public:
  6928. typedef expression_node <T>* expression_ptr;
  6929. typedef string_base_node<T>* str_base_ptr;
  6930. explicit string_size_node(expression_ptr brnch)
  6931. : branch_(brnch),
  6932. branch_deletable_(branch_deletable(branch_)),
  6933. str_base_ptr_(0)
  6934. {
  6935. if (is_generally_string_node(branch_))
  6936. {
  6937. str_base_ptr_ = dynamic_cast<str_base_ptr>(branch_);
  6938. if (0 == str_base_ptr_)
  6939. return;
  6940. }
  6941. }
  6942. ~string_size_node()
  6943. {
  6944. if (branch_ && branch_deletable_)
  6945. {
  6946. destroy_node(branch_);
  6947. }
  6948. }
  6949. inline T value() const
  6950. {
  6951. T result = std::numeric_limits<T>::quiet_NaN();
  6952. if (str_base_ptr_)
  6953. {
  6954. branch_->value();
  6955. result = T(str_base_ptr_->size());
  6956. }
  6957. return result;
  6958. }
  6959. inline typename expression_node<T>::node_type type() const
  6960. {
  6961. return expression_node<T>::e_stringsize;
  6962. }
  6963. private:
  6964. expression_ptr branch_;
  6965. const bool branch_deletable_;
  6966. str_base_ptr str_base_ptr_;
  6967. };
  6968. struct asn_assignment
  6969. {
  6970. static inline void execute(std::string& s, char_cptr data, const std::size_t size)
  6971. { s.assign(data,size); }
  6972. };
  6973. struct asn_addassignment
  6974. {
  6975. static inline void execute(std::string& s, char_cptr data, const std::size_t size)
  6976. { s.append(data,size); }
  6977. };
  6978. template <typename T, typename AssignmentProcess = asn_assignment>
  6979. class assignment_string_node : public binary_node <T>,
  6980. public string_base_node<T>,
  6981. public range_interface <T>
  6982. {
  6983. public:
  6984. typedef expression_node <T>* expression_ptr;
  6985. typedef stringvar_node <T>* strvar_node_ptr;
  6986. typedef string_base_node<T>* str_base_ptr;
  6987. typedef range_pack <T> range_t;
  6988. typedef range_t* range_ptr;
  6989. typedef range_interface<T> irange_t;
  6990. typedef irange_t* irange_ptr;
  6991. assignment_string_node(const operator_type& opr,
  6992. expression_ptr branch0,
  6993. expression_ptr branch1)
  6994. : binary_node<T>(opr, branch0, branch1),
  6995. initialised_(false),
  6996. str0_base_ptr_ (0),
  6997. str1_base_ptr_ (0),
  6998. str0_node_ptr_ (0),
  6999. str1_range_ptr_(0)
  7000. {
  7001. if (is_string_node(binary_node<T>::branch_[0].first))
  7002. {
  7003. str0_node_ptr_ = static_cast<strvar_node_ptr>(binary_node<T>::branch_[0].first);
  7004. str0_base_ptr_ = dynamic_cast<str_base_ptr>(binary_node<T>::branch_[0].first);
  7005. }
  7006. if (is_generally_string_node(binary_node<T>::branch_[1].first))
  7007. {
  7008. str1_base_ptr_ = dynamic_cast<str_base_ptr>(binary_node<T>::branch_[1].first);
  7009. if (0 == str1_base_ptr_)
  7010. return;
  7011. irange_ptr range = dynamic_cast<irange_ptr>(binary_node<T>::branch_[1].first);
  7012. if (0 == range)
  7013. return;
  7014. str1_range_ptr_ = &(range->range_ref());
  7015. }
  7016. initialised_ = str0_base_ptr_ &&
  7017. str1_base_ptr_ &&
  7018. str0_node_ptr_ &&
  7019. str1_range_ptr_ ;
  7020. }
  7021. inline T value() const
  7022. {
  7023. if (initialised_)
  7024. {
  7025. binary_node<T>::branch_[1].first->value();
  7026. std::size_t r0 = 0;
  7027. std::size_t r1 = 0;
  7028. range_t& range = (*str1_range_ptr_);
  7029. if (range(r0, r1, str1_base_ptr_->size()))
  7030. {
  7031. AssignmentProcess::execute(str0_node_ptr_->ref(),
  7032. str1_base_ptr_->base() + r0,
  7033. (r1 - r0) + 1);
  7034. binary_node<T>::branch_[0].first->value();
  7035. }
  7036. }
  7037. return std::numeric_limits<T>::quiet_NaN();
  7038. }
  7039. std::string str() const
  7040. {
  7041. return str0_node_ptr_->str();
  7042. }
  7043. char_cptr base() const
  7044. {
  7045. return str0_node_ptr_->base();
  7046. }
  7047. std::size_t size() const
  7048. {
  7049. return str0_node_ptr_->size();
  7050. }
  7051. range_t& range_ref()
  7052. {
  7053. return str0_node_ptr_->range_ref();
  7054. }
  7055. const range_t& range_ref() const
  7056. {
  7057. return str0_node_ptr_->range_ref();
  7058. }
  7059. inline typename expression_node<T>::node_type type() const
  7060. {
  7061. return expression_node<T>::e_strass;
  7062. }
  7063. private:
  7064. bool initialised_;
  7065. str_base_ptr str0_base_ptr_;
  7066. str_base_ptr str1_base_ptr_;
  7067. strvar_node_ptr str0_node_ptr_;
  7068. range_ptr str1_range_ptr_;
  7069. };
  7070. template <typename T, typename AssignmentProcess = asn_assignment>
  7071. class assignment_string_range_node : public binary_node <T>,
  7072. public string_base_node<T>,
  7073. public range_interface <T>
  7074. {
  7075. public:
  7076. typedef expression_node <T>* expression_ptr;
  7077. typedef stringvar_node <T>* strvar_node_ptr;
  7078. typedef string_base_node<T>* str_base_ptr;
  7079. typedef range_pack <T> range_t;
  7080. typedef range_t* range_ptr;
  7081. typedef range_interface<T> irange_t;
  7082. typedef irange_t* irange_ptr;
  7083. assignment_string_range_node(const operator_type& opr,
  7084. expression_ptr branch0,
  7085. expression_ptr branch1)
  7086. : binary_node<T>(opr, branch0, branch1),
  7087. initialised_(false),
  7088. str0_base_ptr_ (0),
  7089. str1_base_ptr_ (0),
  7090. str0_node_ptr_ (0),
  7091. str0_range_ptr_(0),
  7092. str1_range_ptr_(0)
  7093. {
  7094. if (is_string_range_node(binary_node<T>::branch_[0].first))
  7095. {
  7096. str0_node_ptr_ = static_cast<strvar_node_ptr>(binary_node<T>::branch_[0].first);
  7097. str0_base_ptr_ = dynamic_cast<str_base_ptr>(binary_node<T>::branch_[0].first);
  7098. irange_ptr range = dynamic_cast<irange_ptr>(binary_node<T>::branch_[0].first);
  7099. if (0 == range)
  7100. return;
  7101. str0_range_ptr_ = &(range->range_ref());
  7102. }
  7103. if (is_generally_string_node(binary_node<T>::branch_[1].first))
  7104. {
  7105. str1_base_ptr_ = dynamic_cast<str_base_ptr>(binary_node<T>::branch_[1].first);
  7106. if (0 == str1_base_ptr_)
  7107. return;
  7108. irange_ptr range = dynamic_cast<irange_ptr>(binary_node<T>::branch_[1].first);
  7109. if (0 == range)
  7110. return;
  7111. str1_range_ptr_ = &(range->range_ref());
  7112. }
  7113. initialised_ = str0_base_ptr_ &&
  7114. str1_base_ptr_ &&
  7115. str0_node_ptr_ &&
  7116. str0_range_ptr_ &&
  7117. str1_range_ptr_ ;
  7118. }
  7119. inline T value() const
  7120. {
  7121. if (initialised_)
  7122. {
  7123. binary_node<T>::branch_[0].first->value();
  7124. binary_node<T>::branch_[1].first->value();
  7125. std::size_t s0_r0 = 0;
  7126. std::size_t s0_r1 = 0;
  7127. std::size_t s1_r0 = 0;
  7128. std::size_t s1_r1 = 0;
  7129. range_t& range0 = (*str0_range_ptr_);
  7130. range_t& range1 = (*str1_range_ptr_);
  7131. if (
  7132. range0(s0_r0, s0_r1, str0_base_ptr_->size()) &&
  7133. range1(s1_r0, s1_r1, str1_base_ptr_->size())
  7134. )
  7135. {
  7136. std::size_t size = std::min((s0_r1 - s0_r0), (s1_r1 - s1_r0)) + 1;
  7137. std::copy(str1_base_ptr_->base() + s1_r0,
  7138. str1_base_ptr_->base() + s1_r0 + size,
  7139. const_cast<char_ptr>(base() + s0_r0));
  7140. }
  7141. }
  7142. return std::numeric_limits<T>::quiet_NaN();
  7143. }
  7144. std::string str() const
  7145. {
  7146. return str0_node_ptr_->str();
  7147. }
  7148. char_cptr base() const
  7149. {
  7150. return str0_node_ptr_->base();
  7151. }
  7152. std::size_t size() const
  7153. {
  7154. return str0_node_ptr_->size();
  7155. }
  7156. range_t& range_ref()
  7157. {
  7158. return str0_node_ptr_->range_ref();
  7159. }
  7160. const range_t& range_ref() const
  7161. {
  7162. return str0_node_ptr_->range_ref();
  7163. }
  7164. inline typename expression_node<T>::node_type type() const
  7165. {
  7166. return expression_node<T>::e_strass;
  7167. }
  7168. private:
  7169. bool initialised_;
  7170. str_base_ptr str0_base_ptr_;
  7171. str_base_ptr str1_base_ptr_;
  7172. strvar_node_ptr str0_node_ptr_;
  7173. range_ptr str0_range_ptr_;
  7174. range_ptr str1_range_ptr_;
  7175. };
  7176. template <typename T>
  7177. class conditional_string_node : public trinary_node <T>,
  7178. public string_base_node<T>,
  7179. public range_interface <T>
  7180. {
  7181. public:
  7182. typedef expression_node <T>* expression_ptr;
  7183. typedef string_base_node<T>* str_base_ptr;
  7184. typedef range_pack <T> range_t;
  7185. typedef range_t* range_ptr;
  7186. typedef range_interface<T> irange_t;
  7187. typedef irange_t* irange_ptr;
  7188. conditional_string_node(expression_ptr test,
  7189. expression_ptr consequent,
  7190. expression_ptr alternative)
  7191. : trinary_node<T>(details::e_default,consequent,alternative,test),
  7192. initialised_(false),
  7193. str0_base_ptr_ (0),
  7194. str1_base_ptr_ (0),
  7195. str0_range_ptr_(0),
  7196. str1_range_ptr_(0),
  7197. test_ (test),
  7198. consequent_ (consequent),
  7199. alternative_(alternative)
  7200. {
  7201. range_.n0_c = std::make_pair<bool,std::size_t>(true,0);
  7202. range_.n1_c = std::make_pair<bool,std::size_t>(true,0);
  7203. range_.cache.first = range_.n0_c.second;
  7204. range_.cache.second = range_.n1_c.second;
  7205. if (is_generally_string_node(trinary_node<T>::branch_[0].first))
  7206. {
  7207. str0_base_ptr_ = dynamic_cast<str_base_ptr>(trinary_node<T>::branch_[0].first);
  7208. if (0 == str0_base_ptr_)
  7209. return;
  7210. str0_range_ptr_ = dynamic_cast<irange_ptr>(trinary_node<T>::branch_[0].first);
  7211. if (0 == str0_range_ptr_)
  7212. return;
  7213. }
  7214. if (is_generally_string_node(trinary_node<T>::branch_[1].first))
  7215. {
  7216. str1_base_ptr_ = dynamic_cast<str_base_ptr>(trinary_node<T>::branch_[1].first);
  7217. if (0 == str1_base_ptr_)
  7218. return;
  7219. str1_range_ptr_ = dynamic_cast<irange_ptr>(trinary_node<T>::branch_[1].first);
  7220. if (0 == str1_range_ptr_)
  7221. return;
  7222. }
  7223. initialised_ = str0_base_ptr_ &&
  7224. str1_base_ptr_ &&
  7225. str0_range_ptr_ &&
  7226. str1_range_ptr_ ;
  7227. }
  7228. inline T value() const
  7229. {
  7230. if (initialised_)
  7231. {
  7232. std::size_t r0 = 0;
  7233. std::size_t r1 = 0;
  7234. if (is_true(test_))
  7235. {
  7236. consequent_->value();
  7237. range_t& range = str0_range_ptr_->range_ref();
  7238. if (range(r0, r1, str0_base_ptr_->size()))
  7239. {
  7240. const std::size_t size = (r1 - r0) + 1;
  7241. value_.assign(str0_base_ptr_->base() + r0, size);
  7242. range_.n1_c.second = value_.size() - 1;
  7243. range_.cache.second = range_.n1_c.second;
  7244. return T(1);
  7245. }
  7246. }
  7247. else
  7248. {
  7249. alternative_->value();
  7250. range_t& range = str1_range_ptr_->range_ref();
  7251. if (range(r0, r1, str1_base_ptr_->size()))
  7252. {
  7253. const std::size_t size = (r1 - r0) + 1;
  7254. value_.assign(str1_base_ptr_->base() + r0, size);
  7255. range_.n1_c.second = value_.size() - 1;
  7256. range_.cache.second = range_.n1_c.second;
  7257. return T(0);
  7258. }
  7259. }
  7260. }
  7261. return std::numeric_limits<T>::quiet_NaN();
  7262. }
  7263. std::string str() const
  7264. {
  7265. return value_;
  7266. }
  7267. char_cptr base() const
  7268. {
  7269. return &value_[0];
  7270. }
  7271. std::size_t size() const
  7272. {
  7273. return value_.size();
  7274. }
  7275. range_t& range_ref()
  7276. {
  7277. return range_;
  7278. }
  7279. const range_t& range_ref() const
  7280. {
  7281. return range_;
  7282. }
  7283. inline typename expression_node<T>::node_type type() const
  7284. {
  7285. return expression_node<T>::e_strcondition;
  7286. }
  7287. private:
  7288. bool initialised_;
  7289. str_base_ptr str0_base_ptr_;
  7290. str_base_ptr str1_base_ptr_;
  7291. irange_ptr str0_range_ptr_;
  7292. irange_ptr str1_range_ptr_;
  7293. mutable range_t range_;
  7294. mutable std::string value_;
  7295. expression_ptr test_;
  7296. expression_ptr consequent_;
  7297. expression_ptr alternative_;
  7298. };
  7299. template <typename T>
  7300. class cons_conditional_str_node : public binary_node <T>,
  7301. public string_base_node<T>,
  7302. public range_interface <T>
  7303. {
  7304. public:
  7305. typedef expression_node <T>* expression_ptr;
  7306. typedef string_base_node<T>* str_base_ptr;
  7307. typedef range_pack <T> range_t;
  7308. typedef range_t* range_ptr;
  7309. typedef range_interface<T> irange_t;
  7310. typedef irange_t* irange_ptr;
  7311. cons_conditional_str_node(expression_ptr test,
  7312. expression_ptr consequent)
  7313. : binary_node<T>(details::e_default, consequent, test),
  7314. initialised_(false),
  7315. str0_base_ptr_ (0),
  7316. str0_range_ptr_(0),
  7317. test_ (test),
  7318. consequent_(consequent)
  7319. {
  7320. range_.n0_c = std::make_pair<bool,std::size_t>(true,0);
  7321. range_.n1_c = std::make_pair<bool,std::size_t>(true,0);
  7322. range_.cache.first = range_.n0_c.second;
  7323. range_.cache.second = range_.n1_c.second;
  7324. if (is_generally_string_node(binary_node<T>::branch_[0].first))
  7325. {
  7326. str0_base_ptr_ = dynamic_cast<str_base_ptr>(binary_node<T>::branch_[0].first);
  7327. if (0 == str0_base_ptr_)
  7328. return;
  7329. str0_range_ptr_ = dynamic_cast<irange_ptr>(binary_node<T>::branch_[0].first);
  7330. if (0 == str0_range_ptr_)
  7331. return;
  7332. }
  7333. initialised_ = str0_base_ptr_ && str0_range_ptr_ ;
  7334. }
  7335. inline T value() const
  7336. {
  7337. if (initialised_)
  7338. {
  7339. if (is_true(test_))
  7340. {
  7341. consequent_->value();
  7342. range_t& range = str0_range_ptr_->range_ref();
  7343. std::size_t r0 = 0;
  7344. std::size_t r1 = 0;
  7345. if (range(r0, r1, str0_base_ptr_->size()))
  7346. {
  7347. const std::size_t size = (r1 - r0) + 1;
  7348. value_.assign(str0_base_ptr_->base() + r0, size);
  7349. range_.n1_c.second = value_.size() - 1;
  7350. range_.cache.second = range_.n1_c.second;
  7351. return T(1);
  7352. }
  7353. }
  7354. }
  7355. return std::numeric_limits<T>::quiet_NaN();
  7356. }
  7357. std::string str() const
  7358. {
  7359. return value_;
  7360. }
  7361. char_cptr base() const
  7362. {
  7363. return &value_[0];
  7364. }
  7365. std::size_t size() const
  7366. {
  7367. return value_.size();
  7368. }
  7369. range_t& range_ref()
  7370. {
  7371. return range_;
  7372. }
  7373. const range_t& range_ref() const
  7374. {
  7375. return range_;
  7376. }
  7377. inline typename expression_node<T>::node_type type() const
  7378. {
  7379. return expression_node<T>::e_strccondition;
  7380. }
  7381. private:
  7382. bool initialised_;
  7383. str_base_ptr str0_base_ptr_;
  7384. irange_ptr str0_range_ptr_;
  7385. mutable range_t range_;
  7386. mutable std::string value_;
  7387. expression_ptr test_;
  7388. expression_ptr consequent_;
  7389. };
  7390. template <typename T, typename VarArgFunction>
  7391. class str_vararg_node : public expression_node <T>,
  7392. public string_base_node<T>,
  7393. public range_interface <T>
  7394. {
  7395. public:
  7396. typedef expression_node <T>* expression_ptr;
  7397. typedef string_base_node<T>* str_base_ptr;
  7398. typedef range_pack <T> range_t;
  7399. typedef range_t* range_ptr;
  7400. typedef range_interface<T> irange_t;
  7401. typedef irange_t* irange_ptr;
  7402. template <typename Allocator,
  7403. template <typename, typename> class Sequence>
  7404. explicit str_vararg_node(const Sequence<expression_ptr,Allocator>& arg_list)
  7405. : final_node_(arg_list.back()),
  7406. final_deletable_(branch_deletable(final_node_)),
  7407. initialised_(false),
  7408. str_base_ptr_ (0),
  7409. str_range_ptr_(0)
  7410. {
  7411. if (0 == final_node_)
  7412. return;
  7413. else if (!is_generally_string_node(final_node_))
  7414. return;
  7415. str_base_ptr_ = dynamic_cast<str_base_ptr>(final_node_);
  7416. if (0 == str_base_ptr_)
  7417. return;
  7418. str_range_ptr_ = dynamic_cast<irange_ptr>(final_node_);
  7419. if (0 == str_range_ptr_)
  7420. return;
  7421. initialised_ = str_base_ptr_ && str_range_ptr_;
  7422. if (arg_list.size() > 1)
  7423. {
  7424. const std::size_t arg_list_size = arg_list.size() - 1;
  7425. arg_list_.resize(arg_list_size);
  7426. delete_branch_.resize(arg_list_size);
  7427. for (std::size_t i = 0; i < arg_list_size; ++i)
  7428. {
  7429. if (arg_list[i])
  7430. {
  7431. arg_list_[i] = arg_list[i];
  7432. delete_branch_[i] = static_cast<unsigned char>(branch_deletable(arg_list_[i]) ? 1 : 0);
  7433. }
  7434. else
  7435. {
  7436. arg_list_ .clear();
  7437. delete_branch_.clear();
  7438. return;
  7439. }
  7440. }
  7441. }
  7442. }
  7443. ~str_vararg_node()
  7444. {
  7445. if (final_node_ && final_deletable_)
  7446. {
  7447. destroy_node(final_node_);
  7448. }
  7449. for (std::size_t i = 0; i < arg_list_.size(); ++i)
  7450. {
  7451. if (arg_list_[i] && delete_branch_[i])
  7452. {
  7453. destroy_node(arg_list_[i]);
  7454. }
  7455. }
  7456. }
  7457. inline T value() const
  7458. {
  7459. if (!arg_list_.empty())
  7460. {
  7461. VarArgFunction::process(arg_list_);
  7462. }
  7463. final_node_->value();
  7464. return std::numeric_limits<T>::quiet_NaN();
  7465. }
  7466. std::string str() const
  7467. {
  7468. return str_base_ptr_->str();
  7469. }
  7470. char_cptr base() const
  7471. {
  7472. return str_base_ptr_->base();
  7473. }
  7474. std::size_t size() const
  7475. {
  7476. return str_base_ptr_->size();
  7477. }
  7478. range_t& range_ref()
  7479. {
  7480. return str_range_ptr_->range_ref();
  7481. }
  7482. const range_t& range_ref() const
  7483. {
  7484. return str_range_ptr_->range_ref();
  7485. }
  7486. inline typename expression_node<T>::node_type type() const
  7487. {
  7488. return expression_node<T>::e_stringvararg;
  7489. }
  7490. private:
  7491. expression_ptr final_node_;
  7492. bool final_deletable_;
  7493. bool initialised_;
  7494. str_base_ptr str_base_ptr_;
  7495. irange_ptr str_range_ptr_;
  7496. std::vector<expression_ptr> arg_list_;
  7497. std::vector<unsigned char> delete_branch_;
  7498. };
  7499. #endif
  7500. template <typename T, std::size_t N>
  7501. inline T axn(T a, T x)
  7502. {
  7503. // a*x^n
  7504. return a * exprtk::details::numeric::fast_exp<T,N>::result(x);
  7505. }
  7506. template <typename T, std::size_t N>
  7507. inline T axnb(T a, T x, T b)
  7508. {
  7509. // a*x^n+b
  7510. return a * exprtk::details::numeric::fast_exp<T,N>::result(x) + b;
  7511. }
  7512. template <typename T>
  7513. struct sf_base
  7514. {
  7515. typedef typename details::functor_t<T>::Type Type;
  7516. typedef typename details::functor_t<T> functor_t;
  7517. typedef typename functor_t::qfunc_t quaternary_functor_t;
  7518. typedef typename functor_t::tfunc_t trinary_functor_t;
  7519. typedef typename functor_t::bfunc_t binary_functor_t;
  7520. typedef typename functor_t::ufunc_t unary_functor_t;
  7521. };
  7522. #define define_sfop3(NN,OP0,OP1) \
  7523. template <typename T> \
  7524. struct sf##NN##_op : public sf_base<T> \
  7525. { \
  7526. typedef typename sf_base<T>::Type const Type; \
  7527. static inline T process(Type x, Type y, Type z) \
  7528. { \
  7529. return (OP0); \
  7530. } \
  7531. static inline std::string id() \
  7532. { \
  7533. return OP1; \
  7534. } \
  7535. }; \
  7536. define_sfop3(00,(x + y) / z ,"(t+t)/t")
  7537. define_sfop3(01,(x + y) * z ,"(t+t)*t")
  7538. define_sfop3(02,(x + y) - z ,"(t+t)-t")
  7539. define_sfop3(03,(x + y) + z ,"(t+t)+t")
  7540. define_sfop3(04,(x - y) + z ,"(t-t)+t")
  7541. define_sfop3(05,(x - y) / z ,"(t-t)/t")
  7542. define_sfop3(06,(x - y) * z ,"(t-t)*t")
  7543. define_sfop3(07,(x * y) + z ,"(t*t)+t")
  7544. define_sfop3(08,(x * y) - z ,"(t*t)-t")
  7545. define_sfop3(09,(x * y) / z ,"(t*t)/t")
  7546. define_sfop3(10,(x * y) * z ,"(t*t)*t")
  7547. define_sfop3(11,(x / y) + z ,"(t/t)+t")
  7548. define_sfop3(12,(x / y) - z ,"(t/t)-t")
  7549. define_sfop3(13,(x / y) / z ,"(t/t)/t")
  7550. define_sfop3(14,(x / y) * z ,"(t/t)*t")
  7551. define_sfop3(15,x / (y + z) ,"t/(t+t)")
  7552. define_sfop3(16,x / (y - z) ,"t/(t-t)")
  7553. define_sfop3(17,x / (y * z) ,"t/(t*t)")
  7554. define_sfop3(18,x / (y / z) ,"t/(t/t)")
  7555. define_sfop3(19,x * (y + z) ,"t*(t+t)")
  7556. define_sfop3(20,x * (y - z) ,"t*(t-t)")
  7557. define_sfop3(21,x * (y * z) ,"t*(t*t)")
  7558. define_sfop3(22,x * (y / z) ,"t*(t/t)")
  7559. define_sfop3(23,x - (y + z) ,"t-(t+t)")
  7560. define_sfop3(24,x - (y - z) ,"t-(t-t)")
  7561. define_sfop3(25,x - (y / z) ,"t-(t/t)")
  7562. define_sfop3(26,x - (y * z) ,"t-(t*t)")
  7563. define_sfop3(27,x + (y * z) ,"t+(t*t)")
  7564. define_sfop3(28,x + (y / z) ,"t+(t/t)")
  7565. define_sfop3(29,x + (y + z) ,"t+(t+t)")
  7566. define_sfop3(30,x + (y - z) ,"t+(t-t)")
  7567. define_sfop3(31,(axnb<T,2>(x,y,z))," ")
  7568. define_sfop3(32,(axnb<T,3>(x,y,z))," ")
  7569. define_sfop3(33,(axnb<T,4>(x,y,z))," ")
  7570. define_sfop3(34,(axnb<T,5>(x,y,z))," ")
  7571. define_sfop3(35,(axnb<T,6>(x,y,z))," ")
  7572. define_sfop3(36,(axnb<T,7>(x,y,z))," ")
  7573. define_sfop3(37,(axnb<T,8>(x,y,z))," ")
  7574. define_sfop3(38,(axnb<T,9>(x,y,z))," ")
  7575. define_sfop3(39,x * numeric::log(y) + z,"")
  7576. define_sfop3(40,x * numeric::log(y) - z,"")
  7577. define_sfop3(41,x * numeric::log10(y) + z,"")
  7578. define_sfop3(42,x * numeric::log10(y) - z,"")
  7579. define_sfop3(43,x * numeric::sin(y) + z ,"")
  7580. define_sfop3(44,x * numeric::sin(y) - z ,"")
  7581. define_sfop3(45,x * numeric::cos(y) + z ,"")
  7582. define_sfop3(46,x * numeric::cos(y) - z ,"")
  7583. define_sfop3(47,details::is_true(x) ? y : z,"")
  7584. #define define_sfop4(NN,OP0,OP1) \
  7585. template <typename T> \
  7586. struct sf##NN##_op : public sf_base<T> \
  7587. { \
  7588. typedef typename sf_base<T>::Type const Type; \
  7589. static inline T process(Type x, Type y, Type z, Type w) \
  7590. { \
  7591. return (OP0); \
  7592. } \
  7593. static inline std::string id() { return OP1; } \
  7594. }; \
  7595. define_sfop4(48,(x + ((y + z) / w)),"t+((t+t)/t)")
  7596. define_sfop4(49,(x + ((y + z) * w)),"t+((t+t)*t)")
  7597. define_sfop4(50,(x + ((y - z) / w)),"t+((t-t)/t)")
  7598. define_sfop4(51,(x + ((y - z) * w)),"t+((t-t)*t)")
  7599. define_sfop4(52,(x + ((y * z) / w)),"t+((t*t)/t)")
  7600. define_sfop4(53,(x + ((y * z) * w)),"t+((t*t)*t)")
  7601. define_sfop4(54,(x + ((y / z) + w)),"t+((t/t)+t)")
  7602. define_sfop4(55,(x + ((y / z) / w)),"t+((t/t)/t)")
  7603. define_sfop4(56,(x + ((y / z) * w)),"t+((t/t)*t)")
  7604. define_sfop4(57,(x - ((y + z) / w)),"t-((t+t)/t)")
  7605. define_sfop4(58,(x - ((y + z) * w)),"t-((t+t)*t)")
  7606. define_sfop4(59,(x - ((y - z) / w)),"t-((t-t)/t)")
  7607. define_sfop4(60,(x - ((y - z) * w)),"t-((t-t)*t)")
  7608. define_sfop4(61,(x - ((y * z) / w)),"t-((t*t)/t)")
  7609. define_sfop4(62,(x - ((y * z) * w)),"t-((t*t)*t)")
  7610. define_sfop4(63,(x - ((y / z) / w)),"t-((t/t)/t)")
  7611. define_sfop4(64,(x - ((y / z) * w)),"t-((t/t)*t)")
  7612. define_sfop4(65,(((x + y) * z) - w),"((t+t)*t)-t")
  7613. define_sfop4(66,(((x - y) * z) - w),"((t-t)*t)-t")
  7614. define_sfop4(67,(((x * y) * z) - w),"((t*t)*t)-t")
  7615. define_sfop4(68,(((x / y) * z) - w),"((t/t)*t)-t")
  7616. define_sfop4(69,(((x + y) / z) - w),"((t+t)/t)-t")
  7617. define_sfop4(70,(((x - y) / z) - w),"((t-t)/t)-t")
  7618. define_sfop4(71,(((x * y) / z) - w),"((t*t)/t)-t")
  7619. define_sfop4(72,(((x / y) / z) - w),"((t/t)/t)-t")
  7620. define_sfop4(73,((x * y) + (z * w)),"(t*t)+(t*t)")
  7621. define_sfop4(74,((x * y) - (z * w)),"(t*t)-(t*t)")
  7622. define_sfop4(75,((x * y) + (z / w)),"(t*t)+(t/t)")
  7623. define_sfop4(76,((x * y) - (z / w)),"(t*t)-(t/t)")
  7624. define_sfop4(77,((x / y) + (z / w)),"(t/t)+(t/t)")
  7625. define_sfop4(78,((x / y) - (z / w)),"(t/t)-(t/t)")
  7626. define_sfop4(79,((x / y) - (z * w)),"(t/t)-(t*t)")
  7627. define_sfop4(80,(x / (y + (z * w))),"t/(t+(t*t))")
  7628. define_sfop4(81,(x / (y - (z * w))),"t/(t-(t*t))")
  7629. define_sfop4(82,(x * (y + (z * w))),"t*(t+(t*t))")
  7630. define_sfop4(83,(x * (y - (z * w))),"t*(t-(t*t))")
  7631. define_sfop4(84,(axn<T,2>(x,y) + axn<T,2>(z,w)),"")
  7632. define_sfop4(85,(axn<T,3>(x,y) + axn<T,3>(z,w)),"")
  7633. define_sfop4(86,(axn<T,4>(x,y) + axn<T,4>(z,w)),"")
  7634. define_sfop4(87,(axn<T,5>(x,y) + axn<T,5>(z,w)),"")
  7635. define_sfop4(88,(axn<T,6>(x,y) + axn<T,6>(z,w)),"")
  7636. define_sfop4(89,(axn<T,7>(x,y) + axn<T,7>(z,w)),"")
  7637. define_sfop4(90,(axn<T,8>(x,y) + axn<T,8>(z,w)),"")
  7638. define_sfop4(91,(axn<T,9>(x,y) + axn<T,9>(z,w)),"")
  7639. define_sfop4(92,((details::is_true(x) && details::is_true(y)) ? z : w),"")
  7640. define_sfop4(93,((details::is_true(x) || details::is_true(y)) ? z : w),"")
  7641. define_sfop4(94,((x < y) ? z : w),"")
  7642. define_sfop4(95,((x <= y) ? z : w),"")
  7643. define_sfop4(96,((x > y) ? z : w),"")
  7644. define_sfop4(97,((x >= y) ? z : w),"")
  7645. define_sfop4(98,(details::is_true(numeric::equal(x,y)) ? z : w),"")
  7646. define_sfop4(99,(x * numeric::sin(y) + z * numeric::cos(w)),"")
  7647. define_sfop4(ext00,((x + y) - (z * w)),"(t+t)-(t*t)")
  7648. define_sfop4(ext01,((x + y) - (z / w)),"(t+t)-(t/t)")
  7649. define_sfop4(ext02,((x + y) + (z * w)),"(t+t)+(t*t)")
  7650. define_sfop4(ext03,((x + y) + (z / w)),"(t+t)+(t/t)")
  7651. define_sfop4(ext04,((x - y) + (z * w)),"(t-t)+(t*t)")
  7652. define_sfop4(ext05,((x - y) + (z / w)),"(t-t)+(t/t)")
  7653. define_sfop4(ext06,((x - y) - (z * w)),"(t-t)-(t*t)")
  7654. define_sfop4(ext07,((x - y) - (z / w)),"(t-t)-(t/t)")
  7655. define_sfop4(ext08,((x + y) - (z - w)),"(t+t)-(t-t)")
  7656. define_sfop4(ext09,((x + y) + (z - w)),"(t+t)+(t-t)")
  7657. define_sfop4(ext10,((x + y) + (z + w)),"(t+t)+(t+t)")
  7658. define_sfop4(ext11,((x + y) * (z - w)),"(t+t)*(t-t)")
  7659. define_sfop4(ext12,((x + y) / (z - w)),"(t+t)/(t-t)")
  7660. define_sfop4(ext13,((x - y) - (z + w)),"(t-t)-(t+t)")
  7661. define_sfop4(ext14,((x - y) + (z + w)),"(t-t)+(t+t)")
  7662. define_sfop4(ext15,((x - y) * (z + w)),"(t-t)*(t+t)")
  7663. define_sfop4(ext16,((x - y) / (z + w)),"(t-t)/(t+t)")
  7664. define_sfop4(ext17,((x * y) - (z + w)),"(t*t)-(t+t)")
  7665. define_sfop4(ext18,((x / y) - (z + w)),"(t/t)-(t+t)")
  7666. define_sfop4(ext19,((x * y) + (z + w)),"(t*t)+(t+t)")
  7667. define_sfop4(ext20,((x / y) + (z + w)),"(t/t)+(t+t)")
  7668. define_sfop4(ext21,((x * y) + (z - w)),"(t*t)+(t-t)")
  7669. define_sfop4(ext22,((x / y) + (z - w)),"(t/t)+(t-t)")
  7670. define_sfop4(ext23,((x * y) - (z - w)),"(t*t)-(t-t)")
  7671. define_sfop4(ext24,((x / y) - (z - w)),"(t/t)-(t-t)")
  7672. define_sfop4(ext25,((x + y) * (z * w)),"(t+t)*(t*t)")
  7673. define_sfop4(ext26,((x + y) * (z / w)),"(t+t)*(t/t)")
  7674. define_sfop4(ext27,((x + y) / (z * w)),"(t+t)/(t*t)")
  7675. define_sfop4(ext28,((x + y) / (z / w)),"(t+t)/(t/t)")
  7676. define_sfop4(ext29,((x - y) / (z * w)),"(t-t)/(t*t)")
  7677. define_sfop4(ext30,((x - y) / (z / w)),"(t-t)/(t/t)")
  7678. define_sfop4(ext31,((x - y) * (z * w)),"(t-t)*(t*t)")
  7679. define_sfop4(ext32,((x - y) * (z / w)),"(t-t)*(t/t)")
  7680. define_sfop4(ext33,((x * y) * (z + w)),"(t*t)*(t+t)")
  7681. define_sfop4(ext34,((x / y) * (z + w)),"(t/t)*(t+t)")
  7682. define_sfop4(ext35,((x * y) / (z + w)),"(t*t)/(t+t)")
  7683. define_sfop4(ext36,((x / y) / (z + w)),"(t/t)/(t+t)")
  7684. define_sfop4(ext37,((x * y) / (z - w)),"(t*t)/(t-t)")
  7685. define_sfop4(ext38,((x / y) / (z - w)),"(t/t)/(t-t)")
  7686. define_sfop4(ext39,((x * y) * (z - w)),"(t*t)*(t-t)")
  7687. define_sfop4(ext40,((x * y) / (z * w)),"(t*t)/(t*t)")
  7688. define_sfop4(ext41,((x / y) * (z / w)),"(t/t)*(t/t)")
  7689. define_sfop4(ext42,((x / y) * (z - w)),"(t/t)*(t-t)")
  7690. define_sfop4(ext43,((x * y) * (z * w)),"(t*t)*(t*t)")
  7691. define_sfop4(ext44,(x + (y * (z / w))),"t+(t*(t/t))")
  7692. define_sfop4(ext45,(x - (y * (z / w))),"t-(t*(t/t))")
  7693. define_sfop4(ext46,(x + (y / (z * w))),"t+(t/(t*t))")
  7694. define_sfop4(ext47,(x - (y / (z * w))),"t-(t/(t*t))")
  7695. define_sfop4(ext48,(((x - y) - z) * w),"((t-t)-t)*t")
  7696. define_sfop4(ext49,(((x - y) - z) / w),"((t-t)-t)/t")
  7697. define_sfop4(ext50,(((x - y) + z) * w),"((t-t)+t)*t")
  7698. define_sfop4(ext51,(((x - y) + z) / w),"((t-t)+t)/t")
  7699. define_sfop4(ext52,((x + (y - z)) * w),"(t+(t-t))*t")
  7700. define_sfop4(ext53,((x + (y - z)) / w),"(t+(t-t))/t")
  7701. define_sfop4(ext54,((x + y) / (z + w)),"(t+t)/(t+t)")
  7702. define_sfop4(ext55,((x - y) / (z - w)),"(t-t)/(t-t)")
  7703. define_sfop4(ext56,((x + y) * (z + w)),"(t+t)*(t+t)")
  7704. define_sfop4(ext57,((x - y) * (z - w)),"(t-t)*(t-t)")
  7705. define_sfop4(ext58,((x - y) + (z - w)),"(t-t)+(t-t)")
  7706. define_sfop4(ext59,((x - y) - (z - w)),"(t-t)-(t-t)")
  7707. define_sfop4(ext60,((x / y) + (z * w)),"(t/t)+(t*t)")
  7708. define_sfop4(ext61,(((x * y) * z) / w),"((t*t)*t)/t")
  7709. #undef define_sfop3
  7710. #undef define_sfop4
  7711. template <typename T, typename SpecialFunction>
  7712. class sf3_node : public trinary_node<T>
  7713. {
  7714. public:
  7715. typedef expression_node<T>* expression_ptr;
  7716. sf3_node(const operator_type& opr,
  7717. expression_ptr branch0,
  7718. expression_ptr branch1,
  7719. expression_ptr branch2)
  7720. : trinary_node<T>(opr, branch0, branch1, branch2)
  7721. {}
  7722. inline T value() const
  7723. {
  7724. const T x = trinary_node<T>::branch_[0].first->value();
  7725. const T y = trinary_node<T>::branch_[1].first->value();
  7726. const T z = trinary_node<T>::branch_[2].first->value();
  7727. return SpecialFunction::process(x, y, z);
  7728. }
  7729. };
  7730. template <typename T, typename SpecialFunction>
  7731. class sf4_node : public quaternary_node<T>
  7732. {
  7733. public:
  7734. typedef expression_node<T>* expression_ptr;
  7735. sf4_node(const operator_type& opr,
  7736. expression_ptr branch0,
  7737. expression_ptr branch1,
  7738. expression_ptr branch2,
  7739. expression_ptr branch3)
  7740. : quaternary_node<T>(opr, branch0, branch1, branch2, branch3)
  7741. {}
  7742. inline T value() const
  7743. {
  7744. const T x = quaternary_node<T>::branch_[0].first->value();
  7745. const T y = quaternary_node<T>::branch_[1].first->value();
  7746. const T z = quaternary_node<T>::branch_[2].first->value();
  7747. const T w = quaternary_node<T>::branch_[3].first->value();
  7748. return SpecialFunction::process(x, y, z, w);
  7749. }
  7750. };
  7751. template <typename T, typename SpecialFunction>
  7752. class sf3_var_node : public expression_node<T>
  7753. {
  7754. public:
  7755. typedef expression_node<T>* expression_ptr;
  7756. sf3_var_node(const T& v0, const T& v1, const T& v2)
  7757. : v0_(v0),
  7758. v1_(v1),
  7759. v2_(v2)
  7760. {}
  7761. inline T value() const
  7762. {
  7763. return SpecialFunction::process(v0_, v1_, v2_);
  7764. }
  7765. inline typename expression_node<T>::node_type type() const
  7766. {
  7767. return expression_node<T>::e_trinary;
  7768. }
  7769. private:
  7770. sf3_var_node(sf3_var_node<T,SpecialFunction>&);
  7771. sf3_var_node<T,SpecialFunction>& operator=(sf3_var_node<T,SpecialFunction>&);
  7772. const T& v0_;
  7773. const T& v1_;
  7774. const T& v2_;
  7775. };
  7776. template <typename T, typename SpecialFunction>
  7777. class sf4_var_node : public expression_node<T>
  7778. {
  7779. public:
  7780. typedef expression_node<T>* expression_ptr;
  7781. sf4_var_node(const T& v0, const T& v1, const T& v2, const T& v3)
  7782. : v0_(v0),
  7783. v1_(v1),
  7784. v2_(v2),
  7785. v3_(v3)
  7786. {}
  7787. inline T value() const
  7788. {
  7789. return SpecialFunction::process(v0_, v1_, v2_, v3_);
  7790. }
  7791. inline typename expression_node<T>::node_type type() const
  7792. {
  7793. return expression_node<T>::e_trinary;
  7794. }
  7795. private:
  7796. sf4_var_node(sf4_var_node<T,SpecialFunction>&);
  7797. sf4_var_node<T,SpecialFunction>& operator=(sf4_var_node<T,SpecialFunction>&);
  7798. const T& v0_;
  7799. const T& v1_;
  7800. const T& v2_;
  7801. const T& v3_;
  7802. };
  7803. template <typename T, typename VarArgFunction>
  7804. class vararg_node : public expression_node<T>
  7805. {
  7806. public:
  7807. typedef expression_node<T>* expression_ptr;
  7808. template <typename Allocator,
  7809. template <typename, typename> class Sequence>
  7810. explicit vararg_node(const Sequence<expression_ptr,Allocator>& arg_list)
  7811. {
  7812. arg_list_ .resize(arg_list.size());
  7813. delete_branch_.resize(arg_list.size());
  7814. for (std::size_t i = 0; i < arg_list.size(); ++i)
  7815. {
  7816. if (arg_list[i])
  7817. {
  7818. arg_list_[i] = arg_list[i];
  7819. delete_branch_[i] = static_cast<unsigned char>(branch_deletable(arg_list_[i]) ? 1 : 0);
  7820. }
  7821. else
  7822. {
  7823. arg_list_.clear();
  7824. delete_branch_.clear();
  7825. return;
  7826. }
  7827. }
  7828. }
  7829. ~vararg_node()
  7830. {
  7831. for (std::size_t i = 0; i < arg_list_.size(); ++i)
  7832. {
  7833. if (arg_list_[i] && delete_branch_[i])
  7834. {
  7835. destroy_node(arg_list_[i]);
  7836. }
  7837. }
  7838. }
  7839. inline T value() const
  7840. {
  7841. return VarArgFunction::process(arg_list_);
  7842. }
  7843. inline typename expression_node<T>::node_type type() const
  7844. {
  7845. return expression_node<T>::e_vararg;
  7846. }
  7847. private:
  7848. std::vector<expression_ptr> arg_list_;
  7849. std::vector<unsigned char> delete_branch_;
  7850. };
  7851. template <typename T, typename VarArgFunction>
  7852. class vararg_varnode : public expression_node<T>
  7853. {
  7854. public:
  7855. typedef expression_node<T>* expression_ptr;
  7856. template <typename Allocator,
  7857. template <typename, typename> class Sequence>
  7858. explicit vararg_varnode(const Sequence<expression_ptr,Allocator>& arg_list)
  7859. {
  7860. arg_list_.resize(arg_list.size());
  7861. for (std::size_t i = 0; i < arg_list.size(); ++i)
  7862. {
  7863. if (arg_list[i] && is_variable_node(arg_list[i]))
  7864. {
  7865. variable_node<T>* var_node_ptr = static_cast<variable_node<T>*>(arg_list[i]);
  7866. arg_list_[i] = (&var_node_ptr->ref());
  7867. }
  7868. else
  7869. {
  7870. arg_list_.clear();
  7871. return;
  7872. }
  7873. }
  7874. }
  7875. inline T value() const
  7876. {
  7877. if (!arg_list_.empty())
  7878. return VarArgFunction::process(arg_list_);
  7879. else
  7880. return std::numeric_limits<T>::quiet_NaN();
  7881. }
  7882. inline typename expression_node<T>::node_type type() const
  7883. {
  7884. return expression_node<T>::e_vararg;
  7885. }
  7886. private:
  7887. std::vector<const T*> arg_list_;
  7888. };
  7889. template <typename T, typename VecFunction>
  7890. class vectorize_node : public expression_node<T>
  7891. {
  7892. public:
  7893. typedef expression_node<T>* expression_ptr;
  7894. explicit vectorize_node(const expression_ptr v)
  7895. : ivec_ptr_(0),
  7896. v_(v),
  7897. v_deletable_(branch_deletable(v_))
  7898. {
  7899. if (is_ivector_node(v))
  7900. {
  7901. ivec_ptr_ = dynamic_cast<vector_interface<T>*>(v);
  7902. }
  7903. else
  7904. ivec_ptr_ = 0;
  7905. }
  7906. ~vectorize_node()
  7907. {
  7908. if (v_ && v_deletable_)
  7909. {
  7910. destroy_node(v_);
  7911. }
  7912. }
  7913. inline T value() const
  7914. {
  7915. if (ivec_ptr_)
  7916. {
  7917. v_->value();
  7918. return VecFunction::process(ivec_ptr_);
  7919. }
  7920. else
  7921. return std::numeric_limits<T>::quiet_NaN();
  7922. }
  7923. inline typename expression_node<T>::node_type type() const
  7924. {
  7925. return expression_node<T>::e_vecfunc;
  7926. }
  7927. private:
  7928. vector_interface<T>* ivec_ptr_;
  7929. expression_ptr v_;
  7930. const bool v_deletable_;
  7931. };
  7932. template <typename T>
  7933. class assignment_node : public binary_node<T>
  7934. {
  7935. public:
  7936. typedef expression_node<T>* expression_ptr;
  7937. assignment_node(const operator_type& opr,
  7938. expression_ptr branch0,
  7939. expression_ptr branch1)
  7940. : binary_node<T>(opr, branch0, branch1),
  7941. var_node_ptr_(0)
  7942. {
  7943. if (is_variable_node(binary_node<T>::branch_[0].first))
  7944. {
  7945. var_node_ptr_ = static_cast<variable_node<T>*>(binary_node<T>::branch_[0].first);
  7946. }
  7947. }
  7948. inline T value() const
  7949. {
  7950. if (var_node_ptr_)
  7951. {
  7952. T& result = var_node_ptr_->ref();
  7953. result = binary_node<T>::branch_[1].first->value();
  7954. return result;
  7955. }
  7956. else
  7957. return std::numeric_limits<T>::quiet_NaN();
  7958. }
  7959. private:
  7960. variable_node<T>* var_node_ptr_;
  7961. };
  7962. template <typename T>
  7963. class assignment_vec_elem_node : public binary_node<T>
  7964. {
  7965. public:
  7966. typedef expression_node<T>* expression_ptr;
  7967. assignment_vec_elem_node(const operator_type& opr,
  7968. expression_ptr branch0,
  7969. expression_ptr branch1)
  7970. : binary_node<T>(opr, branch0, branch1),
  7971. vec_node_ptr_(0)
  7972. {
  7973. if (is_vector_elem_node(binary_node<T>::branch_[0].first))
  7974. {
  7975. vec_node_ptr_ = static_cast<vector_elem_node<T>*>(binary_node<T>::branch_[0].first);
  7976. }
  7977. }
  7978. inline T value() const
  7979. {
  7980. if (vec_node_ptr_)
  7981. {
  7982. T& result = vec_node_ptr_->ref();
  7983. result = binary_node<T>::branch_[1].first->value();
  7984. return result;
  7985. }
  7986. else
  7987. return std::numeric_limits<T>::quiet_NaN();
  7988. }
  7989. private:
  7990. vector_elem_node<T>* vec_node_ptr_;
  7991. };
  7992. template <typename T>
  7993. class assignment_rebasevec_elem_node : public binary_node<T>
  7994. {
  7995. public:
  7996. typedef expression_node<T>* expression_ptr;
  7997. assignment_rebasevec_elem_node(const operator_type& opr,
  7998. expression_ptr branch0,
  7999. expression_ptr branch1)
  8000. : binary_node<T>(opr, branch0, branch1),
  8001. rbvec_node_ptr_(0)
  8002. {
  8003. if (is_rebasevector_elem_node(binary_node<T>::branch_[0].first))
  8004. {
  8005. rbvec_node_ptr_ = static_cast<rebasevector_elem_node<T>*>(binary_node<T>::branch_[0].first);
  8006. }
  8007. }
  8008. inline T value() const
  8009. {
  8010. if (rbvec_node_ptr_)
  8011. {
  8012. T& result = rbvec_node_ptr_->ref();
  8013. result = binary_node<T>::branch_[1].first->value();
  8014. return result;
  8015. }
  8016. else
  8017. return std::numeric_limits<T>::quiet_NaN();
  8018. }
  8019. private:
  8020. rebasevector_elem_node<T>* rbvec_node_ptr_;
  8021. };
  8022. template <typename T>
  8023. class assignment_rebasevec_celem_node : public binary_node<T>
  8024. {
  8025. public:
  8026. typedef expression_node<T>* expression_ptr;
  8027. assignment_rebasevec_celem_node(const operator_type& opr,
  8028. expression_ptr branch0,
  8029. expression_ptr branch1)
  8030. : binary_node<T>(opr, branch0, branch1),
  8031. rbvec_node_ptr_(0)
  8032. {
  8033. if (is_rebasevector_celem_node(binary_node<T>::branch_[0].first))
  8034. {
  8035. rbvec_node_ptr_ = static_cast<rebasevector_celem_node<T>*>(binary_node<T>::branch_[0].first);
  8036. }
  8037. }
  8038. inline T value() const
  8039. {
  8040. if (rbvec_node_ptr_)
  8041. {
  8042. T& result = rbvec_node_ptr_->ref();
  8043. result = binary_node<T>::branch_[1].first->value();
  8044. return result;
  8045. }
  8046. else
  8047. return std::numeric_limits<T>::quiet_NaN();
  8048. }
  8049. private:
  8050. rebasevector_celem_node<T>* rbvec_node_ptr_;
  8051. };
  8052. template <typename T>
  8053. class assignment_vec_node : public binary_node <T>,
  8054. public vector_interface<T>
  8055. {
  8056. public:
  8057. typedef expression_node<T>* expression_ptr;
  8058. typedef vector_node<T>* vector_node_ptr;
  8059. typedef vec_data_store<T> vds_t;
  8060. assignment_vec_node(const operator_type& opr,
  8061. expression_ptr branch0,
  8062. expression_ptr branch1)
  8063. : binary_node<T>(opr, branch0, branch1),
  8064. vec_node_ptr_(0)
  8065. {
  8066. if (is_vector_node(binary_node<T>::branch_[0].first))
  8067. {
  8068. vec_node_ptr_ = static_cast<vector_node<T>*>(binary_node<T>::branch_[0].first);
  8069. vds() = vec_node_ptr_->vds();
  8070. }
  8071. }
  8072. inline T value() const
  8073. {
  8074. if (vec_node_ptr_)
  8075. {
  8076. const T v = binary_node<T>::branch_[1].first->value();
  8077. T* vec = vds().data();
  8078. loop_unroll::details lud(size());
  8079. const T* upper_bound = vec + lud.upper_bound;
  8080. while (vec < upper_bound)
  8081. {
  8082. #define exprtk_loop(N) \
  8083. vec[N] = v; \
  8084. exprtk_loop( 0) exprtk_loop( 1)
  8085. exprtk_loop( 2) exprtk_loop( 3)
  8086. #ifndef exprtk_disable_superscalar_unroll
  8087. exprtk_loop( 4) exprtk_loop( 5)
  8088. exprtk_loop( 6) exprtk_loop( 7)
  8089. exprtk_loop( 8) exprtk_loop( 9)
  8090. exprtk_loop(10) exprtk_loop(11)
  8091. exprtk_loop(12) exprtk_loop(13)
  8092. exprtk_loop(14) exprtk_loop(15)
  8093. #endif
  8094. vec += lud.batch_size;
  8095. }
  8096. exprtk_disable_fallthrough_begin
  8097. switch (lud.remainder)
  8098. {
  8099. #define case_stmt(N) \
  8100. case N : *vec++ = v; \
  8101. #ifndef exprtk_disable_superscalar_unroll
  8102. case_stmt(15) case_stmt(14)
  8103. case_stmt(13) case_stmt(12)
  8104. case_stmt(11) case_stmt(10)
  8105. case_stmt( 9) case_stmt( 8)
  8106. case_stmt( 7) case_stmt( 6)
  8107. case_stmt( 5) case_stmt( 4)
  8108. #endif
  8109. case_stmt( 3) case_stmt( 2)
  8110. case_stmt( 1)
  8111. }
  8112. exprtk_disable_fallthrough_end
  8113. #undef exprtk_loop
  8114. #undef case_stmt
  8115. return vec_node_ptr_->value();
  8116. }
  8117. else
  8118. return std::numeric_limits<T>::quiet_NaN();
  8119. }
  8120. vector_node_ptr vec() const
  8121. {
  8122. return vec_node_ptr_;
  8123. }
  8124. vector_node_ptr vec()
  8125. {
  8126. return vec_node_ptr_;
  8127. }
  8128. inline typename expression_node<T>::node_type type() const
  8129. {
  8130. return expression_node<T>::e_vecvalass;
  8131. }
  8132. std::size_t size() const
  8133. {
  8134. return vds().size();
  8135. }
  8136. vds_t& vds()
  8137. {
  8138. return vds_;
  8139. }
  8140. const vds_t& vds() const
  8141. {
  8142. return vds_;
  8143. }
  8144. private:
  8145. vector_node<T>* vec_node_ptr_;
  8146. vds_t vds_;
  8147. };
  8148. template <typename T>
  8149. class assignment_vecvec_node : public binary_node <T>,
  8150. public vector_interface<T>
  8151. {
  8152. public:
  8153. typedef expression_node<T>* expression_ptr;
  8154. typedef vector_node<T>* vector_node_ptr;
  8155. typedef vec_data_store<T> vds_t;
  8156. assignment_vecvec_node(const operator_type& opr,
  8157. expression_ptr branch0,
  8158. expression_ptr branch1)
  8159. : binary_node<T>(opr, branch0, branch1),
  8160. vec0_node_ptr_(0),
  8161. vec1_node_ptr_(0),
  8162. initialised_(false),
  8163. src_is_ivec_(false)
  8164. {
  8165. if (is_vector_node(binary_node<T>::branch_[0].first))
  8166. {
  8167. vec0_node_ptr_ = static_cast<vector_node<T>*>(binary_node<T>::branch_[0].first);
  8168. vds() = vec0_node_ptr_->vds();
  8169. }
  8170. if (is_vector_node(binary_node<T>::branch_[1].first))
  8171. {
  8172. vec1_node_ptr_ = static_cast<vector_node<T>*>(binary_node<T>::branch_[1].first);
  8173. vds_t::match_sizes(vds(),vec1_node_ptr_->vds());
  8174. }
  8175. else if (is_ivector_node(binary_node<T>::branch_[1].first))
  8176. {
  8177. vector_interface<T>* vi = reinterpret_cast<vector_interface<T>*>(0);
  8178. if (0 != (vi = dynamic_cast<vector_interface<T>*>(binary_node<T>::branch_[1].first)))
  8179. {
  8180. vec1_node_ptr_ = vi->vec();
  8181. if (!vi->side_effect())
  8182. {
  8183. vi->vds() = vds();
  8184. src_is_ivec_ = true;
  8185. }
  8186. else
  8187. vds_t::match_sizes(vds(),vi->vds());
  8188. }
  8189. }
  8190. initialised_ = (vec0_node_ptr_ && vec1_node_ptr_);
  8191. }
  8192. inline T value() const
  8193. {
  8194. if (initialised_)
  8195. {
  8196. binary_node<T>::branch_[1].first->value();
  8197. if (src_is_ivec_)
  8198. return vec0_node_ptr_->value();
  8199. T* vec0 = vec0_node_ptr_->vds().data();
  8200. T* vec1 = vec1_node_ptr_->vds().data();
  8201. loop_unroll::details lud(size());
  8202. const T* upper_bound = vec0 + lud.upper_bound;
  8203. while (vec0 < upper_bound)
  8204. {
  8205. #define exprtk_loop(N) \
  8206. vec0[N] = vec1[N]; \
  8207. exprtk_loop( 0) exprtk_loop( 1)
  8208. exprtk_loop( 2) exprtk_loop( 3)
  8209. #ifndef exprtk_disable_superscalar_unroll
  8210. exprtk_loop( 4) exprtk_loop( 5)
  8211. exprtk_loop( 6) exprtk_loop( 7)
  8212. exprtk_loop( 8) exprtk_loop( 9)
  8213. exprtk_loop(10) exprtk_loop(11)
  8214. exprtk_loop(12) exprtk_loop(13)
  8215. exprtk_loop(14) exprtk_loop(15)
  8216. #endif
  8217. vec0 += lud.batch_size;
  8218. vec1 += lud.batch_size;
  8219. }
  8220. exprtk_disable_fallthrough_begin
  8221. switch (lud.remainder)
  8222. {
  8223. #define case_stmt(N) \
  8224. case N : *vec0++ = *vec1++; \
  8225. #ifndef exprtk_disable_superscalar_unroll
  8226. case_stmt(15) case_stmt(14)
  8227. case_stmt(13) case_stmt(12)
  8228. case_stmt(11) case_stmt(10)
  8229. case_stmt( 9) case_stmt( 8)
  8230. case_stmt( 7) case_stmt( 6)
  8231. case_stmt( 5) case_stmt( 4)
  8232. #endif
  8233. case_stmt( 3) case_stmt( 2)
  8234. case_stmt( 1)
  8235. }
  8236. exprtk_disable_fallthrough_end
  8237. #undef exprtk_loop
  8238. #undef case_stmt
  8239. return vec0_node_ptr_->value();
  8240. }
  8241. else
  8242. return std::numeric_limits<T>::quiet_NaN();
  8243. }
  8244. vector_node_ptr vec() const
  8245. {
  8246. return vec0_node_ptr_;
  8247. }
  8248. vector_node_ptr vec()
  8249. {
  8250. return vec0_node_ptr_;
  8251. }
  8252. inline typename expression_node<T>::node_type type() const
  8253. {
  8254. return expression_node<T>::e_vecvecass;
  8255. }
  8256. std::size_t size() const
  8257. {
  8258. return vds().size();
  8259. }
  8260. vds_t& vds()
  8261. {
  8262. return vds_;
  8263. }
  8264. const vds_t& vds() const
  8265. {
  8266. return vds_;
  8267. }
  8268. private:
  8269. vector_node<T>* vec0_node_ptr_;
  8270. vector_node<T>* vec1_node_ptr_;
  8271. bool initialised_;
  8272. bool src_is_ivec_;
  8273. vds_t vds_;
  8274. };
  8275. template <typename T, typename Operation>
  8276. class assignment_op_node : public binary_node<T>
  8277. {
  8278. public:
  8279. typedef expression_node<T>* expression_ptr;
  8280. assignment_op_node(const operator_type& opr,
  8281. expression_ptr branch0,
  8282. expression_ptr branch1)
  8283. : binary_node<T>(opr, branch0, branch1),
  8284. var_node_ptr_(0)
  8285. {
  8286. if (is_variable_node(binary_node<T>::branch_[0].first))
  8287. {
  8288. var_node_ptr_ = static_cast<variable_node<T>*>(binary_node<T>::branch_[0].first);
  8289. }
  8290. }
  8291. inline T value() const
  8292. {
  8293. if (var_node_ptr_)
  8294. {
  8295. T& v = var_node_ptr_->ref();
  8296. v = Operation::process(v,binary_node<T>::branch_[1].first->value());
  8297. return v;
  8298. }
  8299. else
  8300. return std::numeric_limits<T>::quiet_NaN();
  8301. }
  8302. private:
  8303. variable_node<T>* var_node_ptr_;
  8304. };
  8305. template <typename T, typename Operation>
  8306. class assignment_vec_elem_op_node : public binary_node<T>
  8307. {
  8308. public:
  8309. typedef expression_node<T>* expression_ptr;
  8310. assignment_vec_elem_op_node(const operator_type& opr,
  8311. expression_ptr branch0,
  8312. expression_ptr branch1)
  8313. : binary_node<T>(opr, branch0, branch1),
  8314. vec_node_ptr_(0)
  8315. {
  8316. if (is_vector_elem_node(binary_node<T>::branch_[0].first))
  8317. {
  8318. vec_node_ptr_ = static_cast<vector_elem_node<T>*>(binary_node<T>::branch_[0].first);
  8319. }
  8320. }
  8321. inline T value() const
  8322. {
  8323. if (vec_node_ptr_)
  8324. {
  8325. T& v = vec_node_ptr_->ref();
  8326. v = Operation::process(v,binary_node<T>::branch_[1].first->value());
  8327. return v;
  8328. }
  8329. else
  8330. return std::numeric_limits<T>::quiet_NaN();
  8331. }
  8332. private:
  8333. vector_elem_node<T>* vec_node_ptr_;
  8334. };
  8335. template <typename T, typename Operation>
  8336. class assignment_rebasevec_elem_op_node : public binary_node<T>
  8337. {
  8338. public:
  8339. typedef expression_node<T>* expression_ptr;
  8340. assignment_rebasevec_elem_op_node(const operator_type& opr,
  8341. expression_ptr branch0,
  8342. expression_ptr branch1)
  8343. : binary_node<T>(opr, branch0, branch1),
  8344. rbvec_node_ptr_(0)
  8345. {
  8346. if (is_rebasevector_elem_node(binary_node<T>::branch_[0].first))
  8347. {
  8348. rbvec_node_ptr_ = static_cast<rebasevector_elem_node<T>*>(binary_node<T>::branch_[0].first);
  8349. }
  8350. }
  8351. inline T value() const
  8352. {
  8353. if (rbvec_node_ptr_)
  8354. {
  8355. T& v = rbvec_node_ptr_->ref();
  8356. v = Operation::process(v,binary_node<T>::branch_[1].first->value());
  8357. return v;
  8358. }
  8359. else
  8360. return std::numeric_limits<T>::quiet_NaN();
  8361. }
  8362. private:
  8363. rebasevector_elem_node<T>* rbvec_node_ptr_;
  8364. };
  8365. template <typename T, typename Operation>
  8366. class assignment_rebasevec_celem_op_node : public binary_node<T>
  8367. {
  8368. public:
  8369. typedef expression_node<T>* expression_ptr;
  8370. assignment_rebasevec_celem_op_node(const operator_type& opr,
  8371. expression_ptr branch0,
  8372. expression_ptr branch1)
  8373. : binary_node<T>(opr, branch0, branch1),
  8374. rbvec_node_ptr_(0)
  8375. {
  8376. if (is_rebasevector_celem_node(binary_node<T>::branch_[0].first))
  8377. {
  8378. rbvec_node_ptr_ = static_cast<rebasevector_celem_node<T>*>(binary_node<T>::branch_[0].first);
  8379. }
  8380. }
  8381. inline T value() const
  8382. {
  8383. if (rbvec_node_ptr_)
  8384. {
  8385. T& v = rbvec_node_ptr_->ref();
  8386. v = Operation::process(v,binary_node<T>::branch_[1].first->value());
  8387. return v;
  8388. }
  8389. else
  8390. return std::numeric_limits<T>::quiet_NaN();
  8391. }
  8392. private:
  8393. rebasevector_celem_node<T>* rbvec_node_ptr_;
  8394. };
  8395. template <typename T, typename Operation>
  8396. class assignment_vec_op_node : public binary_node <T>,
  8397. public vector_interface<T>
  8398. {
  8399. public:
  8400. typedef expression_node<T>* expression_ptr;
  8401. typedef vector_node<T>* vector_node_ptr;
  8402. typedef vec_data_store<T> vds_t;
  8403. assignment_vec_op_node(const operator_type& opr,
  8404. expression_ptr branch0,
  8405. expression_ptr branch1)
  8406. : binary_node<T>(opr, branch0, branch1),
  8407. vec_node_ptr_(0)
  8408. {
  8409. if (is_vector_node(binary_node<T>::branch_[0].first))
  8410. {
  8411. vec_node_ptr_ = static_cast<vector_node<T>*>(binary_node<T>::branch_[0].first);
  8412. vds() = vec_node_ptr_->vds();
  8413. }
  8414. }
  8415. inline T value() const
  8416. {
  8417. if (vec_node_ptr_)
  8418. {
  8419. const T v = binary_node<T>::branch_[1].first->value();
  8420. T* vec = vds().data();
  8421. loop_unroll::details lud(size());
  8422. const T* upper_bound = vec + lud.upper_bound;
  8423. while (vec < upper_bound)
  8424. {
  8425. #define exprtk_loop(N) \
  8426. Operation::assign(vec[N],v); \
  8427. exprtk_loop( 0) exprtk_loop( 1)
  8428. exprtk_loop( 2) exprtk_loop( 3)
  8429. #ifndef exprtk_disable_superscalar_unroll
  8430. exprtk_loop( 4) exprtk_loop( 5)
  8431. exprtk_loop( 6) exprtk_loop( 7)
  8432. exprtk_loop( 8) exprtk_loop( 9)
  8433. exprtk_loop(10) exprtk_loop(11)
  8434. exprtk_loop(12) exprtk_loop(13)
  8435. exprtk_loop(14) exprtk_loop(15)
  8436. #endif
  8437. vec += lud.batch_size;
  8438. }
  8439. exprtk_disable_fallthrough_begin
  8440. switch (lud.remainder)
  8441. {
  8442. #define case_stmt(N) \
  8443. case N : Operation::assign(*vec++,v); \
  8444. #ifndef exprtk_disable_superscalar_unroll
  8445. case_stmt(15) case_stmt(14)
  8446. case_stmt(13) case_stmt(12)
  8447. case_stmt(11) case_stmt(10)
  8448. case_stmt( 9) case_stmt( 8)
  8449. case_stmt( 7) case_stmt( 6)
  8450. case_stmt( 5) case_stmt( 4)
  8451. #endif
  8452. case_stmt( 3) case_stmt( 2)
  8453. case_stmt( 1)
  8454. }
  8455. exprtk_disable_fallthrough_end
  8456. #undef exprtk_loop
  8457. #undef case_stmt
  8458. return vec_node_ptr_->value();
  8459. }
  8460. else
  8461. return std::numeric_limits<T>::quiet_NaN();
  8462. }
  8463. vector_node_ptr vec() const
  8464. {
  8465. return vec_node_ptr_;
  8466. }
  8467. vector_node_ptr vec()
  8468. {
  8469. return vec_node_ptr_;
  8470. }
  8471. inline typename expression_node<T>::node_type type() const
  8472. {
  8473. return expression_node<T>::e_vecopvalass;
  8474. }
  8475. std::size_t size() const
  8476. {
  8477. return vds().size();
  8478. }
  8479. vds_t& vds()
  8480. {
  8481. return vds_;
  8482. }
  8483. const vds_t& vds() const
  8484. {
  8485. return vds_;
  8486. }
  8487. bool side_effect() const
  8488. {
  8489. return true;
  8490. }
  8491. private:
  8492. vector_node<T>* vec_node_ptr_;
  8493. vds_t vds_;
  8494. };
  8495. template <typename T, typename Operation>
  8496. class assignment_vecvec_op_node : public binary_node <T>,
  8497. public vector_interface<T>
  8498. {
  8499. public:
  8500. typedef expression_node<T>* expression_ptr;
  8501. typedef vector_node<T>* vector_node_ptr;
  8502. typedef vec_data_store<T> vds_t;
  8503. assignment_vecvec_op_node(const operator_type& opr,
  8504. expression_ptr branch0,
  8505. expression_ptr branch1)
  8506. : binary_node<T>(opr, branch0, branch1),
  8507. vec0_node_ptr_(0),
  8508. vec1_node_ptr_(0),
  8509. initialised_(false)
  8510. {
  8511. if (is_vector_node(binary_node<T>::branch_[0].first))
  8512. {
  8513. vec0_node_ptr_ = static_cast<vector_node<T>*>(binary_node<T>::branch_[0].first);
  8514. vds() = vec0_node_ptr_->vds();
  8515. }
  8516. if (is_vector_node(binary_node<T>::branch_[1].first))
  8517. {
  8518. vec1_node_ptr_ = static_cast<vector_node<T>*>(binary_node<T>::branch_[1].first);
  8519. vec1_node_ptr_->vds() = vds();
  8520. }
  8521. else if (is_ivector_node(binary_node<T>::branch_[1].first))
  8522. {
  8523. vector_interface<T>* vi = reinterpret_cast<vector_interface<T>*>(0);
  8524. if (0 != (vi = dynamic_cast<vector_interface<T>*>(binary_node<T>::branch_[1].first)))
  8525. {
  8526. vec1_node_ptr_ = vi->vec();
  8527. vec1_node_ptr_->vds() = vds();
  8528. }
  8529. else
  8530. vds_t::match_sizes(vds(),vec1_node_ptr_->vds());
  8531. }
  8532. initialised_ = (vec0_node_ptr_ && vec1_node_ptr_);
  8533. }
  8534. inline T value() const
  8535. {
  8536. if (initialised_)
  8537. {
  8538. binary_node<T>::branch_[0].first->value();
  8539. binary_node<T>::branch_[1].first->value();
  8540. T* vec0 = vec0_node_ptr_->vds().data();
  8541. const T* vec1 = vec1_node_ptr_->vds().data();
  8542. loop_unroll::details lud(size());
  8543. const T* upper_bound = vec0 + lud.upper_bound;
  8544. while (vec0 < upper_bound)
  8545. {
  8546. #define exprtk_loop(N) \
  8547. vec0[N] = Operation::process(vec0[N], vec1[N]); \
  8548. exprtk_loop( 0) exprtk_loop( 1)
  8549. exprtk_loop( 2) exprtk_loop( 3)
  8550. #ifndef exprtk_disable_superscalar_unroll
  8551. exprtk_loop( 4) exprtk_loop( 5)
  8552. exprtk_loop( 6) exprtk_loop( 7)
  8553. exprtk_loop( 8) exprtk_loop( 9)
  8554. exprtk_loop(10) exprtk_loop(11)
  8555. exprtk_loop(12) exprtk_loop(13)
  8556. exprtk_loop(14) exprtk_loop(15)
  8557. #endif
  8558. vec0 += lud.batch_size;
  8559. vec1 += lud.batch_size;
  8560. }
  8561. int i = 0;
  8562. exprtk_disable_fallthrough_begin
  8563. switch (lud.remainder)
  8564. {
  8565. #define case_stmt(N) \
  8566. case N : { vec0[i] = Operation::process(vec0[i], vec1[i]); ++i; } \
  8567. #ifndef exprtk_disable_superscalar_unroll
  8568. case_stmt(15) case_stmt(14)
  8569. case_stmt(13) case_stmt(12)
  8570. case_stmt(11) case_stmt(10)
  8571. case_stmt( 9) case_stmt( 8)
  8572. case_stmt( 7) case_stmt( 6)
  8573. case_stmt( 5) case_stmt( 4)
  8574. #endif
  8575. case_stmt( 3) case_stmt( 2)
  8576. case_stmt( 1)
  8577. }
  8578. exprtk_disable_fallthrough_end
  8579. #undef exprtk_loop
  8580. #undef case_stmt
  8581. return vec0_node_ptr_->value();
  8582. }
  8583. else
  8584. return std::numeric_limits<T>::quiet_NaN();
  8585. }
  8586. vector_node_ptr vec() const
  8587. {
  8588. return vec0_node_ptr_;
  8589. }
  8590. vector_node_ptr vec()
  8591. {
  8592. return vec0_node_ptr_;
  8593. }
  8594. inline typename expression_node<T>::node_type type() const
  8595. {
  8596. return expression_node<T>::e_vecopvecass;
  8597. }
  8598. std::size_t size() const
  8599. {
  8600. return vds().size();
  8601. }
  8602. vds_t& vds()
  8603. {
  8604. return vds_;
  8605. }
  8606. const vds_t& vds() const
  8607. {
  8608. return vds_;
  8609. }
  8610. bool side_effect() const
  8611. {
  8612. return true;
  8613. }
  8614. private:
  8615. vector_node<T>* vec0_node_ptr_;
  8616. vector_node<T>* vec1_node_ptr_;
  8617. bool initialised_;
  8618. vds_t vds_;
  8619. };
  8620. template <typename T, typename Operation>
  8621. class vec_binop_vecvec_node : public binary_node <T>,
  8622. public vector_interface<T>
  8623. {
  8624. public:
  8625. typedef expression_node<T>* expression_ptr;
  8626. typedef vector_node<T>* vector_node_ptr;
  8627. typedef vector_holder<T>* vector_holder_ptr;
  8628. typedef vec_data_store<T> vds_t;
  8629. vec_binop_vecvec_node(const operator_type& opr,
  8630. expression_ptr branch0,
  8631. expression_ptr branch1)
  8632. : binary_node<T>(opr, branch0, branch1),
  8633. vec0_node_ptr_(0),
  8634. vec1_node_ptr_(0),
  8635. temp_ (0),
  8636. temp_vec_node_(0),
  8637. initialised_(false)
  8638. {
  8639. bool v0_is_ivec = false;
  8640. bool v1_is_ivec = false;
  8641. if (is_vector_node(binary_node<T>::branch_[0].first))
  8642. {
  8643. vec0_node_ptr_ = static_cast<vector_node_ptr>(binary_node<T>::branch_[0].first);
  8644. }
  8645. else if (is_ivector_node(binary_node<T>::branch_[0].first))
  8646. {
  8647. vector_interface<T>* vi = reinterpret_cast<vector_interface<T>*>(0);
  8648. if (0 != (vi = dynamic_cast<vector_interface<T>*>(binary_node<T>::branch_[0].first)))
  8649. {
  8650. vec0_node_ptr_ = vi->vec();
  8651. v0_is_ivec = true;
  8652. }
  8653. }
  8654. if (is_vector_node(binary_node<T>::branch_[1].first))
  8655. {
  8656. vec1_node_ptr_ = static_cast<vector_node_ptr>(binary_node<T>::branch_[1].first);
  8657. }
  8658. else if (is_ivector_node(binary_node<T>::branch_[1].first))
  8659. {
  8660. vector_interface<T>* vi = reinterpret_cast<vector_interface<T>*>(0);
  8661. if (0 != (vi = dynamic_cast<vector_interface<T>*>(binary_node<T>::branch_[1].first)))
  8662. {
  8663. vec1_node_ptr_ = vi->vec();
  8664. v1_is_ivec = true;
  8665. }
  8666. }
  8667. if (vec0_node_ptr_ && vec1_node_ptr_)
  8668. {
  8669. vector_holder<T>& vec0 = vec0_node_ptr_->vec_holder();
  8670. vector_holder<T>& vec1 = vec1_node_ptr_->vec_holder();
  8671. if (v0_is_ivec && (vec0.size() <= vec1.size()))
  8672. vds_ = vds_t(vec0_node_ptr_->vds());
  8673. else if (v1_is_ivec && (vec1.size() <= vec0.size()))
  8674. vds_ = vds_t(vec1_node_ptr_->vds());
  8675. else
  8676. vds_ = vds_t(std::min(vec0.size(),vec1.size()));
  8677. temp_ = new vector_holder<T>(vds().data(),vds().size());
  8678. temp_vec_node_ = new vector_node<T> (vds(),temp_);
  8679. initialised_ = true;
  8680. }
  8681. }
  8682. ~vec_binop_vecvec_node()
  8683. {
  8684. delete temp_;
  8685. delete temp_vec_node_;
  8686. }
  8687. inline T value() const
  8688. {
  8689. if (initialised_)
  8690. {
  8691. binary_node<T>::branch_[0].first->value();
  8692. binary_node<T>::branch_[1].first->value();
  8693. const T* vec0 = vec0_node_ptr_->vds().data();
  8694. const T* vec1 = vec1_node_ptr_->vds().data();
  8695. T* vec2 = vds().data();
  8696. loop_unroll::details lud(size());
  8697. const T* upper_bound = vec2 + lud.upper_bound;
  8698. while (vec2 < upper_bound)
  8699. {
  8700. #define exprtk_loop(N) \
  8701. vec2[N] = Operation::process(vec0[N], vec1[N]); \
  8702. exprtk_loop( 0) exprtk_loop( 1)
  8703. exprtk_loop( 2) exprtk_loop( 3)
  8704. #ifndef exprtk_disable_superscalar_unroll
  8705. exprtk_loop( 4) exprtk_loop( 5)
  8706. exprtk_loop( 6) exprtk_loop( 7)
  8707. exprtk_loop( 8) exprtk_loop( 9)
  8708. exprtk_loop(10) exprtk_loop(11)
  8709. exprtk_loop(12) exprtk_loop(13)
  8710. exprtk_loop(14) exprtk_loop(15)
  8711. #endif
  8712. vec0 += lud.batch_size;
  8713. vec1 += lud.batch_size;
  8714. vec2 += lud.batch_size;
  8715. }
  8716. int i = 0;
  8717. exprtk_disable_fallthrough_begin
  8718. switch (lud.remainder)
  8719. {
  8720. #define case_stmt(N) \
  8721. case N : { vec2[i] = Operation::process(vec0[i], vec1[i]); ++i; } \
  8722. #ifndef exprtk_disable_superscalar_unroll
  8723. case_stmt(15) case_stmt(14)
  8724. case_stmt(13) case_stmt(12)
  8725. case_stmt(11) case_stmt(10)
  8726. case_stmt( 9) case_stmt( 8)
  8727. case_stmt( 7) case_stmt( 6)
  8728. case_stmt( 5) case_stmt( 4)
  8729. #endif
  8730. case_stmt( 3) case_stmt( 2)
  8731. case_stmt( 1)
  8732. }
  8733. exprtk_disable_fallthrough_end
  8734. #undef exprtk_loop
  8735. #undef case_stmt
  8736. return (vds().data())[0];
  8737. }
  8738. else
  8739. return std::numeric_limits<T>::quiet_NaN();
  8740. }
  8741. vector_node_ptr vec() const
  8742. {
  8743. return temp_vec_node_;
  8744. }
  8745. vector_node_ptr vec()
  8746. {
  8747. return temp_vec_node_;
  8748. }
  8749. inline typename expression_node<T>::node_type type() const
  8750. {
  8751. return expression_node<T>::e_vecvecarith;
  8752. }
  8753. std::size_t size() const
  8754. {
  8755. return vds_.size();
  8756. }
  8757. vds_t& vds()
  8758. {
  8759. return vds_;
  8760. }
  8761. const vds_t& vds() const
  8762. {
  8763. return vds_;
  8764. }
  8765. private:
  8766. vector_node_ptr vec0_node_ptr_;
  8767. vector_node_ptr vec1_node_ptr_;
  8768. vector_holder_ptr temp_;
  8769. vector_node_ptr temp_vec_node_;
  8770. bool initialised_;
  8771. vds_t vds_;
  8772. };
  8773. template <typename T, typename Operation>
  8774. class vec_binop_vecval_node : public binary_node <T>,
  8775. public vector_interface<T>
  8776. {
  8777. public:
  8778. typedef expression_node<T>* expression_ptr;
  8779. typedef vector_node<T>* vector_node_ptr;
  8780. typedef vector_holder<T>* vector_holder_ptr;
  8781. typedef vec_data_store<T> vds_t;
  8782. vec_binop_vecval_node(const operator_type& opr,
  8783. expression_ptr branch0,
  8784. expression_ptr branch1)
  8785. : binary_node<T>(opr, branch0, branch1),
  8786. vec0_node_ptr_(0),
  8787. temp_ (0),
  8788. temp_vec_node_(0)
  8789. {
  8790. bool v0_is_ivec = false;
  8791. if (is_vector_node(binary_node<T>::branch_[0].first))
  8792. {
  8793. vec0_node_ptr_ = static_cast<vector_node_ptr>(binary_node<T>::branch_[0].first);
  8794. }
  8795. else if (is_ivector_node(binary_node<T>::branch_[0].first))
  8796. {
  8797. vector_interface<T>* vi = reinterpret_cast<vector_interface<T>*>(0);
  8798. if (0 != (vi = dynamic_cast<vector_interface<T>*>(binary_node<T>::branch_[0].first)))
  8799. {
  8800. vec0_node_ptr_ = vi->vec();
  8801. v0_is_ivec = true;
  8802. }
  8803. }
  8804. if (vec0_node_ptr_)
  8805. {
  8806. if (v0_is_ivec)
  8807. vds() = vec0_node_ptr_->vds();
  8808. else
  8809. vds() = vds_t(vec0_node_ptr_->size());
  8810. temp_ = new vector_holder<T>(vds());
  8811. temp_vec_node_ = new vector_node<T> (vds(),temp_);
  8812. }
  8813. }
  8814. ~vec_binop_vecval_node()
  8815. {
  8816. delete temp_;
  8817. delete temp_vec_node_;
  8818. }
  8819. inline T value() const
  8820. {
  8821. if (vec0_node_ptr_)
  8822. {
  8823. binary_node<T>::branch_[0].first->value();
  8824. const T v = binary_node<T>::branch_[1].first->value();
  8825. const T* vec0 = vec0_node_ptr_->vds().data();
  8826. T* vec1 = vds().data();
  8827. loop_unroll::details lud(size());
  8828. const T* upper_bound = vec0 + lud.upper_bound;
  8829. while (vec0 < upper_bound)
  8830. {
  8831. #define exprtk_loop(N) \
  8832. vec1[N] = Operation::process(vec0[N], v); \
  8833. exprtk_loop( 0) exprtk_loop( 1)
  8834. exprtk_loop( 2) exprtk_loop( 3)
  8835. #ifndef exprtk_disable_superscalar_unroll
  8836. exprtk_loop( 4) exprtk_loop( 5)
  8837. exprtk_loop( 6) exprtk_loop( 7)
  8838. exprtk_loop( 8) exprtk_loop( 9)
  8839. exprtk_loop(10) exprtk_loop(11)
  8840. exprtk_loop(12) exprtk_loop(13)
  8841. exprtk_loop(14) exprtk_loop(15)
  8842. #endif
  8843. vec0 += lud.batch_size;
  8844. vec1 += lud.batch_size;
  8845. }
  8846. int i = 0;
  8847. exprtk_disable_fallthrough_begin
  8848. switch (lud.remainder)
  8849. {
  8850. #define case_stmt(N) \
  8851. case N : { vec1[i] = Operation::process(vec0[i], v); ++i; } \
  8852. #ifndef exprtk_disable_superscalar_unroll
  8853. case_stmt(15) case_stmt(14)
  8854. case_stmt(13) case_stmt(12)
  8855. case_stmt(11) case_stmt(10)
  8856. case_stmt( 9) case_stmt( 8)
  8857. case_stmt( 7) case_stmt( 6)
  8858. case_stmt( 5) case_stmt( 4)
  8859. #endif
  8860. case_stmt( 3) case_stmt( 2)
  8861. case_stmt( 1)
  8862. }
  8863. exprtk_disable_fallthrough_end
  8864. #undef exprtk_loop
  8865. #undef case_stmt
  8866. return (vds().data())[0];
  8867. }
  8868. else
  8869. return std::numeric_limits<T>::quiet_NaN();
  8870. }
  8871. vector_node_ptr vec() const
  8872. {
  8873. return temp_vec_node_;
  8874. }
  8875. vector_node_ptr vec()
  8876. {
  8877. return temp_vec_node_;
  8878. }
  8879. inline typename expression_node<T>::node_type type() const
  8880. {
  8881. return expression_node<T>::e_vecvalarith;
  8882. }
  8883. std::size_t size() const
  8884. {
  8885. return vds().size();
  8886. }
  8887. vds_t& vds()
  8888. {
  8889. return vds_;
  8890. }
  8891. const vds_t& vds() const
  8892. {
  8893. return vds_;
  8894. }
  8895. private:
  8896. vector_node_ptr vec0_node_ptr_;
  8897. vector_holder_ptr temp_;
  8898. vector_node_ptr temp_vec_node_;
  8899. vds_t vds_;
  8900. };
  8901. template <typename T, typename Operation>
  8902. class vec_binop_valvec_node : public binary_node <T>,
  8903. public vector_interface<T>
  8904. {
  8905. public:
  8906. typedef expression_node<T>* expression_ptr;
  8907. typedef vector_node<T>* vector_node_ptr;
  8908. typedef vector_holder<T>* vector_holder_ptr;
  8909. typedef vec_data_store<T> vds_t;
  8910. vec_binop_valvec_node(const operator_type& opr,
  8911. expression_ptr branch0,
  8912. expression_ptr branch1)
  8913. : binary_node<T>(opr, branch0, branch1),
  8914. vec1_node_ptr_(0),
  8915. temp_ (0),
  8916. temp_vec_node_(0)
  8917. {
  8918. bool v1_is_ivec = false;
  8919. if (is_vector_node(binary_node<T>::branch_[1].first))
  8920. {
  8921. vec1_node_ptr_ = static_cast<vector_node_ptr>(binary_node<T>::branch_[1].first);
  8922. }
  8923. else if (is_ivector_node(binary_node<T>::branch_[1].first))
  8924. {
  8925. vector_interface<T>* vi = reinterpret_cast<vector_interface<T>*>(0);
  8926. if (0 != (vi = dynamic_cast<vector_interface<T>*>(binary_node<T>::branch_[1].first)))
  8927. {
  8928. vec1_node_ptr_ = vi->vec();
  8929. v1_is_ivec = true;
  8930. }
  8931. }
  8932. if (vec1_node_ptr_)
  8933. {
  8934. if (v1_is_ivec)
  8935. vds() = vec1_node_ptr_->vds();
  8936. else
  8937. vds() = vds_t(vec1_node_ptr_->size());
  8938. temp_ = new vector_holder<T>(vds());
  8939. temp_vec_node_ = new vector_node<T> (vds(),temp_);
  8940. }
  8941. }
  8942. ~vec_binop_valvec_node()
  8943. {
  8944. delete temp_;
  8945. delete temp_vec_node_;
  8946. }
  8947. inline T value() const
  8948. {
  8949. if (vec1_node_ptr_)
  8950. {
  8951. const T v = binary_node<T>::branch_[0].first->value();
  8952. binary_node<T>::branch_[1].first->value();
  8953. T* vec0 = vds().data();
  8954. const T* vec1 = vec1_node_ptr_->vds().data();
  8955. loop_unroll::details lud(size());
  8956. const T* upper_bound = vec0 + lud.upper_bound;
  8957. while (vec0 < upper_bound)
  8958. {
  8959. #define exprtk_loop(N) \
  8960. vec0[N] = Operation::process(v, vec1[N]); \
  8961. exprtk_loop( 0) exprtk_loop( 1)
  8962. exprtk_loop( 2) exprtk_loop( 3)
  8963. #ifndef exprtk_disable_superscalar_unroll
  8964. exprtk_loop( 4) exprtk_loop( 5)
  8965. exprtk_loop( 6) exprtk_loop( 7)
  8966. exprtk_loop( 8) exprtk_loop( 9)
  8967. exprtk_loop(10) exprtk_loop(11)
  8968. exprtk_loop(12) exprtk_loop(13)
  8969. exprtk_loop(14) exprtk_loop(15)
  8970. #endif
  8971. vec0 += lud.batch_size;
  8972. vec1 += lud.batch_size;
  8973. }
  8974. int i = 0;
  8975. exprtk_disable_fallthrough_begin
  8976. switch (lud.remainder)
  8977. {
  8978. #define case_stmt(N) \
  8979. case N : { vec0[i] = Operation::process(v, vec1[i]); ++i; } \
  8980. #ifndef exprtk_disable_superscalar_unroll
  8981. case_stmt(15) case_stmt(14)
  8982. case_stmt(13) case_stmt(12)
  8983. case_stmt(11) case_stmt(10)
  8984. case_stmt( 9) case_stmt( 8)
  8985. case_stmt( 7) case_stmt( 6)
  8986. case_stmt( 5) case_stmt( 4)
  8987. #endif
  8988. case_stmt( 3) case_stmt( 2)
  8989. case_stmt( 1)
  8990. }
  8991. exprtk_disable_fallthrough_end
  8992. #undef exprtk_loop
  8993. #undef case_stmt
  8994. return (vds().data())[0];
  8995. }
  8996. else
  8997. return std::numeric_limits<T>::quiet_NaN();
  8998. }
  8999. vector_node_ptr vec() const
  9000. {
  9001. return temp_vec_node_;
  9002. }
  9003. vector_node_ptr vec()
  9004. {
  9005. return temp_vec_node_;
  9006. }
  9007. inline typename expression_node<T>::node_type type() const
  9008. {
  9009. return expression_node<T>::e_vecvalarith;
  9010. }
  9011. std::size_t size() const
  9012. {
  9013. return vds().size();
  9014. }
  9015. vds_t& vds()
  9016. {
  9017. return vds_;
  9018. }
  9019. const vds_t& vds() const
  9020. {
  9021. return vds_;
  9022. }
  9023. private:
  9024. vector_node_ptr vec1_node_ptr_;
  9025. vector_holder_ptr temp_;
  9026. vector_node_ptr temp_vec_node_;
  9027. vds_t vds_;
  9028. };
  9029. template <typename T, typename Operation>
  9030. class unary_vector_node : public unary_node <T>,
  9031. public vector_interface<T>
  9032. {
  9033. public:
  9034. typedef expression_node<T>* expression_ptr;
  9035. typedef vector_node<T>* vector_node_ptr;
  9036. typedef vector_holder<T>* vector_holder_ptr;
  9037. typedef vec_data_store<T> vds_t;
  9038. unary_vector_node(const operator_type& opr, expression_ptr branch0)
  9039. : unary_node<T>(opr, branch0),
  9040. vec0_node_ptr_(0),
  9041. temp_ (0),
  9042. temp_vec_node_(0)
  9043. {
  9044. bool vec0_is_ivec = false;
  9045. if (is_vector_node(unary_node<T>::branch_))
  9046. {
  9047. vec0_node_ptr_ = static_cast<vector_node_ptr>(unary_node<T>::branch_);
  9048. }
  9049. else if (is_ivector_node(unary_node<T>::branch_))
  9050. {
  9051. vector_interface<T>* vi = reinterpret_cast<vector_interface<T>*>(0);
  9052. if (0 != (vi = dynamic_cast<vector_interface<T>*>(unary_node<T>::branch_)))
  9053. {
  9054. vec0_node_ptr_ = vi->vec();
  9055. vec0_is_ivec = true;
  9056. }
  9057. }
  9058. if (vec0_node_ptr_)
  9059. {
  9060. if (vec0_is_ivec)
  9061. vds_ = vec0_node_ptr_->vds();
  9062. else
  9063. vds_ = vds_t(vec0_node_ptr_->size());
  9064. temp_ = new vector_holder<T>(vds());
  9065. temp_vec_node_ = new vector_node<T> (vds(),temp_);
  9066. }
  9067. }
  9068. ~unary_vector_node()
  9069. {
  9070. delete temp_;
  9071. delete temp_vec_node_;
  9072. }
  9073. inline T value() const
  9074. {
  9075. unary_node<T>::branch_->value();
  9076. if (vec0_node_ptr_)
  9077. {
  9078. const T* vec0 = vec0_node_ptr_->vds().data();
  9079. T* vec1 = vds().data();
  9080. loop_unroll::details lud(size());
  9081. const T* upper_bound = vec0 + lud.upper_bound;
  9082. while (vec0 < upper_bound)
  9083. {
  9084. #define exprtk_loop(N) \
  9085. vec1[N] = Operation::process(vec0[N]); \
  9086. exprtk_loop( 0) exprtk_loop( 1)
  9087. exprtk_loop( 2) exprtk_loop( 3)
  9088. #ifndef exprtk_disable_superscalar_unroll
  9089. exprtk_loop( 4) exprtk_loop( 5)
  9090. exprtk_loop( 6) exprtk_loop( 7)
  9091. exprtk_loop( 8) exprtk_loop( 9)
  9092. exprtk_loop(10) exprtk_loop(11)
  9093. exprtk_loop(12) exprtk_loop(13)
  9094. exprtk_loop(14) exprtk_loop(15)
  9095. #endif
  9096. vec0 += lud.batch_size;
  9097. vec1 += lud.batch_size;
  9098. }
  9099. int i = 0;
  9100. exprtk_disable_fallthrough_begin
  9101. switch (lud.remainder)
  9102. {
  9103. #define case_stmt(N) \
  9104. case N : { vec1[i] = Operation::process(vec0[i]); ++i; } \
  9105. #ifndef exprtk_disable_superscalar_unroll
  9106. case_stmt(15) case_stmt(14)
  9107. case_stmt(13) case_stmt(12)
  9108. case_stmt(11) case_stmt(10)
  9109. case_stmt( 9) case_stmt( 8)
  9110. case_stmt( 7) case_stmt( 6)
  9111. case_stmt( 5) case_stmt( 4)
  9112. #endif
  9113. case_stmt( 3) case_stmt( 2)
  9114. case_stmt( 1)
  9115. }
  9116. exprtk_disable_fallthrough_end
  9117. #undef exprtk_loop
  9118. #undef case_stmt
  9119. return (vds().data())[0];
  9120. }
  9121. else
  9122. return std::numeric_limits<T>::quiet_NaN();
  9123. }
  9124. vector_node_ptr vec() const
  9125. {
  9126. return temp_vec_node_;
  9127. }
  9128. vector_node_ptr vec()
  9129. {
  9130. return temp_vec_node_;
  9131. }
  9132. inline typename expression_node<T>::node_type type() const
  9133. {
  9134. return expression_node<T>::e_vecunaryop;
  9135. }
  9136. std::size_t size() const
  9137. {
  9138. return vds().size();
  9139. }
  9140. vds_t& vds()
  9141. {
  9142. return vds_;
  9143. }
  9144. const vds_t& vds() const
  9145. {
  9146. return vds_;
  9147. }
  9148. private:
  9149. vector_node_ptr vec0_node_ptr_;
  9150. vector_holder_ptr temp_;
  9151. vector_node_ptr temp_vec_node_;
  9152. vds_t vds_;
  9153. };
  9154. template <typename T>
  9155. class scand_node : public binary_node<T>
  9156. {
  9157. public:
  9158. typedef expression_node<T>* expression_ptr;
  9159. scand_node(const operator_type& opr,
  9160. expression_ptr branch0,
  9161. expression_ptr branch1)
  9162. : binary_node<T>(opr, branch0, branch1)
  9163. {}
  9164. inline T value() const
  9165. {
  9166. return (
  9167. std::not_equal_to<T>()
  9168. (T(0),binary_node<T>::branch_[0].first->value()) &&
  9169. std::not_equal_to<T>()
  9170. (T(0),binary_node<T>::branch_[1].first->value())
  9171. ) ? T(1) : T(0);
  9172. }
  9173. };
  9174. template <typename T>
  9175. class scor_node : public binary_node<T>
  9176. {
  9177. public:
  9178. typedef expression_node<T>* expression_ptr;
  9179. scor_node(const operator_type& opr,
  9180. expression_ptr branch0,
  9181. expression_ptr branch1)
  9182. : binary_node<T>(opr, branch0, branch1)
  9183. {}
  9184. inline T value() const
  9185. {
  9186. return (
  9187. std::not_equal_to<T>()
  9188. (T(0),binary_node<T>::branch_[0].first->value()) ||
  9189. std::not_equal_to<T>()
  9190. (T(0),binary_node<T>::branch_[1].first->value())
  9191. ) ? T(1) : T(0);
  9192. }
  9193. };
  9194. template <typename T, typename IFunction, std::size_t N>
  9195. class function_N_node : public expression_node<T>
  9196. {
  9197. public:
  9198. // Function of N paramters.
  9199. typedef expression_node<T>* expression_ptr;
  9200. typedef std::pair<expression_ptr,bool> branch_t;
  9201. typedef IFunction ifunction;
  9202. explicit function_N_node(ifunction* func)
  9203. : function_((N == func->param_count) ? func : reinterpret_cast<ifunction*>(0)),
  9204. parameter_count_(func->param_count)
  9205. {}
  9206. ~function_N_node()
  9207. {
  9208. cleanup_branches::execute<T,N>(branch_);
  9209. }
  9210. template <std::size_t NumBranches>
  9211. bool init_branches(expression_ptr (&b)[NumBranches])
  9212. {
  9213. // Needed for incompetent and broken msvc compiler versions
  9214. #ifdef _MSC_VER
  9215. #pragma warning(push)
  9216. #pragma warning(disable: 4127)
  9217. #endif
  9218. if (N != NumBranches)
  9219. return false;
  9220. else
  9221. {
  9222. for (std::size_t i = 0; i < NumBranches; ++i)
  9223. {
  9224. if (b[i])
  9225. branch_[i] = std::make_pair(b[i],branch_deletable(b[i]));
  9226. else
  9227. return false;
  9228. }
  9229. return true;
  9230. }
  9231. #ifdef _MSC_VER
  9232. #pragma warning(pop)
  9233. #endif
  9234. }
  9235. inline bool operator <(const function_N_node<T,IFunction,N>& fn) const
  9236. {
  9237. return this < (&fn);
  9238. }
  9239. inline T value() const
  9240. {
  9241. // Needed for incompetent and broken msvc compiler versions
  9242. #ifdef _MSC_VER
  9243. #pragma warning(push)
  9244. #pragma warning(disable: 4127)
  9245. #endif
  9246. if ((0 == function_) || (0 == N))
  9247. return std::numeric_limits<T>::quiet_NaN();
  9248. else
  9249. {
  9250. T v[N];
  9251. evaluate_branches<T,N>::execute(v,branch_);
  9252. return invoke<T,N>::execute(*function_,v);
  9253. }
  9254. #ifdef _MSC_VER
  9255. #pragma warning(pop)
  9256. #endif
  9257. }
  9258. template <typename T_, std::size_t BranchCount>
  9259. struct evaluate_branches
  9260. {
  9261. static inline void execute(T_ (&v)[BranchCount], const branch_t (&b)[BranchCount])
  9262. {
  9263. for (std::size_t i = 0; i < BranchCount; ++i)
  9264. {
  9265. v[i] = b[i].first->value();
  9266. }
  9267. }
  9268. };
  9269. template <typename T_>
  9270. struct evaluate_branches <T_,5>
  9271. {
  9272. static inline void execute(T_ (&v)[5], const branch_t (&b)[5])
  9273. {
  9274. v[0] = b[0].first->value();
  9275. v[1] = b[1].first->value();
  9276. v[2] = b[2].first->value();
  9277. v[3] = b[3].first->value();
  9278. v[4] = b[4].first->value();
  9279. }
  9280. };
  9281. template <typename T_>
  9282. struct evaluate_branches <T_,4>
  9283. {
  9284. static inline void execute(T_ (&v)[4], const branch_t (&b)[4])
  9285. {
  9286. v[0] = b[0].first->value();
  9287. v[1] = b[1].first->value();
  9288. v[2] = b[2].first->value();
  9289. v[3] = b[3].first->value();
  9290. }
  9291. };
  9292. template <typename T_>
  9293. struct evaluate_branches <T_,3>
  9294. {
  9295. static inline void execute(T_ (&v)[3], const branch_t (&b)[3])
  9296. {
  9297. v[0] = b[0].first->value();
  9298. v[1] = b[1].first->value();
  9299. v[2] = b[2].first->value();
  9300. }
  9301. };
  9302. template <typename T_>
  9303. struct evaluate_branches <T_,2>
  9304. {
  9305. static inline void execute(T_ (&v)[2], const branch_t (&b)[2])
  9306. {
  9307. v[0] = b[0].first->value();
  9308. v[1] = b[1].first->value();
  9309. }
  9310. };
  9311. template <typename T_>
  9312. struct evaluate_branches <T_,1>
  9313. {
  9314. static inline void execute(T_ (&v)[1], const branch_t (&b)[1])
  9315. {
  9316. v[0] = b[0].first->value();
  9317. }
  9318. };
  9319. template <typename T_, std::size_t ParamCount>
  9320. struct invoke { static inline T execute(ifunction&, branch_t (&)[ParamCount]) { return std::numeric_limits<T_>::quiet_NaN(); } };
  9321. template <typename T_>
  9322. struct invoke<T_,20>
  9323. {
  9324. static inline T_ execute(ifunction& f, T_ (&v)[20])
  9325. { return f(v[0],v[1],v[2],v[3],v[4],v[5],v[6],v[7],v[8],v[9],v[10],v[11],v[12],v[13],v[14],v[15],v[16],v[17],v[18],v[19]); }
  9326. };
  9327. template <typename T_>
  9328. struct invoke<T_,19>
  9329. {
  9330. static inline T_ execute(ifunction& f, T_ (&v)[19])
  9331. { return f(v[0],v[1],v[2],v[3],v[4],v[5],v[6],v[7],v[8],v[9],v[10],v[11],v[12],v[13],v[14],v[15],v[16],v[17],v[18]); }
  9332. };
  9333. template <typename T_>
  9334. struct invoke<T_,18>
  9335. {
  9336. static inline T_ execute(ifunction& f, T_ (&v)[18])
  9337. { return f(v[0],v[1],v[2],v[3],v[4],v[5],v[6],v[7],v[8],v[9],v[10],v[11],v[12],v[13],v[14],v[15],v[16],v[17]); }
  9338. };
  9339. template <typename T_>
  9340. struct invoke<T_,17>
  9341. {
  9342. static inline T_ execute(ifunction& f, T_ (&v)[17])
  9343. { return f(v[0],v[1],v[2],v[3],v[4],v[5],v[6],v[7],v[8],v[9],v[10],v[11],v[12],v[13],v[14],v[15],v[16]); }
  9344. };
  9345. template <typename T_>
  9346. struct invoke<T_,16>
  9347. {
  9348. static inline T_ execute(ifunction& f, T_ (&v)[16])
  9349. { return f(v[0],v[1],v[2],v[3],v[4],v[5],v[6],v[7],v[8],v[9],v[10],v[11],v[12],v[13],v[14],v[15]); }
  9350. };
  9351. template <typename T_>
  9352. struct invoke<T_,15>
  9353. {
  9354. static inline T_ execute(ifunction& f, T_ (&v)[15])
  9355. { return f(v[0],v[1],v[2],v[3],v[4],v[5],v[6],v[7],v[8],v[9],v[10],v[11],v[12],v[13],v[14]); }
  9356. };
  9357. template <typename T_>
  9358. struct invoke<T_,14>
  9359. {
  9360. static inline T_ execute(ifunction& f, T_ (&v)[14])
  9361. { return f(v[0],v[1],v[2],v[3],v[4],v[5],v[6],v[7],v[8],v[9],v[10],v[11],v[12],v[13]); }
  9362. };
  9363. template <typename T_>
  9364. struct invoke<T_,13>
  9365. {
  9366. static inline T_ execute(ifunction& f, T_ (&v)[13])
  9367. { return f(v[0],v[1],v[2],v[3],v[4],v[5],v[6],v[7],v[8],v[9],v[10],v[11],v[12]); }
  9368. };
  9369. template <typename T_>
  9370. struct invoke<T_,12>
  9371. {
  9372. static inline T_ execute(ifunction& f, T_ (&v)[12])
  9373. { return f(v[0],v[1],v[2],v[3],v[4],v[5],v[6],v[7],v[8],v[9],v[10],v[11]); }
  9374. };
  9375. template <typename T_>
  9376. struct invoke<T_,11>
  9377. {
  9378. static inline T_ execute(ifunction& f, T_ (&v)[11])
  9379. { return f(v[0],v[1],v[2],v[3],v[4],v[5],v[6],v[7],v[8],v[9],v[10]); }
  9380. };
  9381. template <typename T_>
  9382. struct invoke<T_,10>
  9383. {
  9384. static inline T_ execute(ifunction& f, T_ (&v)[10])
  9385. { return f(v[0],v[1],v[2],v[3],v[4],v[5],v[6],v[7],v[8],v[9]); }
  9386. };
  9387. template <typename T_>
  9388. struct invoke<T_,9>
  9389. {
  9390. static inline T_ execute(ifunction& f, T_ (&v)[9])
  9391. { return f(v[0],v[1],v[2],v[3],v[4],v[5],v[6],v[7],v[8]); }
  9392. };
  9393. template <typename T_>
  9394. struct invoke<T_,8>
  9395. {
  9396. static inline T_ execute(ifunction& f, T_ (&v)[8])
  9397. { return f(v[0],v[1],v[2],v[3],v[4],v[5],v[6],v[7]); }
  9398. };
  9399. template <typename T_>
  9400. struct invoke<T_,7>
  9401. {
  9402. static inline T_ execute(ifunction& f, T_ (&v)[7])
  9403. { return f(v[0],v[1],v[2],v[3],v[4],v[5],v[6]); }
  9404. };
  9405. template <typename T_>
  9406. struct invoke<T_,6>
  9407. {
  9408. static inline T_ execute(ifunction& f, T_ (&v)[6])
  9409. { return f(v[0],v[1],v[2],v[3],v[4],v[5]); }
  9410. };
  9411. template <typename T_>
  9412. struct invoke<T_,5>
  9413. {
  9414. static inline T_ execute(ifunction& f, T_ (&v)[5])
  9415. { return f(v[0],v[1],v[2],v[3],v[4]); }
  9416. };
  9417. template <typename T_>
  9418. struct invoke<T_,4>
  9419. {
  9420. static inline T_ execute(ifunction& f, T_ (&v)[4])
  9421. { return f(v[0],v[1],v[2],v[3]); }
  9422. };
  9423. template <typename T_>
  9424. struct invoke<T_,3>
  9425. {
  9426. static inline T_ execute(ifunction& f, T_ (&v)[3])
  9427. { return f(v[0],v[1],v[2]); }
  9428. };
  9429. template <typename T_>
  9430. struct invoke<T_,2>
  9431. {
  9432. static inline T_ execute(ifunction& f, T_ (&v)[2])
  9433. { return f(v[0],v[1]); }
  9434. };
  9435. template <typename T_>
  9436. struct invoke<T_,1>
  9437. {
  9438. static inline T_ execute(ifunction& f, T_ (&v)[1])
  9439. { return f(v[0]); }
  9440. };
  9441. inline typename expression_node<T>::node_type type() const
  9442. {
  9443. return expression_node<T>::e_function;
  9444. }
  9445. private:
  9446. ifunction* function_;
  9447. std::size_t parameter_count_;
  9448. branch_t branch_[N];
  9449. };
  9450. template <typename T, typename IFunction>
  9451. class function_N_node<T,IFunction,0> : public expression_node<T>
  9452. {
  9453. public:
  9454. typedef expression_node<T>* expression_ptr;
  9455. typedef IFunction ifunction;
  9456. explicit function_N_node(ifunction* func)
  9457. : function_((0 == func->param_count) ? func : reinterpret_cast<ifunction*>(0))
  9458. {}
  9459. inline bool operator <(const function_N_node<T,IFunction,0>& fn) const
  9460. {
  9461. return this < (&fn);
  9462. }
  9463. inline T value() const
  9464. {
  9465. if (function_)
  9466. return (*function_)();
  9467. else
  9468. return std::numeric_limits<T>::quiet_NaN();
  9469. }
  9470. inline typename expression_node<T>::node_type type() const
  9471. {
  9472. return expression_node<T>::e_function;
  9473. }
  9474. private:
  9475. ifunction* function_;
  9476. };
  9477. template <typename T, typename VarArgFunction>
  9478. class vararg_function_node : public expression_node<T>
  9479. {
  9480. public:
  9481. typedef expression_node<T>* expression_ptr;
  9482. vararg_function_node(VarArgFunction* func,
  9483. const std::vector<expression_ptr>& arg_list)
  9484. : function_(func),
  9485. arg_list_(arg_list)
  9486. {
  9487. value_list_.resize(arg_list.size(),std::numeric_limits<T>::quiet_NaN());
  9488. }
  9489. ~vararg_function_node()
  9490. {
  9491. for (std::size_t i = 0; i < arg_list_.size(); ++i)
  9492. {
  9493. if (arg_list_[i] && !details::is_variable_node(arg_list_[i]))
  9494. {
  9495. destroy_node(arg_list_[i]);
  9496. }
  9497. }
  9498. }
  9499. inline bool operator <(const vararg_function_node<T,VarArgFunction>& fn) const
  9500. {
  9501. return this < (&fn);
  9502. }
  9503. inline T value() const
  9504. {
  9505. if (function_)
  9506. {
  9507. populate_value_list();
  9508. return (*function_)(value_list_);
  9509. }
  9510. else
  9511. return std::numeric_limits<T>::quiet_NaN();
  9512. }
  9513. inline typename expression_node<T>::node_type type() const
  9514. {
  9515. return expression_node<T>::e_vafunction;
  9516. }
  9517. private:
  9518. inline void populate_value_list() const
  9519. {
  9520. for (std::size_t i = 0; i < arg_list_.size(); ++i)
  9521. {
  9522. value_list_[i] = arg_list_[i]->value();
  9523. }
  9524. }
  9525. VarArgFunction* function_;
  9526. std::vector<expression_ptr> arg_list_;
  9527. mutable std::vector<T> value_list_;
  9528. };
  9529. template <typename T, typename GenericFunction>
  9530. class generic_function_node : public expression_node<T>
  9531. {
  9532. public:
  9533. typedef type_store<T> type_store_t;
  9534. typedef expression_node<T>* expression_ptr;
  9535. typedef variable_node<T> variable_node_t;
  9536. typedef vector_node<T> vector_node_t;
  9537. typedef variable_node_t* variable_node_ptr_t;
  9538. typedef vector_node_t* vector_node_ptr_t;
  9539. typedef range_interface<T> range_interface_t;
  9540. typedef range_data_type<T> range_data_type_t;
  9541. typedef range_pack<T> range_t;
  9542. typedef std::pair<expression_ptr,bool> branch_t;
  9543. typedef std::pair<void*,std::size_t> void_t;
  9544. typedef std::vector<T> tmp_vs_t;
  9545. typedef std::vector<type_store_t> typestore_list_t;
  9546. typedef std::vector<range_data_type_t> range_list_t;
  9547. generic_function_node(const std::vector<expression_ptr>& arg_list,
  9548. GenericFunction* func = (GenericFunction*)(0))
  9549. : function_(func),
  9550. arg_list_(arg_list)
  9551. {}
  9552. virtual ~generic_function_node()
  9553. {
  9554. cleanup_branches::execute(branch_);
  9555. }
  9556. virtual bool init_branches()
  9557. {
  9558. expr_as_vec1_store_.resize(arg_list_.size(),T(0) );
  9559. typestore_list_ .resize(arg_list_.size(),type_store_t() );
  9560. range_list_ .resize(arg_list_.size(),range_data_type_t());
  9561. branch_ .resize(arg_list_.size(),branch_t((expression_ptr)0,false));
  9562. for (std::size_t i = 0; i < arg_list_.size(); ++i)
  9563. {
  9564. type_store_t& ts = typestore_list_[i];
  9565. if (0 == arg_list_[i])
  9566. return false;
  9567. else if (is_ivector_node(arg_list_[i]))
  9568. {
  9569. vector_interface<T>* vi = reinterpret_cast<vector_interface<T>*>(0);
  9570. if (0 == (vi = dynamic_cast<vector_interface<T>*>(arg_list_[i])))
  9571. return false;
  9572. ts.size = vi->size();
  9573. ts.data = vi->vds().data();
  9574. ts.type = type_store_t::e_vector;
  9575. vi->vec()->vec_holder().set_ref(&ts.vec_data);
  9576. }
  9577. #ifndef exprtk_disable_string_capabilities
  9578. else if (is_generally_string_node(arg_list_[i]))
  9579. {
  9580. string_base_node<T>* sbn = reinterpret_cast<string_base_node<T>*>(0);
  9581. if (0 == (sbn = dynamic_cast<string_base_node<T>*>(arg_list_[i])))
  9582. return false;
  9583. ts.size = sbn->size();
  9584. ts.data = reinterpret_cast<void*>(const_cast<char_ptr>(sbn->base()));
  9585. ts.type = type_store_t::e_string;
  9586. range_list_[i].data = ts.data;
  9587. range_list_[i].size = ts.size;
  9588. range_list_[i].type_size = sizeof(char);
  9589. range_list_[i].str_node = sbn;
  9590. range_interface_t* ri = reinterpret_cast<range_interface_t*>(0);
  9591. if (0 == (ri = dynamic_cast<range_interface_t*>(arg_list_[i])))
  9592. return false;
  9593. range_t& rp = ri->range_ref();
  9594. if (
  9595. rp.const_range() &&
  9596. is_const_string_range_node(arg_list_[i])
  9597. )
  9598. {
  9599. ts.size = rp.const_size();
  9600. ts.data = static_cast<char_ptr>(ts.data) + rp.n0_c.second;
  9601. range_list_[i].range = reinterpret_cast<range_t*>(0);
  9602. }
  9603. else
  9604. range_list_[i].range = &(ri->range_ref());
  9605. }
  9606. #endif
  9607. else if (is_variable_node(arg_list_[i]))
  9608. {
  9609. variable_node_ptr_t var = variable_node_ptr_t(0);
  9610. if (0 == (var = dynamic_cast<variable_node_ptr_t>(arg_list_[i])))
  9611. return false;
  9612. ts.size = 1;
  9613. ts.data = &var->ref();
  9614. ts.type = type_store_t::e_scalar;
  9615. }
  9616. else
  9617. {
  9618. ts.size = 1;
  9619. ts.data = reinterpret_cast<void*>(&expr_as_vec1_store_[i]);
  9620. ts.type = type_store_t::e_scalar;
  9621. }
  9622. branch_[i] = std::make_pair(arg_list_[i],branch_deletable(arg_list_[i]));
  9623. }
  9624. return true;
  9625. }
  9626. inline bool operator <(const generic_function_node<T,GenericFunction>& fn) const
  9627. {
  9628. return this < (&fn);
  9629. }
  9630. inline T value() const
  9631. {
  9632. if (function_)
  9633. {
  9634. if (populate_value_list())
  9635. {
  9636. typedef typename GenericFunction::parameter_list_t parameter_list_t;
  9637. return (*function_)(parameter_list_t(typestore_list_));
  9638. }
  9639. }
  9640. return std::numeric_limits<T>::quiet_NaN();
  9641. }
  9642. inline typename expression_node<T>::node_type type() const
  9643. {
  9644. return expression_node<T>::e_genfunction;
  9645. }
  9646. protected:
  9647. inline virtual bool populate_value_list() const
  9648. {
  9649. for (std::size_t i = 0; i < branch_.size(); ++i)
  9650. {
  9651. expr_as_vec1_store_[i] = branch_[i].first->value();
  9652. }
  9653. for (std::size_t i = 0; i < branch_.size(); ++i)
  9654. {
  9655. range_data_type_t& rdt = range_list_[i];
  9656. if (rdt.range)
  9657. {
  9658. range_t& rp = (*rdt.range);
  9659. std::size_t r0 = 0;
  9660. std::size_t r1 = 0;
  9661. if (rp(r0,r1,rdt.size))
  9662. {
  9663. type_store_t& ts = typestore_list_[i];
  9664. ts.size = rp.cache_size();
  9665. #ifndef exprtk_disable_string_capabilities
  9666. if (ts.type == type_store_t::e_string)
  9667. ts.data = const_cast<char_ptr>(rdt.str_node->base()) + rp.cache.first;
  9668. else
  9669. #endif
  9670. ts.data = static_cast<char_ptr>(rdt.data) + (rp.cache.first * rdt.type_size);
  9671. }
  9672. else
  9673. return false;
  9674. }
  9675. }
  9676. return true;
  9677. }
  9678. GenericFunction* function_;
  9679. mutable typestore_list_t typestore_list_;
  9680. private:
  9681. std::vector<expression_ptr> arg_list_;
  9682. std::vector<branch_t> branch_;
  9683. mutable tmp_vs_t expr_as_vec1_store_;
  9684. mutable range_list_t range_list_;
  9685. };
  9686. #ifndef exprtk_disable_string_capabilities
  9687. template <typename T, typename StringFunction>
  9688. class string_function_node : public generic_function_node<T,StringFunction>,
  9689. public string_base_node<T>,
  9690. public range_interface <T>
  9691. {
  9692. public:
  9693. typedef generic_function_node<T,StringFunction> gen_function_t;
  9694. typedef range_pack<T> range_t;
  9695. string_function_node(StringFunction* func,
  9696. const std::vector<typename gen_function_t::expression_ptr>& arg_list)
  9697. : gen_function_t(arg_list,func)
  9698. {
  9699. range_.n0_c = std::make_pair<bool,std::size_t>(true,0);
  9700. range_.n1_c = std::make_pair<bool,std::size_t>(true,0);
  9701. range_.cache.first = range_.n0_c.second;
  9702. range_.cache.second = range_.n1_c.second;
  9703. }
  9704. inline bool operator <(const string_function_node<T,StringFunction>& fn) const
  9705. {
  9706. return this < (&fn);
  9707. }
  9708. inline T value() const
  9709. {
  9710. if (gen_function_t::function_)
  9711. {
  9712. if (gen_function_t::populate_value_list())
  9713. {
  9714. typedef typename StringFunction::parameter_list_t parameter_list_t;
  9715. const T result = (*gen_function_t::function_)
  9716. (
  9717. ret_string_,
  9718. parameter_list_t(gen_function_t::typestore_list_)
  9719. );
  9720. range_.n1_c.second = ret_string_.size() - 1;
  9721. range_.cache.second = range_.n1_c.second;
  9722. return result;
  9723. }
  9724. }
  9725. return std::numeric_limits<T>::quiet_NaN();
  9726. }
  9727. inline typename expression_node<T>::node_type type() const
  9728. {
  9729. return expression_node<T>::e_strfunction;
  9730. }
  9731. std::string str() const
  9732. {
  9733. return ret_string_;
  9734. }
  9735. char_cptr base() const
  9736. {
  9737. return &ret_string_[0];
  9738. }
  9739. std::size_t size() const
  9740. {
  9741. return ret_string_.size();
  9742. }
  9743. range_t& range_ref()
  9744. {
  9745. return range_;
  9746. }
  9747. const range_t& range_ref() const
  9748. {
  9749. return range_;
  9750. }
  9751. protected:
  9752. mutable range_t range_;
  9753. mutable std::string ret_string_;
  9754. };
  9755. #endif
  9756. template <typename T, typename GenericFunction>
  9757. class multimode_genfunction_node : public generic_function_node<T,GenericFunction>
  9758. {
  9759. public:
  9760. typedef generic_function_node<T,GenericFunction> gen_function_t;
  9761. typedef range_pack<T> range_t;
  9762. multimode_genfunction_node(GenericFunction* func,
  9763. const std::size_t& param_seq_index,
  9764. const std::vector<typename gen_function_t::expression_ptr>& arg_list)
  9765. : gen_function_t(arg_list,func),
  9766. param_seq_index_(param_seq_index)
  9767. {}
  9768. inline T value() const
  9769. {
  9770. if (gen_function_t::function_)
  9771. {
  9772. if (gen_function_t::populate_value_list())
  9773. {
  9774. typedef typename GenericFunction::parameter_list_t parameter_list_t;
  9775. return (*gen_function_t::function_)
  9776. (
  9777. param_seq_index_,
  9778. parameter_list_t(gen_function_t::typestore_list_)
  9779. );
  9780. }
  9781. }
  9782. return std::numeric_limits<T>::quiet_NaN();
  9783. }
  9784. inline typename expression_node<T>::node_type type() const
  9785. {
  9786. return expression_node<T>::e_genfunction;
  9787. }
  9788. private:
  9789. std::size_t param_seq_index_;
  9790. };
  9791. #ifndef exprtk_disable_string_capabilities
  9792. template <typename T, typename StringFunction>
  9793. class multimode_strfunction_node : public string_function_node<T,StringFunction>
  9794. {
  9795. public:
  9796. typedef string_function_node<T,StringFunction> str_function_t;
  9797. typedef range_pack<T> range_t;
  9798. multimode_strfunction_node(StringFunction* func,
  9799. const std::size_t& param_seq_index,
  9800. const std::vector<typename str_function_t::expression_ptr>& arg_list)
  9801. : str_function_t(func,arg_list),
  9802. param_seq_index_(param_seq_index)
  9803. {}
  9804. inline T value() const
  9805. {
  9806. if (str_function_t::function_)
  9807. {
  9808. if (str_function_t::populate_value_list())
  9809. {
  9810. typedef typename StringFunction::parameter_list_t parameter_list_t;
  9811. const T result = (*str_function_t::function_)
  9812. (
  9813. param_seq_index_,
  9814. str_function_t::ret_string_,
  9815. parameter_list_t(str_function_t::typestore_list_)
  9816. );
  9817. str_function_t::range_.n1_c.second = str_function_t::ret_string_.size() - 1;
  9818. str_function_t::range_.cache.second = str_function_t::range_.n1_c.second;
  9819. return result;
  9820. }
  9821. }
  9822. return std::numeric_limits<T>::quiet_NaN();
  9823. }
  9824. inline typename expression_node<T>::node_type type() const
  9825. {
  9826. return expression_node<T>::e_strfunction;
  9827. }
  9828. private:
  9829. const std::size_t param_seq_index_;
  9830. };
  9831. #endif
  9832. class return_exception
  9833. {};
  9834. template <typename T>
  9835. class null_igenfunc
  9836. {
  9837. public:
  9838. virtual ~null_igenfunc()
  9839. {}
  9840. typedef type_store<T> generic_type;
  9841. typedef typename generic_type::parameter_list parameter_list_t;
  9842. inline virtual T operator() (parameter_list_t)
  9843. {
  9844. return std::numeric_limits<T>::quiet_NaN();
  9845. }
  9846. };
  9847. #ifndef exprtk_disable_return_statement
  9848. template <typename T>
  9849. class return_node : public generic_function_node<T,null_igenfunc<T> >
  9850. {
  9851. public:
  9852. typedef null_igenfunc<T> igeneric_function_t;
  9853. typedef igeneric_function_t* igeneric_function_ptr;
  9854. typedef generic_function_node<T,igeneric_function_t> gen_function_t;
  9855. typedef results_context<T> results_context_t;
  9856. return_node(const std::vector<typename gen_function_t::expression_ptr>& arg_list,
  9857. results_context_t& rc)
  9858. : gen_function_t (arg_list),
  9859. results_context_(&rc)
  9860. {}
  9861. inline T value() const
  9862. {
  9863. if (
  9864. (0 != results_context_) &&
  9865. gen_function_t::populate_value_list()
  9866. )
  9867. {
  9868. typedef typename type_store<T>::parameter_list parameter_list_t;
  9869. results_context_->
  9870. assign(parameter_list_t(gen_function_t::typestore_list_));
  9871. throw return_exception();
  9872. }
  9873. return std::numeric_limits<T>::quiet_NaN();
  9874. }
  9875. inline typename expression_node<T>::node_type type() const
  9876. {
  9877. return expression_node<T>::e_return;
  9878. }
  9879. private:
  9880. results_context_t* results_context_;
  9881. };
  9882. template <typename T>
  9883. class return_envelope_node : public expression_node<T>
  9884. {
  9885. public:
  9886. typedef expression_node<T>* expression_ptr;
  9887. typedef results_context<T> results_context_t;
  9888. return_envelope_node(expression_ptr body, results_context_t& rc)
  9889. : results_context_(&rc ),
  9890. return_invoked_ (false),
  9891. body_ (body ),
  9892. body_deletable_ (branch_deletable(body_))
  9893. {}
  9894. ~return_envelope_node()
  9895. {
  9896. if (body_ && body_deletable_)
  9897. {
  9898. destroy_node(body_);
  9899. }
  9900. }
  9901. inline T value() const
  9902. {
  9903. try
  9904. {
  9905. return_invoked_ = false;
  9906. results_context_->clear();
  9907. return body_->value();
  9908. }
  9909. catch(const return_exception&)
  9910. {
  9911. return_invoked_ = true;
  9912. return std::numeric_limits<T>::quiet_NaN();
  9913. }
  9914. }
  9915. inline typename expression_node<T>::node_type type() const
  9916. {
  9917. return expression_node<T>::e_retenv;
  9918. }
  9919. inline bool* retinvk_ptr()
  9920. {
  9921. return &return_invoked_;
  9922. }
  9923. private:
  9924. results_context_t* results_context_;
  9925. mutable bool return_invoked_;
  9926. expression_ptr body_;
  9927. const bool body_deletable_;
  9928. };
  9929. #endif
  9930. #define exprtk_define_unary_op(OpName) \
  9931. template <typename T> \
  9932. struct OpName##_op \
  9933. { \
  9934. typedef typename functor_t<T>::Type Type; \
  9935. typedef typename expression_node<T>::node_type node_t; \
  9936. \
  9937. static inline T process(Type v) \
  9938. { \
  9939. return numeric:: OpName (v); \
  9940. } \
  9941. \
  9942. static inline node_t type() \
  9943. { \
  9944. return expression_node<T>::e_##OpName; \
  9945. } \
  9946. \
  9947. static inline details::operator_type operation() \
  9948. { \
  9949. return details::e_##OpName; \
  9950. } \
  9951. }; \
  9952. exprtk_define_unary_op(abs )
  9953. exprtk_define_unary_op(acos )
  9954. exprtk_define_unary_op(acosh)
  9955. exprtk_define_unary_op(asin )
  9956. exprtk_define_unary_op(asinh)
  9957. exprtk_define_unary_op(atan )
  9958. exprtk_define_unary_op(atanh)
  9959. exprtk_define_unary_op(ceil )
  9960. exprtk_define_unary_op(cos )
  9961. exprtk_define_unary_op(cosh )
  9962. exprtk_define_unary_op(cot )
  9963. exprtk_define_unary_op(csc )
  9964. exprtk_define_unary_op(d2g )
  9965. exprtk_define_unary_op(d2r )
  9966. exprtk_define_unary_op(erf )
  9967. exprtk_define_unary_op(erfc )
  9968. exprtk_define_unary_op(exp )
  9969. exprtk_define_unary_op(expm1)
  9970. exprtk_define_unary_op(floor)
  9971. exprtk_define_unary_op(frac )
  9972. exprtk_define_unary_op(g2d )
  9973. exprtk_define_unary_op(log )
  9974. exprtk_define_unary_op(log10)
  9975. exprtk_define_unary_op(log2 )
  9976. exprtk_define_unary_op(log1p)
  9977. exprtk_define_unary_op(ncdf )
  9978. exprtk_define_unary_op(neg )
  9979. exprtk_define_unary_op(notl )
  9980. exprtk_define_unary_op(pos )
  9981. exprtk_define_unary_op(r2d )
  9982. exprtk_define_unary_op(round)
  9983. exprtk_define_unary_op(sec )
  9984. exprtk_define_unary_op(sgn )
  9985. exprtk_define_unary_op(sin )
  9986. exprtk_define_unary_op(sinc )
  9987. exprtk_define_unary_op(sinh )
  9988. exprtk_define_unary_op(sqrt )
  9989. exprtk_define_unary_op(tan )
  9990. exprtk_define_unary_op(tanh )
  9991. exprtk_define_unary_op(trunc)
  9992. #undef exprtk_define_unary_op
  9993. template <typename T>
  9994. struct opr_base
  9995. {
  9996. typedef typename details::functor_t<T>::Type Type;
  9997. typedef typename details::functor_t<T>::RefType RefType;
  9998. typedef typename details::functor_t<T> functor_t;
  9999. typedef typename functor_t::qfunc_t quaternary_functor_t;
  10000. typedef typename functor_t::tfunc_t trinary_functor_t;
  10001. typedef typename functor_t::bfunc_t binary_functor_t;
  10002. typedef typename functor_t::ufunc_t unary_functor_t;
  10003. };
  10004. template <typename T>
  10005. struct add_op : public opr_base<T>
  10006. {
  10007. typedef typename opr_base<T>::Type Type;
  10008. typedef typename opr_base<T>::RefType RefType;
  10009. static inline T process(Type t1, Type t2) { return t1 + t2; }
  10010. static inline T process(Type t1, Type t2, Type t3) { return t1 + t2 + t3; }
  10011. static inline void assign(RefType t1, Type t2) { t1 += t2; }
  10012. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_add; }
  10013. static inline details::operator_type operation() { return details::e_add; }
  10014. };
  10015. template <typename T>
  10016. struct mul_op : public opr_base<T>
  10017. {
  10018. typedef typename opr_base<T>::Type Type;
  10019. typedef typename opr_base<T>::RefType RefType;
  10020. static inline T process(Type t1, Type t2) { return t1 * t2; }
  10021. static inline T process(Type t1, Type t2, Type t3) { return t1 * t2 * t3; }
  10022. static inline void assign(RefType t1, Type t2) { t1 *= t2; }
  10023. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_mul; }
  10024. static inline details::operator_type operation() { return details::e_mul; }
  10025. };
  10026. template <typename T>
  10027. struct sub_op : public opr_base<T>
  10028. {
  10029. typedef typename opr_base<T>::Type Type;
  10030. typedef typename opr_base<T>::RefType RefType;
  10031. static inline T process(Type t1, Type t2) { return t1 - t2; }
  10032. static inline T process(Type t1, Type t2, Type t3) { return t1 - t2 - t3; }
  10033. static inline void assign(RefType t1, Type t2) { t1 -= t2; }
  10034. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_sub; }
  10035. static inline details::operator_type operation() { return details::e_sub; }
  10036. };
  10037. template <typename T>
  10038. struct div_op : public opr_base<T>
  10039. {
  10040. typedef typename opr_base<T>::Type Type;
  10041. typedef typename opr_base<T>::RefType RefType;
  10042. static inline T process(Type t1, Type t2) { return t1 / t2; }
  10043. static inline T process(Type t1, Type t2, Type t3) { return t1 / t2 / t3; }
  10044. static inline void assign(RefType t1, Type t2) { t1 /= t2; }
  10045. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_div; }
  10046. static inline details::operator_type operation() { return details::e_div; }
  10047. };
  10048. template <typename T>
  10049. struct mod_op : public opr_base<T>
  10050. {
  10051. typedef typename opr_base<T>::Type Type;
  10052. typedef typename opr_base<T>::RefType RefType;
  10053. static inline T process(Type t1, Type t2) { return numeric::modulus<T>(t1,t2); }
  10054. static inline void assign(RefType t1, Type t2) { t1 = numeric::modulus<T>(t1,t2); }
  10055. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_mod; }
  10056. static inline details::operator_type operation() { return details::e_mod; }
  10057. };
  10058. template <typename T>
  10059. struct pow_op : public opr_base<T>
  10060. {
  10061. typedef typename opr_base<T>::Type Type;
  10062. typedef typename opr_base<T>::RefType RefType;
  10063. static inline T process(Type t1, Type t2) { return numeric::pow<T>(t1,t2); }
  10064. static inline void assign(RefType t1, Type t2) { t1 = numeric::pow<T>(t1,t2); }
  10065. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_pow; }
  10066. static inline details::operator_type operation() { return details::e_pow; }
  10067. };
  10068. template <typename T>
  10069. struct lt_op : public opr_base<T>
  10070. {
  10071. typedef typename opr_base<T>::Type Type;
  10072. static inline T process(Type t1, Type t2) { return ((t1 < t2) ? T(1) : T(0)); }
  10073. static inline T process(const std::string& t1, const std::string& t2) { return ((t1 < t2) ? T(1) : T(0)); }
  10074. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_lt; }
  10075. static inline details::operator_type operation() { return details::e_lt; }
  10076. };
  10077. template <typename T>
  10078. struct lte_op : public opr_base<T>
  10079. {
  10080. typedef typename opr_base<T>::Type Type;
  10081. static inline T process(Type t1, Type t2) { return ((t1 <= t2) ? T(1) : T(0)); }
  10082. static inline T process(const std::string& t1, const std::string& t2) { return ((t1 <= t2) ? T(1) : T(0)); }
  10083. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_lte; }
  10084. static inline details::operator_type operation() { return details::e_lte; }
  10085. };
  10086. template <typename T>
  10087. struct gt_op : public opr_base<T>
  10088. {
  10089. typedef typename opr_base<T>::Type Type;
  10090. static inline T process(Type t1, Type t2) { return ((t1 > t2) ? T(1) : T(0)); }
  10091. static inline T process(const std::string& t1, const std::string& t2) { return ((t1 > t2) ? T(1) : T(0)); }
  10092. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_gt; }
  10093. static inline details::operator_type operation() { return details::e_gt; }
  10094. };
  10095. template <typename T>
  10096. struct gte_op : public opr_base<T>
  10097. {
  10098. typedef typename opr_base<T>::Type Type;
  10099. static inline T process(Type t1, Type t2) { return ((t1 >= t2) ? T(1) : T(0)); }
  10100. static inline T process(const std::string& t1, const std::string& t2) { return ((t1 >= t2) ? T(1) : T(0)); }
  10101. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_gte; }
  10102. static inline details::operator_type operation() { return details::e_gte; }
  10103. };
  10104. template <typename T>
  10105. struct eq_op : public opr_base<T>
  10106. {
  10107. typedef typename opr_base<T>::Type Type;
  10108. static inline T process(Type t1, Type t2) { return (std::equal_to<T>()(t1,t2) ? T(1) : T(0)); }
  10109. static inline T process(const std::string& t1, const std::string& t2) { return ((t1 == t2) ? T(1) : T(0)); }
  10110. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_eq; }
  10111. static inline details::operator_type operation() { return details::e_eq; }
  10112. };
  10113. template <typename T>
  10114. struct equal_op : public opr_base<T>
  10115. {
  10116. typedef typename opr_base<T>::Type Type;
  10117. static inline T process(Type t1, Type t2) { return numeric::equal(t1,t2); }
  10118. static inline T process(const std::string& t1, const std::string& t2) { return ((t1 == t2) ? T(1) : T(0)); }
  10119. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_eq; }
  10120. static inline details::operator_type operation() { return details::e_equal; }
  10121. };
  10122. template <typename T>
  10123. struct ne_op : public opr_base<T>
  10124. {
  10125. typedef typename opr_base<T>::Type Type;
  10126. static inline T process(Type t1, Type t2) { return (std::not_equal_to<T>()(t1,t2) ? T(1) : T(0)); }
  10127. static inline T process(const std::string& t1, const std::string& t2) { return ((t1 != t2) ? T(1) : T(0)); }
  10128. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_ne; }
  10129. static inline details::operator_type operation() { return details::e_ne; }
  10130. };
  10131. template <typename T>
  10132. struct and_op : public opr_base<T>
  10133. {
  10134. typedef typename opr_base<T>::Type Type;
  10135. static inline T process(Type t1, Type t2) { return (details::is_true(t1) && details::is_true(t2)) ? T(1) : T(0); }
  10136. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_and; }
  10137. static inline details::operator_type operation() { return details::e_and; }
  10138. };
  10139. template <typename T>
  10140. struct nand_op : public opr_base<T>
  10141. {
  10142. typedef typename opr_base<T>::Type Type;
  10143. static inline T process(Type t1, Type t2) { return (details::is_true(t1) && details::is_true(t2)) ? T(0) : T(1); }
  10144. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_nand; }
  10145. static inline details::operator_type operation() { return details::e_nand; }
  10146. };
  10147. template <typename T>
  10148. struct or_op : public opr_base<T>
  10149. {
  10150. typedef typename opr_base<T>::Type Type;
  10151. static inline T process(Type t1, Type t2) { return (details::is_true(t1) || details::is_true(t2)) ? T(1) : T(0); }
  10152. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_or; }
  10153. static inline details::operator_type operation() { return details::e_or; }
  10154. };
  10155. template <typename T>
  10156. struct nor_op : public opr_base<T>
  10157. {
  10158. typedef typename opr_base<T>::Type Type;
  10159. static inline T process(Type t1, Type t2) { return (details::is_true(t1) || details::is_true(t2)) ? T(0) : T(1); }
  10160. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_nor; }
  10161. static inline details::operator_type operation() { return details::e_nor; }
  10162. };
  10163. template <typename T>
  10164. struct xor_op : public opr_base<T>
  10165. {
  10166. typedef typename opr_base<T>::Type Type;
  10167. static inline T process(Type t1, Type t2) { return numeric::xor_opr<T>(t1,t2); }
  10168. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_nor; }
  10169. static inline details::operator_type operation() { return details::e_xor; }
  10170. };
  10171. template <typename T>
  10172. struct xnor_op : public opr_base<T>
  10173. {
  10174. typedef typename opr_base<T>::Type Type;
  10175. static inline T process(Type t1, Type t2) { return numeric::xnor_opr<T>(t1,t2); }
  10176. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_nor; }
  10177. static inline details::operator_type operation() { return details::e_xnor; }
  10178. };
  10179. template <typename T>
  10180. struct in_op : public opr_base<T>
  10181. {
  10182. typedef typename opr_base<T>::Type Type;
  10183. static inline T process(const T&, const T&) { return std::numeric_limits<T>::quiet_NaN(); }
  10184. static inline T process(const std::string& t1, const std::string& t2) { return ((std::string::npos != t2.find(t1)) ? T(1) : T(0)); }
  10185. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_in; }
  10186. static inline details::operator_type operation() { return details::e_in; }
  10187. };
  10188. template <typename T>
  10189. struct like_op : public opr_base<T>
  10190. {
  10191. typedef typename opr_base<T>::Type Type;
  10192. static inline T process(const T&, const T&) { return std::numeric_limits<T>::quiet_NaN(); }
  10193. static inline T process(const std::string& t1, const std::string& t2) { return (details::wc_match(t2,t1) ? T(1) : T(0)); }
  10194. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_like; }
  10195. static inline details::operator_type operation() { return details::e_like; }
  10196. };
  10197. template <typename T>
  10198. struct ilike_op : public opr_base<T>
  10199. {
  10200. typedef typename opr_base<T>::Type Type;
  10201. static inline T process(const T&, const T&) { return std::numeric_limits<T>::quiet_NaN(); }
  10202. static inline T process(const std::string& t1, const std::string& t2) { return (details::wc_imatch(t2,t1) ? T(1) : T(0)); }
  10203. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_ilike; }
  10204. static inline details::operator_type operation() { return details::e_ilike; }
  10205. };
  10206. template <typename T>
  10207. struct inrange_op : public opr_base<T>
  10208. {
  10209. typedef typename opr_base<T>::Type Type;
  10210. static inline T process(const T& t0, const T& t1, const T& t2) { return ((t0 <= t1) && (t1 <= t2)) ? T(1) : T(0); }
  10211. static inline T process(const std::string& t0, const std::string& t1, const std::string& t2)
  10212. {
  10213. return ((t0 <= t1) && (t1 <= t2)) ? T(1) : T(0);
  10214. }
  10215. static inline typename expression_node<T>::node_type type() { return expression_node<T>::e_inranges; }
  10216. static inline details::operator_type operation() { return details::e_inrange; }
  10217. };
  10218. template <typename T>
  10219. inline T value(details::expression_node<T>* n)
  10220. {
  10221. return n->value();
  10222. }
  10223. template <typename T>
  10224. inline T value(T* t)
  10225. {
  10226. return (*t);
  10227. }
  10228. template <typename T>
  10229. struct vararg_add_op : public opr_base<T>
  10230. {
  10231. typedef typename opr_base<T>::Type Type;
  10232. template <typename Type,
  10233. typename Allocator,
  10234. template <typename, typename> class Sequence>
  10235. static inline T process(const Sequence<Type,Allocator>& arg_list)
  10236. {
  10237. switch (arg_list.size())
  10238. {
  10239. case 0 : return T(0);
  10240. case 1 : return process_1(arg_list);
  10241. case 2 : return process_2(arg_list);
  10242. case 3 : return process_3(arg_list);
  10243. case 4 : return process_4(arg_list);
  10244. case 5 : return process_5(arg_list);
  10245. default :
  10246. {
  10247. T result = T(0);
  10248. for (std::size_t i = 0; i < arg_list.size(); ++i)
  10249. {
  10250. result += value(arg_list[i]);
  10251. }
  10252. return result;
  10253. }
  10254. }
  10255. }
  10256. template <typename Sequence>
  10257. static inline T process_1(const Sequence& arg_list)
  10258. {
  10259. return value(arg_list[0]);
  10260. }
  10261. template <typename Sequence>
  10262. static inline T process_2(const Sequence& arg_list)
  10263. {
  10264. return value(arg_list[0]) + value(arg_list[1]);
  10265. }
  10266. template <typename Sequence>
  10267. static inline T process_3(const Sequence& arg_list)
  10268. {
  10269. return value(arg_list[0]) + value(arg_list[1]) +
  10270. value(arg_list[2]) ;
  10271. }
  10272. template <typename Sequence>
  10273. static inline T process_4(const Sequence& arg_list)
  10274. {
  10275. return value(arg_list[0]) + value(arg_list[1]) +
  10276. value(arg_list[2]) + value(arg_list[3]) ;
  10277. }
  10278. template <typename Sequence>
  10279. static inline T process_5(const Sequence& arg_list)
  10280. {
  10281. return value(arg_list[0]) + value(arg_list[1]) +
  10282. value(arg_list[2]) + value(arg_list[3]) +
  10283. value(arg_list[4]) ;
  10284. }
  10285. };
  10286. template <typename T>
  10287. struct vararg_mul_op : public opr_base<T>
  10288. {
  10289. typedef typename opr_base<T>::Type Type;
  10290. template <typename Type,
  10291. typename Allocator,
  10292. template <typename, typename> class Sequence>
  10293. static inline T process(const Sequence<Type,Allocator>& arg_list)
  10294. {
  10295. switch (arg_list.size())
  10296. {
  10297. case 0 : return T(0);
  10298. case 1 : return process_1(arg_list);
  10299. case 2 : return process_2(arg_list);
  10300. case 3 : return process_3(arg_list);
  10301. case 4 : return process_4(arg_list);
  10302. case 5 : return process_5(arg_list);
  10303. default :
  10304. {
  10305. T result = T(value(arg_list[0]));
  10306. for (std::size_t i = 1; i < arg_list.size(); ++i)
  10307. {
  10308. result *= value(arg_list[i]);
  10309. }
  10310. return result;
  10311. }
  10312. }
  10313. }
  10314. template <typename Sequence>
  10315. static inline T process_1(const Sequence& arg_list)
  10316. {
  10317. return value(arg_list[0]);
  10318. }
  10319. template <typename Sequence>
  10320. static inline T process_2(const Sequence& arg_list)
  10321. {
  10322. return value(arg_list[0]) * value(arg_list[1]);
  10323. }
  10324. template <typename Sequence>
  10325. static inline T process_3(const Sequence& arg_list)
  10326. {
  10327. return value(arg_list[0]) * value(arg_list[1]) *
  10328. value(arg_list[2]) ;
  10329. }
  10330. template <typename Sequence>
  10331. static inline T process_4(const Sequence& arg_list)
  10332. {
  10333. return value(arg_list[0]) * value(arg_list[1]) *
  10334. value(arg_list[2]) * value(arg_list[3]) ;
  10335. }
  10336. template <typename Sequence>
  10337. static inline T process_5(const Sequence& arg_list)
  10338. {
  10339. return value(arg_list[0]) * value(arg_list[1]) *
  10340. value(arg_list[2]) * value(arg_list[3]) *
  10341. value(arg_list[4]) ;
  10342. }
  10343. };
  10344. template <typename T>
  10345. struct vararg_avg_op : public opr_base<T>
  10346. {
  10347. typedef typename opr_base<T>::Type Type;
  10348. template <typename Type,
  10349. typename Allocator,
  10350. template <typename, typename> class Sequence>
  10351. static inline T process(const Sequence<Type,Allocator>& arg_list)
  10352. {
  10353. switch (arg_list.size())
  10354. {
  10355. case 0 : return T(0);
  10356. case 1 : return process_1(arg_list);
  10357. case 2 : return process_2(arg_list);
  10358. case 3 : return process_3(arg_list);
  10359. case 4 : return process_4(arg_list);
  10360. case 5 : return process_5(arg_list);
  10361. default : return vararg_add_op<T>::process(arg_list) / arg_list.size();
  10362. }
  10363. }
  10364. template <typename Sequence>
  10365. static inline T process_1(const Sequence& arg_list)
  10366. {
  10367. return value(arg_list[0]);
  10368. }
  10369. template <typename Sequence>
  10370. static inline T process_2(const Sequence& arg_list)
  10371. {
  10372. return (value(arg_list[0]) + value(arg_list[1])) / T(2);
  10373. }
  10374. template <typename Sequence>
  10375. static inline T process_3(const Sequence& arg_list)
  10376. {
  10377. return (value(arg_list[0]) + value(arg_list[1]) + value(arg_list[2])) / T(3);
  10378. }
  10379. template <typename Sequence>
  10380. static inline T process_4(const Sequence& arg_list)
  10381. {
  10382. return (value(arg_list[0]) + value(arg_list[1]) +
  10383. value(arg_list[2]) + value(arg_list[3])) / T(4);
  10384. }
  10385. template <typename Sequence>
  10386. static inline T process_5(const Sequence& arg_list)
  10387. {
  10388. return (value(arg_list[0]) + value(arg_list[1]) +
  10389. value(arg_list[2]) + value(arg_list[3]) +
  10390. value(arg_list[4])) / T(5);
  10391. }
  10392. };
  10393. template <typename T>
  10394. struct vararg_min_op : public opr_base<T>
  10395. {
  10396. typedef typename opr_base<T>::Type Type;
  10397. template <typename Type,
  10398. typename Allocator,
  10399. template <typename, typename> class Sequence>
  10400. static inline T process(const Sequence<Type,Allocator>& arg_list)
  10401. {
  10402. switch (arg_list.size())
  10403. {
  10404. case 0 : return T(0);
  10405. case 1 : return process_1(arg_list);
  10406. case 2 : return process_2(arg_list);
  10407. case 3 : return process_3(arg_list);
  10408. case 4 : return process_4(arg_list);
  10409. case 5 : return process_5(arg_list);
  10410. default :
  10411. {
  10412. T result = T(value(arg_list[0]));
  10413. for (std::size_t i = 1; i < arg_list.size(); ++i)
  10414. {
  10415. const T v = value(arg_list[i]);
  10416. if (v < result)
  10417. result = v;
  10418. }
  10419. return result;
  10420. }
  10421. }
  10422. }
  10423. template <typename Sequence>
  10424. static inline T process_1(const Sequence& arg_list)
  10425. {
  10426. return value(arg_list[0]);
  10427. }
  10428. template <typename Sequence>
  10429. static inline T process_2(const Sequence& arg_list)
  10430. {
  10431. return std::min<T>(value(arg_list[0]),value(arg_list[1]));
  10432. }
  10433. template <typename Sequence>
  10434. static inline T process_3(const Sequence& arg_list)
  10435. {
  10436. return std::min<T>(std::min<T>(value(arg_list[0]),value(arg_list[1])),value(arg_list[2]));
  10437. }
  10438. template <typename Sequence>
  10439. static inline T process_4(const Sequence& arg_list)
  10440. {
  10441. return std::min<T>(
  10442. std::min<T>(value(arg_list[0]), value(arg_list[1])),
  10443. std::min<T>(value(arg_list[2]), value(arg_list[3])));
  10444. }
  10445. template <typename Sequence>
  10446. static inline T process_5(const Sequence& arg_list)
  10447. {
  10448. return std::min<T>(
  10449. std::min<T>(std::min<T>(value(arg_list[0]), value(arg_list[1])),
  10450. std::min<T>(value(arg_list[2]), value(arg_list[3]))),
  10451. value(arg_list[4]));
  10452. }
  10453. };
  10454. template <typename T>
  10455. struct vararg_max_op : public opr_base<T>
  10456. {
  10457. typedef typename opr_base<T>::Type Type;
  10458. template <typename Type,
  10459. typename Allocator,
  10460. template <typename, typename> class Sequence>
  10461. static inline T process(const Sequence<Type,Allocator>& arg_list)
  10462. {
  10463. switch (arg_list.size())
  10464. {
  10465. case 0 : return T(0);
  10466. case 1 : return process_1(arg_list);
  10467. case 2 : return process_2(arg_list);
  10468. case 3 : return process_3(arg_list);
  10469. case 4 : return process_4(arg_list);
  10470. case 5 : return process_5(arg_list);
  10471. default :
  10472. {
  10473. T result = T(value(arg_list[0]));
  10474. for (std::size_t i = 1; i < arg_list.size(); ++i)
  10475. {
  10476. const T v = value(arg_list[i]);
  10477. if (v > result)
  10478. result = v;
  10479. }
  10480. return result;
  10481. }
  10482. }
  10483. }
  10484. template <typename Sequence>
  10485. static inline T process_1(const Sequence& arg_list)
  10486. {
  10487. return value(arg_list[0]);
  10488. }
  10489. template <typename Sequence>
  10490. static inline T process_2(const Sequence& arg_list)
  10491. {
  10492. return std::max<T>(value(arg_list[0]),value(arg_list[1]));
  10493. }
  10494. template <typename Sequence>
  10495. static inline T process_3(const Sequence& arg_list)
  10496. {
  10497. return std::max<T>(std::max<T>(value(arg_list[0]),value(arg_list[1])),value(arg_list[2]));
  10498. }
  10499. template <typename Sequence>
  10500. static inline T process_4(const Sequence& arg_list)
  10501. {
  10502. return std::max<T>(
  10503. std::max<T>(value(arg_list[0]), value(arg_list[1])),
  10504. std::max<T>(value(arg_list[2]), value(arg_list[3])));
  10505. }
  10506. template <typename Sequence>
  10507. static inline T process_5(const Sequence& arg_list)
  10508. {
  10509. return std::max<T>(
  10510. std::max<T>(std::max<T>(value(arg_list[0]), value(arg_list[1])),
  10511. std::max<T>(value(arg_list[2]), value(arg_list[3]))),
  10512. value(arg_list[4]));
  10513. }
  10514. };
  10515. template <typename T>
  10516. struct vararg_mand_op : public opr_base<T>
  10517. {
  10518. typedef typename opr_base<T>::Type Type;
  10519. template <typename Type,
  10520. typename Allocator,
  10521. template <typename, typename> class Sequence>
  10522. static inline T process(const Sequence<Type,Allocator>& arg_list)
  10523. {
  10524. switch (arg_list.size())
  10525. {
  10526. case 1 : return process_1(arg_list);
  10527. case 2 : return process_2(arg_list);
  10528. case 3 : return process_3(arg_list);
  10529. case 4 : return process_4(arg_list);
  10530. case 5 : return process_5(arg_list);
  10531. default :
  10532. {
  10533. for (std::size_t i = 0; i < arg_list.size(); ++i)
  10534. {
  10535. if (std::equal_to<T>()(T(0), value(arg_list[i])))
  10536. return T(0);
  10537. }
  10538. return T(1);
  10539. }
  10540. }
  10541. }
  10542. template <typename Sequence>
  10543. static inline T process_1(const Sequence& arg_list)
  10544. {
  10545. return std::not_equal_to<T>()
  10546. (T(0), value(arg_list[0])) ? T(1) : T(0);
  10547. }
  10548. template <typename Sequence>
  10549. static inline T process_2(const Sequence& arg_list)
  10550. {
  10551. return (
  10552. std::not_equal_to<T>()(T(0), value(arg_list[0])) &&
  10553. std::not_equal_to<T>()(T(0), value(arg_list[1]))
  10554. ) ? T(1) : T(0);
  10555. }
  10556. template <typename Sequence>
  10557. static inline T process_3(const Sequence& arg_list)
  10558. {
  10559. return (
  10560. std::not_equal_to<T>()(T(0), value(arg_list[0])) &&
  10561. std::not_equal_to<T>()(T(0), value(arg_list[1])) &&
  10562. std::not_equal_to<T>()(T(0), value(arg_list[2]))
  10563. ) ? T(1) : T(0);
  10564. }
  10565. template <typename Sequence>
  10566. static inline T process_4(const Sequence& arg_list)
  10567. {
  10568. return (
  10569. std::not_equal_to<T>()(T(0), value(arg_list[0])) &&
  10570. std::not_equal_to<T>()(T(0), value(arg_list[1])) &&
  10571. std::not_equal_to<T>()(T(0), value(arg_list[2])) &&
  10572. std::not_equal_to<T>()(T(0), value(arg_list[3]))
  10573. ) ? T(1) : T(0);
  10574. }
  10575. template <typename Sequence>
  10576. static inline T process_5(const Sequence& arg_list)
  10577. {
  10578. return (
  10579. std::not_equal_to<T>()(T(0), value(arg_list[0])) &&
  10580. std::not_equal_to<T>()(T(0), value(arg_list[1])) &&
  10581. std::not_equal_to<T>()(T(0), value(arg_list[2])) &&
  10582. std::not_equal_to<T>()(T(0), value(arg_list[3])) &&
  10583. std::not_equal_to<T>()(T(0), value(arg_list[4]))
  10584. ) ? T(1) : T(0);
  10585. }
  10586. };
  10587. template <typename T>
  10588. struct vararg_mor_op : public opr_base<T>
  10589. {
  10590. typedef typename opr_base<T>::Type Type;
  10591. template <typename Type,
  10592. typename Allocator,
  10593. template <typename, typename> class Sequence>
  10594. static inline T process(const Sequence<Type,Allocator>& arg_list)
  10595. {
  10596. switch (arg_list.size())
  10597. {
  10598. case 1 : return process_1(arg_list);
  10599. case 2 : return process_2(arg_list);
  10600. case 3 : return process_3(arg_list);
  10601. case 4 : return process_4(arg_list);
  10602. case 5 : return process_5(arg_list);
  10603. default :
  10604. {
  10605. for (std::size_t i = 0; i < arg_list.size(); ++i)
  10606. {
  10607. if (std::not_equal_to<T>()(T(0), value(arg_list[i])))
  10608. return T(1);
  10609. }
  10610. return T(0);
  10611. }
  10612. }
  10613. }
  10614. template <typename Sequence>
  10615. static inline T process_1(const Sequence& arg_list)
  10616. {
  10617. return std::not_equal_to<T>()
  10618. (T(0), value(arg_list[0])) ? T(1) : T(0);
  10619. }
  10620. template <typename Sequence>
  10621. static inline T process_2(const Sequence& arg_list)
  10622. {
  10623. return (
  10624. std::not_equal_to<T>()(T(0), value(arg_list[0])) ||
  10625. std::not_equal_to<T>()(T(0), value(arg_list[1]))
  10626. ) ? T(1) : T(0);
  10627. }
  10628. template <typename Sequence>
  10629. static inline T process_3(const Sequence& arg_list)
  10630. {
  10631. return (
  10632. std::not_equal_to<T>()(T(0), value(arg_list[0])) ||
  10633. std::not_equal_to<T>()(T(0), value(arg_list[1])) ||
  10634. std::not_equal_to<T>()(T(0), value(arg_list[2]))
  10635. ) ? T(1) : T(0);
  10636. }
  10637. template <typename Sequence>
  10638. static inline T process_4(const Sequence& arg_list)
  10639. {
  10640. return (
  10641. std::not_equal_to<T>()(T(0), value(arg_list[0])) ||
  10642. std::not_equal_to<T>()(T(0), value(arg_list[1])) ||
  10643. std::not_equal_to<T>()(T(0), value(arg_list[2])) ||
  10644. std::not_equal_to<T>()(T(0), value(arg_list[3]))
  10645. ) ? T(1) : T(0);
  10646. }
  10647. template <typename Sequence>
  10648. static inline T process_5(const Sequence& arg_list)
  10649. {
  10650. return (
  10651. std::not_equal_to<T>()(T(0), value(arg_list[0])) ||
  10652. std::not_equal_to<T>()(T(0), value(arg_list[1])) ||
  10653. std::not_equal_to<T>()(T(0), value(arg_list[2])) ||
  10654. std::not_equal_to<T>()(T(0), value(arg_list[3])) ||
  10655. std::not_equal_to<T>()(T(0), value(arg_list[4]))
  10656. ) ? T(1) : T(0);
  10657. }
  10658. };
  10659. template <typename T>
  10660. struct vararg_multi_op : public opr_base<T>
  10661. {
  10662. typedef typename opr_base<T>::Type Type;
  10663. template <typename Type,
  10664. typename Allocator,
  10665. template <typename, typename> class Sequence>
  10666. static inline T process(const Sequence<Type,Allocator>& arg_list)
  10667. {
  10668. switch (arg_list.size())
  10669. {
  10670. case 0 : return std::numeric_limits<T>::quiet_NaN();
  10671. case 1 : return process_1(arg_list);
  10672. case 2 : return process_2(arg_list);
  10673. case 3 : return process_3(arg_list);
  10674. case 4 : return process_4(arg_list);
  10675. case 5 : return process_5(arg_list);
  10676. case 6 : return process_6(arg_list);
  10677. case 7 : return process_7(arg_list);
  10678. case 8 : return process_8(arg_list);
  10679. default :
  10680. {
  10681. for (std::size_t i = 0; i < (arg_list.size() - 1); ++i)
  10682. {
  10683. value(arg_list[i]);
  10684. }
  10685. return value(arg_list.back());
  10686. }
  10687. }
  10688. }
  10689. template <typename Sequence>
  10690. static inline T process_1(const Sequence& arg_list)
  10691. {
  10692. return value(arg_list[0]);
  10693. }
  10694. template <typename Sequence>
  10695. static inline T process_2(const Sequence& arg_list)
  10696. {
  10697. value(arg_list[0]);
  10698. return value(arg_list[1]);
  10699. }
  10700. template <typename Sequence>
  10701. static inline T process_3(const Sequence& arg_list)
  10702. {
  10703. value(arg_list[0]);
  10704. value(arg_list[1]);
  10705. return value(arg_list[2]);
  10706. }
  10707. template <typename Sequence>
  10708. static inline T process_4(const Sequence& arg_list)
  10709. {
  10710. value(arg_list[0]);
  10711. value(arg_list[1]);
  10712. value(arg_list[2]);
  10713. return value(arg_list[3]);
  10714. }
  10715. template <typename Sequence>
  10716. static inline T process_5(const Sequence& arg_list)
  10717. {
  10718. value(arg_list[0]);
  10719. value(arg_list[1]);
  10720. value(arg_list[2]);
  10721. value(arg_list[3]);
  10722. return value(arg_list[4]);
  10723. }
  10724. template <typename Sequence>
  10725. static inline T process_6(const Sequence& arg_list)
  10726. {
  10727. value(arg_list[0]);
  10728. value(arg_list[1]);
  10729. value(arg_list[2]);
  10730. value(arg_list[3]);
  10731. value(arg_list[4]);
  10732. return value(arg_list[5]);
  10733. }
  10734. template <typename Sequence>
  10735. static inline T process_7(const Sequence& arg_list)
  10736. {
  10737. value(arg_list[0]);
  10738. value(arg_list[1]);
  10739. value(arg_list[2]);
  10740. value(arg_list[3]);
  10741. value(arg_list[4]);
  10742. value(arg_list[5]);
  10743. return value(arg_list[6]);
  10744. }
  10745. template <typename Sequence>
  10746. static inline T process_8(const Sequence& arg_list)
  10747. {
  10748. value(arg_list[0]);
  10749. value(arg_list[1]);
  10750. value(arg_list[2]);
  10751. value(arg_list[3]);
  10752. value(arg_list[4]);
  10753. value(arg_list[5]);
  10754. value(arg_list[6]);
  10755. return value(arg_list[7]);
  10756. }
  10757. };
  10758. template <typename T>
  10759. struct vec_add_op
  10760. {
  10761. typedef vector_interface<T>* ivector_ptr;
  10762. static inline T process(const ivector_ptr v)
  10763. {
  10764. const T* vec = v->vec()->vds().data();
  10765. const std::size_t vec_size = v->vec()->vds().size();
  10766. loop_unroll::details lud(vec_size);
  10767. if (vec_size <= static_cast<std::size_t>(lud.batch_size))
  10768. {
  10769. T result = T(0);
  10770. int i = 0;
  10771. exprtk_disable_fallthrough_begin
  10772. switch (vec_size)
  10773. {
  10774. #define case_stmt(N) \
  10775. case N : result += vec[i++]; \
  10776. #ifndef exprtk_disable_superscalar_unroll
  10777. case_stmt(16) case_stmt(15)
  10778. case_stmt(14) case_stmt(13)
  10779. case_stmt(12) case_stmt(11)
  10780. case_stmt(10) case_stmt( 9)
  10781. case_stmt( 8) case_stmt( 7)
  10782. case_stmt( 6) case_stmt( 5)
  10783. #endif
  10784. case_stmt( 4) case_stmt( 3)
  10785. case_stmt( 2) case_stmt( 1)
  10786. }
  10787. exprtk_disable_fallthrough_end
  10788. #undef case_stmt
  10789. return result;
  10790. }
  10791. T r[] = {
  10792. T(0), T(0), T(0), T(0), T(0), T(0), T(0), T(0),
  10793. T(0), T(0), T(0), T(0), T(0), T(0), T(0), T(0)
  10794. };
  10795. const T* upper_bound = vec + lud.upper_bound;
  10796. while (vec < upper_bound)
  10797. {
  10798. #define exprtk_loop(N) \
  10799. r[N] += vec[N]; \
  10800. exprtk_loop( 0) exprtk_loop( 1)
  10801. exprtk_loop( 2) exprtk_loop( 3)
  10802. #ifndef exprtk_disable_superscalar_unroll
  10803. exprtk_loop( 4) exprtk_loop( 5)
  10804. exprtk_loop( 6) exprtk_loop( 7)
  10805. exprtk_loop( 8) exprtk_loop( 9)
  10806. exprtk_loop(10) exprtk_loop(11)
  10807. exprtk_loop(12) exprtk_loop(13)
  10808. exprtk_loop(14) exprtk_loop(15)
  10809. #endif
  10810. vec += lud.batch_size;
  10811. }
  10812. int i = 0;
  10813. exprtk_disable_fallthrough_begin
  10814. switch (lud.remainder)
  10815. {
  10816. #define case_stmt(N) \
  10817. case N : r[0] += vec[i++]; \
  10818. #ifndef exprtk_disable_superscalar_unroll
  10819. case_stmt(15) case_stmt(14)
  10820. case_stmt(13) case_stmt(12)
  10821. case_stmt(11) case_stmt(10)
  10822. case_stmt( 9) case_stmt( 8)
  10823. case_stmt( 7) case_stmt( 6)
  10824. case_stmt( 5) case_stmt( 4)
  10825. #endif
  10826. case_stmt( 3) case_stmt( 2)
  10827. case_stmt( 1)
  10828. }
  10829. exprtk_disable_fallthrough_end
  10830. #undef exprtk_loop
  10831. #undef case_stmt
  10832. return (r[ 0] + r[ 1] + r[ 2] + r[ 3])
  10833. #ifndef exprtk_disable_superscalar_unroll
  10834. + (r[ 4] + r[ 5] + r[ 6] + r[ 7])
  10835. + (r[ 8] + r[ 9] + r[10] + r[11])
  10836. + (r[12] + r[13] + r[14] + r[15])
  10837. #endif
  10838. ;
  10839. }
  10840. };
  10841. template <typename T>
  10842. struct vec_mul_op
  10843. {
  10844. typedef vector_interface<T>* ivector_ptr;
  10845. static inline T process(const ivector_ptr v)
  10846. {
  10847. const T* vec = v->vec()->vds().data();
  10848. const std::size_t vec_size = v->vec()->vds().size();
  10849. loop_unroll::details lud(vec_size);
  10850. if (vec_size <= static_cast<std::size_t>(lud.batch_size))
  10851. {
  10852. T result = T(1);
  10853. int i = 0;
  10854. exprtk_disable_fallthrough_begin
  10855. switch (vec_size)
  10856. {
  10857. #define case_stmt(N) \
  10858. case N : result *= vec[i++]; \
  10859. #ifndef exprtk_disable_superscalar_unroll
  10860. case_stmt(16) case_stmt(15)
  10861. case_stmt(14) case_stmt(13)
  10862. case_stmt(12) case_stmt(11)
  10863. case_stmt(10) case_stmt( 9)
  10864. case_stmt( 8) case_stmt( 7)
  10865. case_stmt( 6) case_stmt( 5)
  10866. #endif
  10867. case_stmt( 4) case_stmt( 3)
  10868. case_stmt( 2) case_stmt( 1)
  10869. }
  10870. exprtk_disable_fallthrough_end
  10871. #undef case_stmt
  10872. return result;
  10873. }
  10874. T r[] = {
  10875. T(1), T(1), T(1), T(1), T(1), T(1), T(1), T(1),
  10876. T(1), T(1), T(1), T(1), T(1), T(1), T(1), T(1)
  10877. };
  10878. const T* upper_bound = vec + lud.upper_bound;
  10879. while (vec < upper_bound)
  10880. {
  10881. #define exprtk_loop(N) \
  10882. r[N] *= vec[N]; \
  10883. exprtk_loop( 0) exprtk_loop( 1)
  10884. exprtk_loop( 2) exprtk_loop( 3)
  10885. #ifndef exprtk_disable_superscalar_unroll
  10886. exprtk_loop( 4) exprtk_loop( 5)
  10887. exprtk_loop( 6) exprtk_loop( 7)
  10888. exprtk_loop( 8) exprtk_loop( 9)
  10889. exprtk_loop(10) exprtk_loop(11)
  10890. exprtk_loop(12) exprtk_loop(13)
  10891. exprtk_loop(14) exprtk_loop(15)
  10892. #endif
  10893. vec += lud.batch_size;
  10894. }
  10895. int i = 0;
  10896. exprtk_disable_fallthrough_begin
  10897. switch (lud.remainder)
  10898. {
  10899. #define case_stmt(N) \
  10900. case N : r[0] *= vec[i++]; \
  10901. #ifndef exprtk_disable_superscalar_unroll
  10902. case_stmt(15) case_stmt(14)
  10903. case_stmt(13) case_stmt(12)
  10904. case_stmt(11) case_stmt(10)
  10905. case_stmt( 9) case_stmt( 8)
  10906. case_stmt( 7) case_stmt( 6)
  10907. case_stmt( 5) case_stmt( 4)
  10908. #endif
  10909. case_stmt( 3) case_stmt( 2)
  10910. case_stmt( 1)
  10911. }
  10912. exprtk_disable_fallthrough_end
  10913. #undef exprtk_loop
  10914. #undef case_stmt
  10915. return (r[ 0] * r[ 1] * r[ 2] * r[ 3])
  10916. #ifndef exprtk_disable_superscalar_unroll
  10917. + (r[ 4] * r[ 5] * r[ 6] * r[ 7])
  10918. + (r[ 8] * r[ 9] * r[10] * r[11])
  10919. + (r[12] * r[13] * r[14] * r[15])
  10920. #endif
  10921. ;
  10922. }
  10923. };
  10924. template <typename T>
  10925. struct vec_avg_op
  10926. {
  10927. typedef vector_interface<T>* ivector_ptr;
  10928. static inline T process(const ivector_ptr v)
  10929. {
  10930. const std::size_t vec_size = v->vec()->vds().size();
  10931. return vec_add_op<T>::process(v) / vec_size;
  10932. }
  10933. };
  10934. template <typename T>
  10935. struct vec_min_op
  10936. {
  10937. typedef vector_interface<T>* ivector_ptr;
  10938. static inline T process(const ivector_ptr v)
  10939. {
  10940. const T* vec = v->vec()->vds().data();
  10941. const std::size_t vec_size = v->vec()->vds().size();
  10942. T result = vec[0];
  10943. for (std::size_t i = 1; i < vec_size; ++i)
  10944. {
  10945. T v_i = vec[i];
  10946. if (v_i < result)
  10947. result = v_i;
  10948. }
  10949. return result;
  10950. }
  10951. };
  10952. template <typename T>
  10953. struct vec_max_op
  10954. {
  10955. typedef vector_interface<T>* ivector_ptr;
  10956. static inline T process(const ivector_ptr v)
  10957. {
  10958. const T* vec = v->vec()->vds().data();
  10959. const std::size_t vec_size = v->vec()->vds().size();
  10960. T result = vec[0];
  10961. for (std::size_t i = 1; i < vec_size; ++i)
  10962. {
  10963. T v_i = vec[i];
  10964. if (v_i > result)
  10965. result = v_i;
  10966. }
  10967. return result;
  10968. }
  10969. };
  10970. template <typename T>
  10971. class vov_base_node : public expression_node<T>
  10972. {
  10973. public:
  10974. virtual ~vov_base_node()
  10975. {}
  10976. inline virtual operator_type operation() const
  10977. {
  10978. return details::e_default;
  10979. }
  10980. virtual const T& v0() const = 0;
  10981. virtual const T& v1() const = 0;
  10982. };
  10983. template <typename T>
  10984. class cov_base_node : public expression_node<T>
  10985. {
  10986. public:
  10987. virtual ~cov_base_node()
  10988. {}
  10989. inline virtual operator_type operation() const
  10990. {
  10991. return details::e_default;
  10992. }
  10993. virtual const T c() const = 0;
  10994. virtual const T& v() const = 0;
  10995. };
  10996. template <typename T>
  10997. class voc_base_node : public expression_node<T>
  10998. {
  10999. public:
  11000. virtual ~voc_base_node()
  11001. {}
  11002. inline virtual operator_type operation() const
  11003. {
  11004. return details::e_default;
  11005. }
  11006. virtual const T c() const = 0;
  11007. virtual const T& v() const = 0;
  11008. };
  11009. template <typename T>
  11010. class vob_base_node : public expression_node<T>
  11011. {
  11012. public:
  11013. virtual ~vob_base_node()
  11014. {}
  11015. virtual const T& v() const = 0;
  11016. };
  11017. template <typename T>
  11018. class bov_base_node : public expression_node<T>
  11019. {
  11020. public:
  11021. virtual ~bov_base_node()
  11022. {}
  11023. virtual const T& v() const = 0;
  11024. };
  11025. template <typename T>
  11026. class cob_base_node : public expression_node<T>
  11027. {
  11028. public:
  11029. virtual ~cob_base_node()
  11030. {}
  11031. inline virtual operator_type operation() const
  11032. {
  11033. return details::e_default;
  11034. }
  11035. virtual const T c() const = 0;
  11036. virtual void set_c(const T) = 0;
  11037. virtual expression_node<T>* move_branch(const std::size_t& index) = 0;
  11038. };
  11039. template <typename T>
  11040. class boc_base_node : public expression_node<T>
  11041. {
  11042. public:
  11043. virtual ~boc_base_node()
  11044. {}
  11045. inline virtual operator_type operation() const
  11046. {
  11047. return details::e_default;
  11048. }
  11049. virtual const T c() const = 0;
  11050. virtual void set_c(const T) = 0;
  11051. virtual expression_node<T>* move_branch(const std::size_t& index) = 0;
  11052. };
  11053. template <typename T>
  11054. class uv_base_node : public expression_node<T>
  11055. {
  11056. public:
  11057. virtual ~uv_base_node()
  11058. {}
  11059. inline virtual operator_type operation() const
  11060. {
  11061. return details::e_default;
  11062. }
  11063. virtual const T& v() const = 0;
  11064. };
  11065. template <typename T>
  11066. class sos_base_node : public expression_node<T>
  11067. {
  11068. public:
  11069. virtual ~sos_base_node()
  11070. {}
  11071. inline virtual operator_type operation() const
  11072. {
  11073. return details::e_default;
  11074. }
  11075. };
  11076. template <typename T>
  11077. class sosos_base_node : public expression_node<T>
  11078. {
  11079. public:
  11080. virtual ~sosos_base_node()
  11081. {}
  11082. inline virtual operator_type operation() const
  11083. {
  11084. return details::e_default;
  11085. }
  11086. };
  11087. template <typename T>
  11088. class T0oT1oT2_base_node : public expression_node<T>
  11089. {
  11090. public:
  11091. virtual ~T0oT1oT2_base_node()
  11092. {}
  11093. virtual std::string type_id() const = 0;
  11094. };
  11095. template <typename T>
  11096. class T0oT1oT2oT3_base_node : public expression_node<T>
  11097. {
  11098. public:
  11099. virtual ~T0oT1oT2oT3_base_node()
  11100. {}
  11101. virtual std::string type_id() const = 0;
  11102. };
  11103. template <typename T, typename Operation>
  11104. class unary_variable_node : public uv_base_node<T>
  11105. {
  11106. public:
  11107. typedef expression_node<T>* expression_ptr;
  11108. typedef Operation operation_t;
  11109. explicit unary_variable_node(const T& var)
  11110. : v_(var)
  11111. {}
  11112. inline T value() const
  11113. {
  11114. return Operation::process(v_);
  11115. }
  11116. inline typename expression_node<T>::node_type type() const
  11117. {
  11118. return Operation::type();
  11119. }
  11120. inline operator_type operation() const
  11121. {
  11122. return Operation::operation();
  11123. }
  11124. inline const T& v() const
  11125. {
  11126. return v_;
  11127. }
  11128. private:
  11129. unary_variable_node(unary_variable_node<T,Operation>&);
  11130. unary_variable_node<T,Operation>& operator=(unary_variable_node<T,Operation>&);
  11131. const T& v_;
  11132. };
  11133. template <typename T>
  11134. class uvouv_node : public expression_node<T>
  11135. {
  11136. public:
  11137. // UOpr1(v0) Op UOpr2(v1)
  11138. typedef expression_node<T>* expression_ptr;
  11139. typedef typename details::functor_t<T> functor_t;
  11140. typedef typename functor_t::bfunc_t bfunc_t;
  11141. typedef typename functor_t::ufunc_t ufunc_t;
  11142. explicit uvouv_node(const T& var0,const T& var1,
  11143. ufunc_t uf0, ufunc_t uf1, bfunc_t bf)
  11144. : v0_(var0),
  11145. v1_(var1),
  11146. u0_(uf0 ),
  11147. u1_(uf1 ),
  11148. f_ (bf )
  11149. {}
  11150. inline T value() const
  11151. {
  11152. return f_(u0_(v0_),u1_(v1_));
  11153. }
  11154. inline typename expression_node<T>::node_type type() const
  11155. {
  11156. return expression_node<T>::e_uvouv;
  11157. }
  11158. inline operator_type operation() const
  11159. {
  11160. return details::e_default;
  11161. }
  11162. inline const T& v0()
  11163. {
  11164. return v0_;
  11165. }
  11166. inline const T& v1()
  11167. {
  11168. return v1_;
  11169. }
  11170. inline ufunc_t u0()
  11171. {
  11172. return u0_;
  11173. }
  11174. inline ufunc_t u1()
  11175. {
  11176. return u1_;
  11177. }
  11178. inline ufunc_t f()
  11179. {
  11180. return f_;
  11181. }
  11182. private:
  11183. uvouv_node(uvouv_node<T>&);
  11184. uvouv_node<T>& operator=(uvouv_node<T>&);
  11185. const T& v0_;
  11186. const T& v1_;
  11187. const ufunc_t u0_;
  11188. const ufunc_t u1_;
  11189. const bfunc_t f_;
  11190. };
  11191. template <typename T, typename Operation>
  11192. class unary_branch_node : public expression_node<T>
  11193. {
  11194. public:
  11195. typedef expression_node<T>* expression_ptr;
  11196. typedef Operation operation_t;
  11197. explicit unary_branch_node(expression_ptr brnch)
  11198. : branch_(brnch),
  11199. branch_deletable_(branch_deletable(branch_))
  11200. {}
  11201. ~unary_branch_node()
  11202. {
  11203. if (branch_ && branch_deletable_)
  11204. {
  11205. destroy_node(branch_);
  11206. }
  11207. }
  11208. inline T value() const
  11209. {
  11210. return Operation::process(branch_->value());
  11211. }
  11212. inline typename expression_node<T>::node_type type() const
  11213. {
  11214. return Operation::type();
  11215. }
  11216. inline operator_type operation() const
  11217. {
  11218. return Operation::operation();
  11219. }
  11220. inline expression_node<T>* branch(const std::size_t&) const
  11221. {
  11222. return branch_;
  11223. }
  11224. inline void release()
  11225. {
  11226. branch_deletable_ = false;
  11227. }
  11228. private:
  11229. unary_branch_node(unary_branch_node<T,Operation>&);
  11230. unary_branch_node<T,Operation>& operator=(unary_branch_node<T,Operation>&);
  11231. expression_ptr branch_;
  11232. bool branch_deletable_;
  11233. };
  11234. template <typename T> struct is_const { enum {result = 0}; };
  11235. template <typename T> struct is_const <const T> { enum {result = 1}; };
  11236. template <typename T> struct is_const_ref { enum {result = 0}; };
  11237. template <typename T> struct is_const_ref <const T&> { enum {result = 1}; };
  11238. template <typename T> struct is_ref { enum {result = 0}; };
  11239. template <typename T> struct is_ref<T&> { enum {result = 1}; };
  11240. template <typename T> struct is_ref<const T&> { enum {result = 0}; };
  11241. template <std::size_t State>
  11242. struct param_to_str { static std::string result() { static const std::string r("v"); return r; } };
  11243. template <>
  11244. struct param_to_str<0> { static std::string result() { static const std::string r("c"); return r; } };
  11245. #define exprtk_crtype(Type) \
  11246. param_to_str<is_const_ref< Type >::result>::result() \
  11247. template <typename T>
  11248. struct T0oT1oT2process
  11249. {
  11250. typedef typename details::functor_t<T> functor_t;
  11251. typedef typename functor_t::bfunc_t bfunc_t;
  11252. struct mode0
  11253. {
  11254. static inline T process(const T& t0, const T& t1, const T& t2, const bfunc_t bf0, const bfunc_t bf1)
  11255. {
  11256. // (T0 o0 T1) o1 T2
  11257. return bf1(bf0(t0,t1),t2);
  11258. }
  11259. template <typename T0, typename T1, typename T2>
  11260. static inline std::string id()
  11261. {
  11262. static const std::string result = "(" + exprtk_crtype(T0) + "o" +
  11263. exprtk_crtype(T1) + ")o(" +
  11264. exprtk_crtype(T2) + ")" ;
  11265. return result;
  11266. }
  11267. };
  11268. struct mode1
  11269. {
  11270. static inline T process(const T& t0, const T& t1, const T& t2, const bfunc_t bf0, const bfunc_t bf1)
  11271. {
  11272. // T0 o0 (T1 o1 T2)
  11273. return bf0(t0,bf1(t1,t2));
  11274. }
  11275. template <typename T0, typename T1, typename T2>
  11276. static inline std::string id()
  11277. {
  11278. static const std::string result = "(" + exprtk_crtype(T0) + ")o(" +
  11279. exprtk_crtype(T1) + "o" +
  11280. exprtk_crtype(T2) + ")" ;
  11281. return result;
  11282. }
  11283. };
  11284. };
  11285. template <typename T>
  11286. struct T0oT1oT20T3process
  11287. {
  11288. typedef typename details::functor_t<T> functor_t;
  11289. typedef typename functor_t::bfunc_t bfunc_t;
  11290. struct mode0
  11291. {
  11292. static inline T process(const T& t0, const T& t1,
  11293. const T& t2, const T& t3,
  11294. const bfunc_t bf0, const bfunc_t bf1, const bfunc_t bf2)
  11295. {
  11296. // (T0 o0 T1) o1 (T2 o2 T3)
  11297. return bf1(bf0(t0,t1),bf2(t2,t3));
  11298. }
  11299. template <typename T0, typename T1, typename T2, typename T3>
  11300. static inline std::string id()
  11301. {
  11302. static const std::string result = "(" + exprtk_crtype(T0) + "o" +
  11303. exprtk_crtype(T1) + ")o" +
  11304. "(" + exprtk_crtype(T2) + "o" +
  11305. exprtk_crtype(T3) + ")" ;
  11306. return result;
  11307. }
  11308. };
  11309. struct mode1
  11310. {
  11311. static inline T process(const T& t0, const T& t1,
  11312. const T& t2, const T& t3,
  11313. const bfunc_t bf0, const bfunc_t bf1, const bfunc_t bf2)
  11314. {
  11315. // (T0 o0 (T1 o1 (T2 o2 T3))
  11316. return bf0(t0,bf1(t1,bf2(t2,t3)));
  11317. }
  11318. template <typename T0, typename T1, typename T2, typename T3>
  11319. static inline std::string id()
  11320. {
  11321. static const std::string result = "(" + exprtk_crtype(T0) + ")o((" +
  11322. exprtk_crtype(T1) + ")o(" +
  11323. exprtk_crtype(T2) + "o" +
  11324. exprtk_crtype(T3) + "))" ;
  11325. return result;
  11326. }
  11327. };
  11328. struct mode2
  11329. {
  11330. static inline T process(const T& t0, const T& t1,
  11331. const T& t2, const T& t3,
  11332. const bfunc_t bf0, const bfunc_t bf1, const bfunc_t bf2)
  11333. {
  11334. // (T0 o0 ((T1 o1 T2) o2 T3)
  11335. return bf0(t0,bf2(bf1(t1,t2),t3));
  11336. }
  11337. template <typename T0, typename T1, typename T2, typename T3>
  11338. static inline std::string id()
  11339. {
  11340. static const std::string result = "(" + exprtk_crtype(T0) + ")o((" +
  11341. exprtk_crtype(T1) + "o" +
  11342. exprtk_crtype(T2) + ")o(" +
  11343. exprtk_crtype(T3) + "))" ;
  11344. return result;
  11345. }
  11346. };
  11347. struct mode3
  11348. {
  11349. static inline T process(const T& t0, const T& t1,
  11350. const T& t2, const T& t3,
  11351. const bfunc_t bf0, const bfunc_t bf1, const bfunc_t bf2)
  11352. {
  11353. // (((T0 o0 T1) o1 T2) o2 T3)
  11354. return bf2(bf1(bf0(t0,t1),t2),t3);
  11355. }
  11356. template <typename T0, typename T1, typename T2, typename T3>
  11357. static inline std::string id()
  11358. {
  11359. static const std::string result = "((" + exprtk_crtype(T0) + "o" +
  11360. exprtk_crtype(T1) + ")o(" +
  11361. exprtk_crtype(T2) + "))o(" +
  11362. exprtk_crtype(T3) + ")";
  11363. return result;
  11364. }
  11365. };
  11366. struct mode4
  11367. {
  11368. static inline T process(const T& t0, const T& t1,
  11369. const T& t2, const T& t3,
  11370. const bfunc_t bf0, const bfunc_t bf1, const bfunc_t bf2)
  11371. {
  11372. // ((T0 o0 (T1 o1 T2)) o2 T3
  11373. return bf2(bf0(t0,bf1(t1,t2)),t3);
  11374. }
  11375. template <typename T0, typename T1, typename T2, typename T3>
  11376. static inline std::string id()
  11377. {
  11378. static const std::string result = "((" + exprtk_crtype(T0) + ")o(" +
  11379. exprtk_crtype(T1) + "o" +
  11380. exprtk_crtype(T2) + "))o(" +
  11381. exprtk_crtype(T3) + ")" ;
  11382. return result;
  11383. }
  11384. };
  11385. };
  11386. #undef exprtk_crtype
  11387. template <typename T, typename T0, typename T1>
  11388. struct nodetype_T0oT1 { static const typename expression_node<T>::node_type result; };
  11389. template <typename T, typename T0, typename T1>
  11390. const typename expression_node<T>::node_type nodetype_T0oT1<T,T0,T1>::result = expression_node<T>::e_none;
  11391. #define synthesis_node_type_define(T0_,T1_,v_) \
  11392. template <typename T, typename T0, typename T1> \
  11393. struct nodetype_T0oT1<T,T0_,T1_> { static const typename expression_node<T>::node_type result; }; \
  11394. template <typename T, typename T0, typename T1> \
  11395. const typename expression_node<T>::node_type nodetype_T0oT1<T,T0_,T1_>::result = expression_node<T>:: v_; \
  11396. synthesis_node_type_define(const T0&, const T1&, e_vov)
  11397. synthesis_node_type_define(const T0&, const T1 , e_voc)
  11398. synthesis_node_type_define(const T0 , const T1&, e_cov)
  11399. synthesis_node_type_define( T0&, T1&, e_none)
  11400. synthesis_node_type_define(const T0 , const T1 , e_none)
  11401. synthesis_node_type_define( T0&, const T1 , e_none)
  11402. synthesis_node_type_define(const T0 , T1&, e_none)
  11403. synthesis_node_type_define(const T0&, T1&, e_none)
  11404. synthesis_node_type_define( T0&, const T1&, e_none)
  11405. #undef synthesis_node_type_define
  11406. template <typename T, typename T0, typename T1, typename T2>
  11407. struct nodetype_T0oT1oT2 { static const typename expression_node<T>::node_type result; };
  11408. template <typename T, typename T0, typename T1, typename T2>
  11409. const typename expression_node<T>::node_type nodetype_T0oT1oT2<T,T0,T1,T2>::result = expression_node<T>::e_none;
  11410. #define synthesis_node_type_define(T0_,T1_,T2_,v_) \
  11411. template <typename T, typename T0, typename T1, typename T2> \
  11412. struct nodetype_T0oT1oT2<T,T0_,T1_,T2_> { static const typename expression_node<T>::node_type result; }; \
  11413. template <typename T, typename T0, typename T1, typename T2> \
  11414. const typename expression_node<T>::node_type nodetype_T0oT1oT2<T,T0_,T1_,T2_>::result = expression_node<T>:: v_; \
  11415. synthesis_node_type_define(const T0&, const T1&, const T2&, e_vovov)
  11416. synthesis_node_type_define(const T0&, const T1&, const T2 , e_vovoc)
  11417. synthesis_node_type_define(const T0&, const T1 , const T2&, e_vocov)
  11418. synthesis_node_type_define(const T0 , const T1&, const T2&, e_covov)
  11419. synthesis_node_type_define(const T0 , const T1&, const T2 , e_covoc)
  11420. synthesis_node_type_define(const T0 , const T1 , const T2 , e_none )
  11421. synthesis_node_type_define(const T0 , const T1 , const T2&, e_none )
  11422. synthesis_node_type_define(const T0&, const T1 , const T2 , e_none )
  11423. synthesis_node_type_define( T0&, T1&, T2&, e_none )
  11424. #undef synthesis_node_type_define
  11425. template <typename T, typename T0, typename T1, typename T2, typename T3>
  11426. struct nodetype_T0oT1oT2oT3 { static const typename expression_node<T>::node_type result; };
  11427. template <typename T, typename T0, typename T1, typename T2, typename T3>
  11428. const typename expression_node<T>::node_type nodetype_T0oT1oT2oT3<T,T0,T1,T2,T3>::result = expression_node<T>::e_none;
  11429. #define synthesis_node_type_define(T0_,T1_,T2_,T3_,v_) \
  11430. template <typename T, typename T0, typename T1, typename T2, typename T3> \
  11431. struct nodetype_T0oT1oT2oT3<T,T0_,T1_,T2_,T3_> { static const typename expression_node<T>::node_type result; }; \
  11432. template <typename T, typename T0, typename T1, typename T2, typename T3> \
  11433. const typename expression_node<T>::node_type nodetype_T0oT1oT2oT3<T,T0_,T1_,T2_,T3_>::result = expression_node<T>:: v_; \
  11434. synthesis_node_type_define(const T0&, const T1&, const T2&, const T3&, e_vovovov)
  11435. synthesis_node_type_define(const T0&, const T1&, const T2&, const T3 , e_vovovoc)
  11436. synthesis_node_type_define(const T0&, const T1&, const T2 , const T3&, e_vovocov)
  11437. synthesis_node_type_define(const T0&, const T1 , const T2&, const T3&, e_vocovov)
  11438. synthesis_node_type_define(const T0 , const T1&, const T2&, const T3&, e_covovov)
  11439. synthesis_node_type_define(const T0 , const T1&, const T2 , const T3&, e_covocov)
  11440. synthesis_node_type_define(const T0&, const T1 , const T2&, const T3 , e_vocovoc)
  11441. synthesis_node_type_define(const T0 , const T1&, const T2&, const T3 , e_covovoc)
  11442. synthesis_node_type_define(const T0&, const T1 , const T2 , const T3&, e_vococov)
  11443. synthesis_node_type_define(const T0 , const T1 , const T2 , const T3 , e_none )
  11444. synthesis_node_type_define(const T0 , const T1 , const T2 , const T3&, e_none )
  11445. synthesis_node_type_define(const T0 , const T1 , const T2&, const T3 , e_none )
  11446. synthesis_node_type_define(const T0 , const T1&, const T2 , const T3 , e_none )
  11447. synthesis_node_type_define(const T0&, const T1 , const T2 , const T3 , e_none )
  11448. synthesis_node_type_define(const T0 , const T1 , const T2&, const T3&, e_none )
  11449. synthesis_node_type_define(const T0&, const T1&, const T2 , const T3 , e_none )
  11450. #undef synthesis_node_type_define
  11451. template <typename T, typename T0, typename T1>
  11452. class T0oT1 : public expression_node<T>
  11453. {
  11454. public:
  11455. typedef typename details::functor_t<T> functor_t;
  11456. typedef typename functor_t::bfunc_t bfunc_t;
  11457. typedef T value_type;
  11458. typedef T0oT1<T,T0,T1> node_type;
  11459. T0oT1(T0 p0, T1 p1, const bfunc_t p2)
  11460. : t0_(p0),
  11461. t1_(p1),
  11462. f_ (p2)
  11463. {}
  11464. inline typename expression_node<T>::node_type type() const
  11465. {
  11466. static const typename expression_node<T>::node_type result = nodetype_T0oT1<T,T0,T1>::result;
  11467. return result;
  11468. }
  11469. inline operator_type operation() const
  11470. {
  11471. return e_default;
  11472. }
  11473. inline T value() const
  11474. {
  11475. return f_(t0_,t1_);
  11476. }
  11477. inline T0 t0() const
  11478. {
  11479. return t0_;
  11480. }
  11481. inline T1 t1() const
  11482. {
  11483. return t1_;
  11484. }
  11485. inline bfunc_t f() const
  11486. {
  11487. return f_;
  11488. }
  11489. template <typename Allocator>
  11490. static inline expression_node<T>* allocate(Allocator& allocator,
  11491. T0 p0, T1 p1,
  11492. bfunc_t p2)
  11493. {
  11494. return allocator
  11495. .template allocate_type<node_type, T0, T1, bfunc_t&>
  11496. (p0, p1, p2);
  11497. }
  11498. private:
  11499. T0oT1(T0oT1<T,T0,T1>&) {}
  11500. T0oT1<T,T0,T1>& operator=(T0oT1<T,T0,T1>&) { return (*this); }
  11501. T0 t0_;
  11502. T1 t1_;
  11503. const bfunc_t f_;
  11504. };
  11505. template <typename T, typename T0, typename T1, typename T2, typename ProcessMode>
  11506. class T0oT1oT2 : public T0oT1oT2_base_node<T>
  11507. {
  11508. public:
  11509. typedef typename details::functor_t<T> functor_t;
  11510. typedef typename functor_t::bfunc_t bfunc_t;
  11511. typedef T value_type;
  11512. typedef T0oT1oT2<T,T0,T1,T2,ProcessMode> node_type;
  11513. typedef ProcessMode process_mode_t;
  11514. T0oT1oT2(T0 p0, T1 p1, T2 p2, const bfunc_t p3, const bfunc_t p4)
  11515. : t0_(p0),
  11516. t1_(p1),
  11517. t2_(p2),
  11518. f0_(p3),
  11519. f1_(p4)
  11520. {}
  11521. inline typename expression_node<T>::node_type type() const
  11522. {
  11523. static const typename expression_node<T>::node_type result = nodetype_T0oT1oT2<T,T0,T1,T2>::result;
  11524. return result;
  11525. }
  11526. inline operator_type operation() const
  11527. {
  11528. return e_default;
  11529. }
  11530. inline T value() const
  11531. {
  11532. return ProcessMode::process(t0_, t1_, t2_, f0_, f1_);
  11533. }
  11534. inline T0 t0() const
  11535. {
  11536. return t0_;
  11537. }
  11538. inline T1 t1() const
  11539. {
  11540. return t1_;
  11541. }
  11542. inline T2 t2() const
  11543. {
  11544. return t2_;
  11545. }
  11546. bfunc_t f0() const
  11547. {
  11548. return f0_;
  11549. }
  11550. bfunc_t f1() const
  11551. {
  11552. return f1_;
  11553. }
  11554. std::string type_id() const
  11555. {
  11556. return id();
  11557. }
  11558. static inline std::string id()
  11559. {
  11560. return process_mode_t::template id<T0,T1,T2>();
  11561. }
  11562. template <typename Allocator>
  11563. static inline expression_node<T>* allocate(Allocator& allocator, T0 p0, T1 p1, T2 p2, bfunc_t p3, bfunc_t p4)
  11564. {
  11565. return allocator
  11566. .template allocate_type<node_type, T0, T1, T2, bfunc_t, bfunc_t>
  11567. (p0, p1, p2, p3, p4);
  11568. }
  11569. private:
  11570. T0oT1oT2(node_type&) {}
  11571. node_type& operator=(node_type&) { return (*this); }
  11572. T0 t0_;
  11573. T1 t1_;
  11574. T2 t2_;
  11575. const bfunc_t f0_;
  11576. const bfunc_t f1_;
  11577. };
  11578. template <typename T, typename T0_, typename T1_, typename T2_, typename T3_, typename ProcessMode>
  11579. class T0oT1oT2oT3 : public T0oT1oT2oT3_base_node<T>
  11580. {
  11581. public:
  11582. typedef typename details::functor_t<T> functor_t;
  11583. typedef typename functor_t::bfunc_t bfunc_t;
  11584. typedef T value_type;
  11585. typedef T0_ T0;
  11586. typedef T1_ T1;
  11587. typedef T2_ T2;
  11588. typedef T3_ T3;
  11589. typedef T0oT1oT2oT3<T,T0,T1,T2,T3,ProcessMode> node_type;
  11590. typedef ProcessMode process_mode_t;
  11591. T0oT1oT2oT3(T0 p0, T1 p1, T2 p2, T3 p3, bfunc_t p4, bfunc_t p5, bfunc_t p6)
  11592. : t0_(p0),
  11593. t1_(p1),
  11594. t2_(p2),
  11595. t3_(p3),
  11596. f0_(p4),
  11597. f1_(p5),
  11598. f2_(p6)
  11599. {}
  11600. inline T value() const
  11601. {
  11602. return ProcessMode::process(t0_, t1_, t2_, t3_, f0_, f1_, f2_);
  11603. }
  11604. inline T0 t0() const
  11605. {
  11606. return t0_;
  11607. }
  11608. inline T1 t1() const
  11609. {
  11610. return t1_;
  11611. }
  11612. inline T2 t2() const
  11613. {
  11614. return t2_;
  11615. }
  11616. inline T3 t3() const
  11617. {
  11618. return t3_;
  11619. }
  11620. inline bfunc_t f0() const
  11621. {
  11622. return f0_;
  11623. }
  11624. inline bfunc_t f1() const
  11625. {
  11626. return f1_;
  11627. }
  11628. inline bfunc_t f2() const
  11629. {
  11630. return f2_;
  11631. }
  11632. inline std::string type_id() const
  11633. {
  11634. return id();
  11635. }
  11636. static inline std::string id()
  11637. {
  11638. return process_mode_t::template id<T0, T1, T2, T3>();
  11639. }
  11640. template <typename Allocator>
  11641. static inline expression_node<T>* allocate(Allocator& allocator,
  11642. T0 p0, T1 p1, T2 p2, T3 p3,
  11643. bfunc_t p4, bfunc_t p5, bfunc_t p6)
  11644. {
  11645. return allocator
  11646. .template allocate_type<node_type, T0, T1, T2, T3, bfunc_t, bfunc_t>
  11647. (p0, p1, p2, p3, p4, p5, p6);
  11648. }
  11649. private:
  11650. T0oT1oT2oT3(node_type&) {}
  11651. node_type& operator=(node_type&) { return (*this); }
  11652. T0 t0_;
  11653. T1 t1_;
  11654. T2 t2_;
  11655. T3 t3_;
  11656. const bfunc_t f0_;
  11657. const bfunc_t f1_;
  11658. const bfunc_t f2_;
  11659. };
  11660. template <typename T, typename T0, typename T1, typename T2>
  11661. class T0oT1oT2_sf3 : public T0oT1oT2_base_node<T>
  11662. {
  11663. public:
  11664. typedef typename details::functor_t<T> functor_t;
  11665. typedef typename functor_t::tfunc_t tfunc_t;
  11666. typedef T value_type;
  11667. typedef T0oT1oT2_sf3<T,T0,T1,T2> node_type;
  11668. T0oT1oT2_sf3(T0 p0, T1 p1, T2 p2, const tfunc_t p3)
  11669. : t0_(p0),
  11670. t1_(p1),
  11671. t2_(p2),
  11672. f_ (p3)
  11673. {}
  11674. inline typename expression_node<T>::node_type type() const
  11675. {
  11676. static const typename expression_node<T>::node_type result = nodetype_T0oT1oT2<T,T0,T1,T2>::result;
  11677. return result;
  11678. }
  11679. inline operator_type operation() const
  11680. {
  11681. return e_default;
  11682. }
  11683. inline T value() const
  11684. {
  11685. return f_(t0_, t1_, t2_);
  11686. }
  11687. inline T0 t0() const
  11688. {
  11689. return t0_;
  11690. }
  11691. inline T1 t1() const
  11692. {
  11693. return t1_;
  11694. }
  11695. inline T2 t2() const
  11696. {
  11697. return t2_;
  11698. }
  11699. tfunc_t f() const
  11700. {
  11701. return f_;
  11702. }
  11703. std::string type_id() const
  11704. {
  11705. return id();
  11706. }
  11707. static inline std::string id()
  11708. {
  11709. return "sf3";
  11710. }
  11711. template <typename Allocator>
  11712. static inline expression_node<T>* allocate(Allocator& allocator, T0 p0, T1 p1, T2 p2, tfunc_t p3)
  11713. {
  11714. return allocator
  11715. .template allocate_type<node_type, T0, T1, T2, tfunc_t>
  11716. (p0, p1, p2, p3);
  11717. }
  11718. private:
  11719. T0oT1oT2_sf3(node_type&) {}
  11720. node_type& operator=(node_type&) { return (*this); }
  11721. T0 t0_;
  11722. T1 t1_;
  11723. T2 t2_;
  11724. const tfunc_t f_;
  11725. };
  11726. template <typename T, typename T0, typename T1, typename T2>
  11727. class sf3ext_type_node : public T0oT1oT2_base_node<T>
  11728. {
  11729. public:
  11730. virtual ~sf3ext_type_node()
  11731. {}
  11732. virtual T0 t0() const = 0;
  11733. virtual T1 t1() const = 0;
  11734. virtual T2 t2() const = 0;
  11735. };
  11736. template <typename T, typename T0, typename T1, typename T2, typename SF3Operation>
  11737. class T0oT1oT2_sf3ext : public sf3ext_type_node<T,T0,T1,T2>
  11738. {
  11739. public:
  11740. typedef typename details::functor_t<T> functor_t;
  11741. typedef typename functor_t::tfunc_t tfunc_t;
  11742. typedef T value_type;
  11743. typedef T0oT1oT2_sf3ext<T,T0,T1,T2,SF3Operation> node_type;
  11744. T0oT1oT2_sf3ext(T0 p0, T1 p1, T2 p2)
  11745. : t0_(p0),
  11746. t1_(p1),
  11747. t2_(p2)
  11748. {}
  11749. inline typename expression_node<T>::node_type type() const
  11750. {
  11751. static const typename expression_node<T>::node_type result = nodetype_T0oT1oT2<T,T0,T1,T2>::result;
  11752. return result;
  11753. }
  11754. inline operator_type operation() const
  11755. {
  11756. return e_default;
  11757. }
  11758. inline T value() const
  11759. {
  11760. return SF3Operation::process(t0_, t1_, t2_);
  11761. }
  11762. T0 t0() const
  11763. {
  11764. return t0_;
  11765. }
  11766. T1 t1() const
  11767. {
  11768. return t1_;
  11769. }
  11770. T2 t2() const
  11771. {
  11772. return t2_;
  11773. }
  11774. std::string type_id() const
  11775. {
  11776. return id();
  11777. }
  11778. static inline std::string id()
  11779. {
  11780. return SF3Operation::id();
  11781. }
  11782. template <typename Allocator>
  11783. static inline expression_node<T>* allocate(Allocator& allocator, T0 p0, T1 p1, T2 p2)
  11784. {
  11785. return allocator
  11786. .template allocate_type<node_type, T0, T1, T2>
  11787. (p0, p1, p2);
  11788. }
  11789. private:
  11790. T0oT1oT2_sf3ext(node_type&) {}
  11791. node_type& operator=(node_type&) { return (*this); }
  11792. T0 t0_;
  11793. T1 t1_;
  11794. T2 t2_;
  11795. };
  11796. template <typename T>
  11797. inline bool is_sf3ext_node(const expression_node<T>* n)
  11798. {
  11799. switch (n->type())
  11800. {
  11801. case expression_node<T>::e_vovov : return true;
  11802. case expression_node<T>::e_vovoc : return true;
  11803. case expression_node<T>::e_vocov : return true;
  11804. case expression_node<T>::e_covov : return true;
  11805. case expression_node<T>::e_covoc : return true;
  11806. default : return false;
  11807. }
  11808. }
  11809. template <typename T, typename T0, typename T1, typename T2, typename T3>
  11810. class T0oT1oT2oT3_sf4 : public T0oT1oT2_base_node<T>
  11811. {
  11812. public:
  11813. typedef typename details::functor_t<T> functor_t;
  11814. typedef typename functor_t::qfunc_t qfunc_t;
  11815. typedef T value_type;
  11816. typedef T0oT1oT2oT3_sf4<T,T0,T1,T2,T3> node_type;
  11817. T0oT1oT2oT3_sf4(T0 p0, T1 p1, T2 p2, T3 p3, const qfunc_t p4)
  11818. : t0_(p0),
  11819. t1_(p1),
  11820. t2_(p2),
  11821. t3_(p3),
  11822. f_ (p4)
  11823. {}
  11824. inline typename expression_node<T>::node_type type() const
  11825. {
  11826. static const typename expression_node<T>::node_type result = nodetype_T0oT1oT2oT3<T,T0,T1,T2,T3>::result;
  11827. return result;
  11828. }
  11829. inline operator_type operation() const
  11830. {
  11831. return e_default;
  11832. }
  11833. inline T value() const
  11834. {
  11835. return f_(t0_, t1_, t2_, t3_);
  11836. }
  11837. inline T0 t0() const
  11838. {
  11839. return t0_;
  11840. }
  11841. inline T1 t1() const
  11842. {
  11843. return t1_;
  11844. }
  11845. inline T2 t2() const
  11846. {
  11847. return t2_;
  11848. }
  11849. inline T3 t3() const
  11850. {
  11851. return t3_;
  11852. }
  11853. qfunc_t f() const
  11854. {
  11855. return f_;
  11856. }
  11857. std::string type_id() const
  11858. {
  11859. return id();
  11860. }
  11861. static inline std::string id()
  11862. {
  11863. return "sf4";
  11864. }
  11865. template <typename Allocator>
  11866. static inline expression_node<T>* allocate(Allocator& allocator, T0 p0, T1 p1, T2 p2, T3 p3, qfunc_t p4)
  11867. {
  11868. return allocator
  11869. .template allocate_type<node_type, T0, T1, T2, T3, qfunc_t>
  11870. (p0, p1, p2, p3, p4);
  11871. }
  11872. private:
  11873. T0oT1oT2oT3_sf4(node_type&) {}
  11874. node_type& operator=(node_type&) { return (*this); }
  11875. T0 t0_;
  11876. T1 t1_;
  11877. T2 t2_;
  11878. T3 t3_;
  11879. const qfunc_t f_;
  11880. };
  11881. template <typename T, typename T0, typename T1, typename T2, typename T3, typename SF4Operation>
  11882. class T0oT1oT2oT3_sf4ext : public T0oT1oT2oT3_base_node<T>
  11883. {
  11884. public:
  11885. typedef typename details::functor_t<T> functor_t;
  11886. typedef typename functor_t::tfunc_t tfunc_t;
  11887. typedef T value_type;
  11888. typedef T0oT1oT2oT3_sf4ext<T,T0,T1,T2,T3,SF4Operation> node_type;
  11889. T0oT1oT2oT3_sf4ext(T0 p0, T1 p1, T2 p2, T3 p3)
  11890. : t0_(p0),
  11891. t1_(p1),
  11892. t2_(p2),
  11893. t3_(p3)
  11894. {}
  11895. inline typename expression_node<T>::node_type type() const
  11896. {
  11897. static const typename expression_node<T>::node_type result = nodetype_T0oT1oT2oT3<T,T0,T1,T2,T3>::result;
  11898. return result;
  11899. }
  11900. inline operator_type operation() const
  11901. {
  11902. return e_default;
  11903. }
  11904. inline T value() const
  11905. {
  11906. return SF4Operation::process(t0_, t1_, t2_, t3_);
  11907. }
  11908. inline T0 t0() const
  11909. {
  11910. return t0_;
  11911. }
  11912. inline T1 t1() const
  11913. {
  11914. return t1_;
  11915. }
  11916. inline T2 t2() const
  11917. {
  11918. return t2_;
  11919. }
  11920. inline T3 t3() const
  11921. {
  11922. return t3_;
  11923. }
  11924. std::string type_id() const
  11925. {
  11926. return id();
  11927. }
  11928. static inline std::string id()
  11929. {
  11930. return SF4Operation::id();
  11931. }
  11932. template <typename Allocator>
  11933. static inline expression_node<T>* allocate(Allocator& allocator, T0 p0, T1 p1, T2 p2, T3 p3)
  11934. {
  11935. return allocator
  11936. .template allocate_type<node_type, T0, T1, T2, T3>
  11937. (p0, p1, p2, p3);
  11938. }
  11939. private:
  11940. T0oT1oT2oT3_sf4ext(node_type&) {}
  11941. node_type& operator=(node_type&) { return (*this); }
  11942. T0 t0_;
  11943. T1 t1_;
  11944. T2 t2_;
  11945. T3 t3_;
  11946. };
  11947. template <typename T>
  11948. inline bool is_sf4ext_node(const expression_node<T>* n)
  11949. {
  11950. switch (n->type())
  11951. {
  11952. case expression_node<T>::e_vovovov : return true;
  11953. case expression_node<T>::e_vovovoc : return true;
  11954. case expression_node<T>::e_vovocov : return true;
  11955. case expression_node<T>::e_vocovov : return true;
  11956. case expression_node<T>::e_covovov : return true;
  11957. case expression_node<T>::e_covocov : return true;
  11958. case expression_node<T>::e_vocovoc : return true;
  11959. case expression_node<T>::e_covovoc : return true;
  11960. case expression_node<T>::e_vococov : return true;
  11961. default : return false;
  11962. }
  11963. }
  11964. template <typename T, typename T0, typename T1>
  11965. struct T0oT1_define
  11966. {
  11967. typedef details::T0oT1<T, T0, T1> type0;
  11968. };
  11969. template <typename T, typename T0, typename T1, typename T2>
  11970. struct T0oT1oT2_define
  11971. {
  11972. typedef details::T0oT1oT2<T, T0, T1, T2, typename T0oT1oT2process<T>::mode0> type0;
  11973. typedef details::T0oT1oT2<T, T0, T1, T2, typename T0oT1oT2process<T>::mode1> type1;
  11974. typedef details::T0oT1oT2_sf3<T, T0, T1, T2> sf3_type;
  11975. typedef details::sf3ext_type_node<T, T0, T1, T2> sf3_type_node;
  11976. };
  11977. template <typename T, typename T0, typename T1, typename T2, typename T3>
  11978. struct T0oT1oT2oT3_define
  11979. {
  11980. typedef details::T0oT1oT2oT3<T, T0, T1, T2, T3, typename T0oT1oT20T3process<T>::mode0> type0;
  11981. typedef details::T0oT1oT2oT3<T, T0, T1, T2, T3, typename T0oT1oT20T3process<T>::mode1> type1;
  11982. typedef details::T0oT1oT2oT3<T, T0, T1, T2, T3, typename T0oT1oT20T3process<T>::mode2> type2;
  11983. typedef details::T0oT1oT2oT3<T, T0, T1, T2, T3, typename T0oT1oT20T3process<T>::mode3> type3;
  11984. typedef details::T0oT1oT2oT3<T, T0, T1, T2, T3, typename T0oT1oT20T3process<T>::mode4> type4;
  11985. typedef details::T0oT1oT2oT3_sf4<T, T0, T1, T2, T3> sf4_type;
  11986. };
  11987. template <typename T, typename Operation>
  11988. class vov_node : public vov_base_node<T>
  11989. {
  11990. public:
  11991. typedef expression_node<T>* expression_ptr;
  11992. typedef Operation operation_t;
  11993. // variable op variable node
  11994. explicit vov_node(const T& var0, const T& var1)
  11995. : v0_(var0),
  11996. v1_(var1)
  11997. {}
  11998. inline T value() const
  11999. {
  12000. return Operation::process(v0_,v1_);
  12001. }
  12002. inline typename expression_node<T>::node_type type() const
  12003. {
  12004. return Operation::type();
  12005. }
  12006. inline operator_type operation() const
  12007. {
  12008. return Operation::operation();
  12009. }
  12010. inline const T& v0() const
  12011. {
  12012. return v0_;
  12013. }
  12014. inline const T& v1() const
  12015. {
  12016. return v1_;
  12017. }
  12018. protected:
  12019. const T& v0_;
  12020. const T& v1_;
  12021. private:
  12022. vov_node(vov_node<T,Operation>&);
  12023. vov_node<T,Operation>& operator=(vov_node<T,Operation>&);
  12024. };
  12025. template <typename T, typename Operation>
  12026. class cov_node : public cov_base_node<T>
  12027. {
  12028. public:
  12029. typedef expression_node<T>* expression_ptr;
  12030. typedef Operation operation_t;
  12031. // constant op variable node
  12032. explicit cov_node(const T& const_var, const T& var)
  12033. : c_(const_var),
  12034. v_(var)
  12035. {}
  12036. inline T value() const
  12037. {
  12038. return Operation::process(c_,v_);
  12039. }
  12040. inline typename expression_node<T>::node_type type() const
  12041. {
  12042. return Operation::type();
  12043. }
  12044. inline operator_type operation() const
  12045. {
  12046. return Operation::operation();
  12047. }
  12048. inline const T c() const
  12049. {
  12050. return c_;
  12051. }
  12052. inline const T& v() const
  12053. {
  12054. return v_;
  12055. }
  12056. protected:
  12057. const T c_;
  12058. const T& v_;
  12059. private:
  12060. cov_node(const cov_node<T,Operation>&);
  12061. cov_node<T,Operation>& operator=(const cov_node<T,Operation>&);
  12062. };
  12063. template <typename T, typename Operation>
  12064. class voc_node : public voc_base_node<T>
  12065. {
  12066. public:
  12067. typedef expression_node<T>* expression_ptr;
  12068. typedef Operation operation_t;
  12069. // variable op constant node
  12070. explicit voc_node(const T& var, const T& const_var)
  12071. : v_(var),
  12072. c_(const_var)
  12073. {}
  12074. inline T value() const
  12075. {
  12076. return Operation::process(v_,c_);
  12077. }
  12078. inline operator_type operation() const
  12079. {
  12080. return Operation::operation();
  12081. }
  12082. inline const T c() const
  12083. {
  12084. return c_;
  12085. }
  12086. inline const T& v() const
  12087. {
  12088. return v_;
  12089. }
  12090. protected:
  12091. const T& v_;
  12092. const T c_;
  12093. private:
  12094. voc_node(const voc_node<T,Operation>&);
  12095. voc_node<T,Operation>& operator=(const voc_node<T,Operation>&);
  12096. };
  12097. template <typename T, typename Operation>
  12098. class vob_node : public vob_base_node<T>
  12099. {
  12100. public:
  12101. typedef expression_node<T>* expression_ptr;
  12102. typedef std::pair<expression_ptr,bool> branch_t;
  12103. typedef Operation operation_t;
  12104. // variable op constant node
  12105. explicit vob_node(const T& var, const expression_ptr brnch)
  12106. : v_(var)
  12107. {
  12108. init_branches<1>(branch_,brnch);
  12109. }
  12110. ~vob_node()
  12111. {
  12112. cleanup_branches::execute<T,1>(branch_);
  12113. }
  12114. inline T value() const
  12115. {
  12116. return Operation::process(v_,branch_[0].first->value());
  12117. }
  12118. inline operator_type operation() const
  12119. {
  12120. return Operation::operation();
  12121. }
  12122. inline const T& v() const
  12123. {
  12124. return v_;
  12125. }
  12126. inline expression_node<T>* branch(const std::size_t&) const
  12127. {
  12128. return branch_[0].first;
  12129. }
  12130. private:
  12131. vob_node(const vob_node<T,Operation>&);
  12132. vob_node<T,Operation>& operator=(const vob_node<T,Operation>&);
  12133. const T& v_;
  12134. branch_t branch_[1];
  12135. };
  12136. template <typename T, typename Operation>
  12137. class bov_node : public bov_base_node<T>
  12138. {
  12139. public:
  12140. typedef expression_node<T>* expression_ptr;
  12141. typedef std::pair<expression_ptr,bool> branch_t;
  12142. typedef Operation operation_t;
  12143. // variable op constant node
  12144. explicit bov_node(const expression_ptr brnch, const T& var)
  12145. : v_(var)
  12146. {
  12147. init_branches<1>(branch_,brnch);
  12148. }
  12149. ~bov_node()
  12150. {
  12151. cleanup_branches::execute<T,1>(branch_);
  12152. }
  12153. inline T value() const
  12154. {
  12155. return Operation::process(branch_[0].first->value(),v_);
  12156. }
  12157. inline operator_type operation() const
  12158. {
  12159. return Operation::operation();
  12160. }
  12161. inline const T& v() const
  12162. {
  12163. return v_;
  12164. }
  12165. inline expression_node<T>* branch(const std::size_t&) const
  12166. {
  12167. return branch_[0].first;
  12168. }
  12169. private:
  12170. bov_node(const bov_node<T,Operation>&);
  12171. bov_node<T,Operation>& operator=(const bov_node<T,Operation>&);
  12172. const T& v_;
  12173. branch_t branch_[1];
  12174. };
  12175. template <typename T, typename Operation>
  12176. class cob_node : public cob_base_node<T>
  12177. {
  12178. public:
  12179. typedef expression_node<T>* expression_ptr;
  12180. typedef std::pair<expression_ptr,bool> branch_t;
  12181. typedef Operation operation_t;
  12182. // variable op constant node
  12183. explicit cob_node(const T const_var, const expression_ptr brnch)
  12184. : c_(const_var)
  12185. {
  12186. init_branches<1>(branch_,brnch);
  12187. }
  12188. ~cob_node()
  12189. {
  12190. cleanup_branches::execute<T,1>(branch_);
  12191. }
  12192. inline T value() const
  12193. {
  12194. return Operation::process(c_,branch_[0].first->value());
  12195. }
  12196. inline operator_type operation() const
  12197. {
  12198. return Operation::operation();
  12199. }
  12200. inline const T c() const
  12201. {
  12202. return c_;
  12203. }
  12204. inline void set_c(const T new_c)
  12205. {
  12206. (*const_cast<T*>(&c_)) = new_c;
  12207. }
  12208. inline expression_node<T>* branch(const std::size_t&) const
  12209. {
  12210. return branch_[0].first;
  12211. }
  12212. inline expression_node<T>* move_branch(const std::size_t&)
  12213. {
  12214. branch_[0].second = false;
  12215. return branch_[0].first;
  12216. }
  12217. private:
  12218. cob_node(const cob_node<T,Operation>&);
  12219. cob_node<T,Operation>& operator=(const cob_node<T,Operation>&);
  12220. const T c_;
  12221. branch_t branch_[1];
  12222. };
  12223. template <typename T, typename Operation>
  12224. class boc_node : public boc_base_node<T>
  12225. {
  12226. public:
  12227. typedef expression_node<T>* expression_ptr;
  12228. typedef std::pair<expression_ptr,bool> branch_t;
  12229. typedef Operation operation_t;
  12230. // variable op constant node
  12231. explicit boc_node(const expression_ptr brnch, const T const_var)
  12232. : c_(const_var)
  12233. {
  12234. init_branches<1>(branch_,brnch);
  12235. }
  12236. ~boc_node()
  12237. {
  12238. cleanup_branches::execute<T,1>(branch_);
  12239. }
  12240. inline T value() const
  12241. {
  12242. return Operation::process(branch_[0].first->value(),c_);
  12243. }
  12244. inline operator_type operation() const
  12245. {
  12246. return Operation::operation();
  12247. }
  12248. inline const T c() const
  12249. {
  12250. return c_;
  12251. }
  12252. inline void set_c(const T new_c)
  12253. {
  12254. (*const_cast<T*>(&c_)) = new_c;
  12255. }
  12256. inline expression_node<T>* branch(const std::size_t&) const
  12257. {
  12258. return branch_[0].first;
  12259. }
  12260. inline expression_node<T>* move_branch(const std::size_t&)
  12261. {
  12262. branch_[0].second = false;
  12263. return branch_[0].first;
  12264. }
  12265. private:
  12266. boc_node(const boc_node<T,Operation>&);
  12267. boc_node<T,Operation>& operator=(const boc_node<T,Operation>&);
  12268. const T c_;
  12269. branch_t branch_[1];
  12270. };
  12271. #ifndef exprtk_disable_string_capabilities
  12272. template <typename T, typename SType0, typename SType1, typename Operation>
  12273. class sos_node : public sos_base_node<T>
  12274. {
  12275. public:
  12276. typedef expression_node<T>* expression_ptr;
  12277. typedef Operation operation_t;
  12278. // string op string node
  12279. explicit sos_node(SType0 p0, SType1 p1)
  12280. : s0_(p0),
  12281. s1_(p1)
  12282. {}
  12283. inline T value() const
  12284. {
  12285. return Operation::process(s0_,s1_);
  12286. }
  12287. inline typename expression_node<T>::node_type type() const
  12288. {
  12289. return Operation::type();
  12290. }
  12291. inline operator_type operation() const
  12292. {
  12293. return Operation::operation();
  12294. }
  12295. inline std::string& s0()
  12296. {
  12297. return s0_;
  12298. }
  12299. inline std::string& s1()
  12300. {
  12301. return s1_;
  12302. }
  12303. protected:
  12304. SType0 s0_;
  12305. SType1 s1_;
  12306. private:
  12307. sos_node(sos_node<T,SType0,SType1,Operation>&);
  12308. sos_node<T,SType0,SType1,Operation>& operator=(sos_node<T,SType0,SType1,Operation>&);
  12309. };
  12310. template <typename T, typename SType0, typename SType1, typename RangePack, typename Operation>
  12311. class str_xrox_node : public sos_base_node<T>
  12312. {
  12313. public:
  12314. typedef expression_node<T>* expression_ptr;
  12315. typedef Operation operation_t;
  12316. // string-range op string node
  12317. explicit str_xrox_node(SType0 p0, SType1 p1, RangePack rp0)
  12318. : s0_ (p0 ),
  12319. s1_ (p1 ),
  12320. rp0_(rp0)
  12321. {}
  12322. ~str_xrox_node()
  12323. {
  12324. rp0_.free();
  12325. }
  12326. inline T value() const
  12327. {
  12328. std::size_t r0 = 0;
  12329. std::size_t r1 = 0;
  12330. if (rp0_(r0, r1, s0_.size()))
  12331. return Operation::process(s0_.substr(r0, (r1 - r0) + 1), s1_);
  12332. else
  12333. return T(0);
  12334. }
  12335. inline typename expression_node<T>::node_type type() const
  12336. {
  12337. return Operation::type();
  12338. }
  12339. inline operator_type operation() const
  12340. {
  12341. return Operation::operation();
  12342. }
  12343. inline std::string& s0()
  12344. {
  12345. return s0_;
  12346. }
  12347. inline std::string& s1()
  12348. {
  12349. return s1_;
  12350. }
  12351. protected:
  12352. SType0 s0_;
  12353. SType1 s1_;
  12354. RangePack rp0_;
  12355. private:
  12356. str_xrox_node(str_xrox_node<T,SType0,SType1,RangePack,Operation>&);
  12357. str_xrox_node<T,SType0,SType1,RangePack,Operation>& operator=(str_xrox_node<T,SType0,SType1,RangePack,Operation>&);
  12358. };
  12359. template <typename T, typename SType0, typename SType1, typename RangePack, typename Operation>
  12360. class str_xoxr_node : public sos_base_node<T>
  12361. {
  12362. public:
  12363. typedef expression_node<T>* expression_ptr;
  12364. typedef Operation operation_t;
  12365. // string op string range node
  12366. explicit str_xoxr_node(SType0 p0, SType1 p1, RangePack rp1)
  12367. : s0_ (p0 ),
  12368. s1_ (p1 ),
  12369. rp1_(rp1)
  12370. {}
  12371. ~str_xoxr_node()
  12372. {
  12373. rp1_.free();
  12374. }
  12375. inline T value() const
  12376. {
  12377. std::size_t r0 = 0;
  12378. std::size_t r1 = 0;
  12379. if (rp1_(r0, r1, s1_.size()))
  12380. return Operation::process(s0_, s1_.substr(r0, (r1 - r0) + 1));
  12381. else
  12382. return T(0);
  12383. }
  12384. inline typename expression_node<T>::node_type type() const
  12385. {
  12386. return Operation::type();
  12387. }
  12388. inline operator_type operation() const
  12389. {
  12390. return Operation::operation();
  12391. }
  12392. inline std::string& s0()
  12393. {
  12394. return s0_;
  12395. }
  12396. inline std::string& s1()
  12397. {
  12398. return s1_;
  12399. }
  12400. protected:
  12401. SType0 s0_;
  12402. SType1 s1_;
  12403. RangePack rp1_;
  12404. private:
  12405. str_xoxr_node(str_xoxr_node<T,SType0,SType1,RangePack,Operation>&);
  12406. str_xoxr_node<T,SType0,SType1,RangePack,Operation>& operator=(str_xoxr_node<T,SType0,SType1,RangePack,Operation>&);
  12407. };
  12408. template <typename T, typename SType0, typename SType1, typename RangePack, typename Operation>
  12409. class str_xroxr_node : public sos_base_node<T>
  12410. {
  12411. public:
  12412. typedef expression_node<T>* expression_ptr;
  12413. typedef Operation operation_t;
  12414. // string-range op string-range node
  12415. explicit str_xroxr_node(SType0 p0, SType1 p1, RangePack rp0, RangePack rp1)
  12416. : s0_ (p0 ),
  12417. s1_ (p1 ),
  12418. rp0_(rp0),
  12419. rp1_(rp1)
  12420. {}
  12421. ~str_xroxr_node()
  12422. {
  12423. rp0_.free();
  12424. rp1_.free();
  12425. }
  12426. inline T value() const
  12427. {
  12428. std::size_t r0_0 = 0;
  12429. std::size_t r0_1 = 0;
  12430. std::size_t r1_0 = 0;
  12431. std::size_t r1_1 = 0;
  12432. if (
  12433. rp0_(r0_0, r1_0, s0_.size()) &&
  12434. rp1_(r0_1, r1_1, s1_.size())
  12435. )
  12436. {
  12437. return Operation::process(
  12438. s0_.substr(r0_0, (r1_0 - r0_0) + 1),
  12439. s1_.substr(r0_1, (r1_1 - r0_1) + 1)
  12440. );
  12441. }
  12442. else
  12443. return T(0);
  12444. }
  12445. inline typename expression_node<T>::node_type type() const
  12446. {
  12447. return Operation::type();
  12448. }
  12449. inline operator_type operation() const
  12450. {
  12451. return Operation::operation();
  12452. }
  12453. inline std::string& s0()
  12454. {
  12455. return s0_;
  12456. }
  12457. inline std::string& s1()
  12458. {
  12459. return s1_;
  12460. }
  12461. protected:
  12462. SType0 s0_;
  12463. SType1 s1_;
  12464. RangePack rp0_;
  12465. RangePack rp1_;
  12466. private:
  12467. str_xroxr_node(str_xroxr_node<T,SType0,SType1,RangePack,Operation>&);
  12468. str_xroxr_node<T,SType0,SType1,RangePack,Operation>& operator=(str_xroxr_node<T,SType0,SType1,RangePack,Operation>&);
  12469. };
  12470. template <typename T, typename Operation>
  12471. class str_sogens_node : public binary_node<T>
  12472. {
  12473. public:
  12474. typedef expression_node <T>* expression_ptr;
  12475. typedef string_base_node<T>* str_base_ptr;
  12476. typedef range_pack <T> range_t;
  12477. typedef range_t* range_ptr;
  12478. typedef range_interface<T> irange_t;
  12479. typedef irange_t* irange_ptr;
  12480. str_sogens_node(const operator_type& opr,
  12481. expression_ptr branch0,
  12482. expression_ptr branch1)
  12483. : binary_node<T>(opr, branch0, branch1),
  12484. str0_base_ptr_ (0),
  12485. str1_base_ptr_ (0),
  12486. str0_range_ptr_(0),
  12487. str1_range_ptr_(0)
  12488. {
  12489. if (is_generally_string_node(binary_node<T>::branch_[0].first))
  12490. {
  12491. str0_base_ptr_ = dynamic_cast<str_base_ptr>(binary_node<T>::branch_[0].first);
  12492. if (0 == str0_base_ptr_)
  12493. return;
  12494. irange_ptr range = dynamic_cast<irange_ptr>(binary_node<T>::branch_[0].first);
  12495. if (0 == range)
  12496. return;
  12497. str0_range_ptr_ = &(range->range_ref());
  12498. }
  12499. if (is_generally_string_node(binary_node<T>::branch_[1].first))
  12500. {
  12501. str1_base_ptr_ = dynamic_cast<str_base_ptr>(binary_node<T>::branch_[1].first);
  12502. if (0 == str1_base_ptr_)
  12503. return;
  12504. irange_ptr range = dynamic_cast<irange_ptr>(binary_node<T>::branch_[1].first);
  12505. if (0 == range)
  12506. return;
  12507. str1_range_ptr_ = &(range->range_ref());
  12508. }
  12509. }
  12510. inline T value() const
  12511. {
  12512. if (
  12513. str0_base_ptr_ &&
  12514. str1_base_ptr_ &&
  12515. str0_range_ptr_ &&
  12516. str1_range_ptr_
  12517. )
  12518. {
  12519. binary_node<T>::branch_[0].first->value();
  12520. binary_node<T>::branch_[1].first->value();
  12521. std::size_t str0_r0 = 0;
  12522. std::size_t str0_r1 = 0;
  12523. std::size_t str1_r0 = 0;
  12524. std::size_t str1_r1 = 0;
  12525. range_t& range0 = (*str0_range_ptr_);
  12526. range_t& range1 = (*str1_range_ptr_);
  12527. if (
  12528. range0(str0_r0, str0_r1, str0_base_ptr_->size()) &&
  12529. range1(str1_r0, str1_r1, str1_base_ptr_->size())
  12530. )
  12531. {
  12532. return Operation::process(
  12533. str0_base_ptr_->str().substr(str0_r0,(str0_r1 - str0_r0) + 1),
  12534. str1_base_ptr_->str().substr(str1_r0,(str1_r1 - str1_r0) + 1)
  12535. );
  12536. }
  12537. }
  12538. return std::numeric_limits<T>::quiet_NaN();
  12539. }
  12540. inline typename expression_node<T>::node_type type() const
  12541. {
  12542. return Operation::type();
  12543. }
  12544. inline operator_type operation() const
  12545. {
  12546. return Operation::operation();
  12547. }
  12548. private:
  12549. str_sogens_node(str_sogens_node<T,Operation>&);
  12550. str_sogens_node<T,Operation>& operator=(str_sogens_node<T,Operation>&);
  12551. str_base_ptr str0_base_ptr_;
  12552. str_base_ptr str1_base_ptr_;
  12553. range_ptr str0_range_ptr_;
  12554. range_ptr str1_range_ptr_;
  12555. };
  12556. template <typename T, typename SType0, typename SType1, typename SType2, typename Operation>
  12557. class sosos_node : public sosos_base_node<T>
  12558. {
  12559. public:
  12560. typedef expression_node<T>* expression_ptr;
  12561. typedef Operation operation_t;
  12562. // variable op variable node
  12563. explicit sosos_node(SType0 p0, SType1 p1, SType2 p2)
  12564. : s0_(p0),
  12565. s1_(p1),
  12566. s2_(p2)
  12567. {}
  12568. inline T value() const
  12569. {
  12570. return Operation::process(s0_,s1_,s2_);
  12571. }
  12572. inline typename expression_node<T>::node_type type() const
  12573. {
  12574. return Operation::type();
  12575. }
  12576. inline operator_type operation() const
  12577. {
  12578. return Operation::operation();
  12579. }
  12580. inline std::string& s0()
  12581. {
  12582. return s0_;
  12583. }
  12584. inline std::string& s1()
  12585. {
  12586. return s1_;
  12587. }
  12588. inline std::string& s2()
  12589. {
  12590. return s2_;
  12591. }
  12592. protected:
  12593. SType0 s0_;
  12594. SType1 s1_;
  12595. SType2 s2_;
  12596. private:
  12597. sosos_node(sosos_node<T,SType0,SType1,SType2,Operation>&);
  12598. sosos_node<T,SType0,SType1,SType2,Operation>& operator=(sosos_node<T,SType0,SType1,SType2,Operation>&);
  12599. };
  12600. #endif
  12601. template <typename T, typename PowOp>
  12602. class ipow_node : public expression_node<T>
  12603. {
  12604. public:
  12605. typedef expression_node<T>* expression_ptr;
  12606. typedef PowOp operation_t;
  12607. explicit ipow_node(const T& v)
  12608. : v_(v)
  12609. {}
  12610. inline T value() const
  12611. {
  12612. return PowOp::result(v_);
  12613. }
  12614. inline typename expression_node<T>::node_type type() const
  12615. {
  12616. return expression_node<T>::e_ipow;
  12617. }
  12618. private:
  12619. ipow_node(const ipow_node<T,PowOp>&);
  12620. ipow_node<T,PowOp>& operator=(const ipow_node<T,PowOp>&);
  12621. const T& v_;
  12622. };
  12623. template <typename T, typename PowOp>
  12624. class bipow_node : public expression_node<T>
  12625. {
  12626. public:
  12627. typedef expression_node<T>* expression_ptr;
  12628. typedef std::pair<expression_ptr, bool> branch_t;
  12629. typedef PowOp operation_t;
  12630. explicit bipow_node(expression_ptr brnch)
  12631. {
  12632. init_branches<1>(branch_, brnch);
  12633. }
  12634. ~bipow_node()
  12635. {
  12636. cleanup_branches::execute<T,1>(branch_);
  12637. }
  12638. inline T value() const
  12639. {
  12640. return PowOp::result(branch_[0].first->value());
  12641. }
  12642. inline typename expression_node<T>::node_type type() const
  12643. {
  12644. return expression_node<T>::e_ipow;
  12645. }
  12646. private:
  12647. bipow_node(const bipow_node<T,PowOp>&);
  12648. bipow_node<T,PowOp>& operator=(const bipow_node<T,PowOp>&);
  12649. branch_t branch_[1];
  12650. };
  12651. template <typename T, typename PowOp>
  12652. class ipowinv_node : public expression_node<T>
  12653. {
  12654. public:
  12655. typedef expression_node<T>* expression_ptr;
  12656. typedef PowOp operation_t;
  12657. explicit ipowinv_node(const T& v)
  12658. : v_(v)
  12659. {}
  12660. inline T value() const
  12661. {
  12662. return (T(1) / PowOp::result(v_));
  12663. }
  12664. inline typename expression_node<T>::node_type type() const
  12665. {
  12666. return expression_node<T>::e_ipowinv;
  12667. }
  12668. private:
  12669. ipowinv_node(const ipowinv_node<T,PowOp>&);
  12670. ipowinv_node<T,PowOp>& operator=(const ipowinv_node<T,PowOp>&);
  12671. const T& v_;
  12672. };
  12673. template <typename T, typename PowOp>
  12674. class bipowninv_node : public expression_node<T>
  12675. {
  12676. public:
  12677. typedef expression_node<T>* expression_ptr;
  12678. typedef std::pair<expression_ptr, bool> branch_t;
  12679. typedef PowOp operation_t;
  12680. explicit bipowninv_node(expression_ptr brnch)
  12681. {
  12682. init_branches<1>(branch_, brnch);
  12683. }
  12684. ~bipowninv_node()
  12685. {
  12686. cleanup_branches::execute<T,1>(branch_);
  12687. }
  12688. inline T value() const
  12689. {
  12690. return (T(1) / PowOp::result(branch_[0].first->value()));
  12691. }
  12692. inline typename expression_node<T>::node_type type() const
  12693. {
  12694. return expression_node<T>::e_ipowinv;
  12695. }
  12696. private:
  12697. bipowninv_node(const bipowninv_node<T,PowOp>&);
  12698. bipowninv_node<T,PowOp>& operator=(const bipowninv_node<T,PowOp>&);
  12699. branch_t branch_[1];
  12700. };
  12701. template <typename T>
  12702. inline bool is_vov_node(const expression_node<T>* node)
  12703. {
  12704. return (0 != dynamic_cast<const vov_base_node<T>*>(node));
  12705. }
  12706. template <typename T>
  12707. inline bool is_cov_node(const expression_node<T>* node)
  12708. {
  12709. return (0 != dynamic_cast<const cov_base_node<T>*>(node));
  12710. }
  12711. template <typename T>
  12712. inline bool is_voc_node(const expression_node<T>* node)
  12713. {
  12714. return (0 != dynamic_cast<const voc_base_node<T>*>(node));
  12715. }
  12716. template <typename T>
  12717. inline bool is_cob_node(const expression_node<T>* node)
  12718. {
  12719. return (0 != dynamic_cast<const cob_base_node<T>*>(node));
  12720. }
  12721. template <typename T>
  12722. inline bool is_boc_node(const expression_node<T>* node)
  12723. {
  12724. return (0 != dynamic_cast<const boc_base_node<T>*>(node));
  12725. }
  12726. template <typename T>
  12727. inline bool is_t0ot1ot2_node(const expression_node<T>* node)
  12728. {
  12729. return (0 != dynamic_cast<const T0oT1oT2_base_node<T>*>(node));
  12730. }
  12731. template <typename T>
  12732. inline bool is_t0ot1ot2ot3_node(const expression_node<T>* node)
  12733. {
  12734. return (0 != dynamic_cast<const T0oT1oT2oT3_base_node<T>*>(node));
  12735. }
  12736. template <typename T>
  12737. inline bool is_uv_node(const expression_node<T>* node)
  12738. {
  12739. return (0 != dynamic_cast<const uv_base_node<T>*>(node));
  12740. }
  12741. template <typename T>
  12742. inline bool is_string_node(const expression_node<T>* node)
  12743. {
  12744. return node && (expression_node<T>::e_stringvar == node->type());
  12745. }
  12746. template <typename T>
  12747. inline bool is_string_range_node(const expression_node<T>* node)
  12748. {
  12749. return node && (expression_node<T>::e_stringvarrng == node->type());
  12750. }
  12751. template <typename T>
  12752. inline bool is_const_string_node(const expression_node<T>* node)
  12753. {
  12754. return node && (expression_node<T>::e_stringconst == node->type());
  12755. }
  12756. template <typename T>
  12757. inline bool is_const_string_range_node(const expression_node<T>* node)
  12758. {
  12759. return node && (expression_node<T>::e_cstringvarrng == node->type());
  12760. }
  12761. template <typename T>
  12762. inline bool is_string_assignment_node(const expression_node<T>* node)
  12763. {
  12764. return node && (expression_node<T>::e_strass == node->type());
  12765. }
  12766. template <typename T>
  12767. inline bool is_string_concat_node(const expression_node<T>* node)
  12768. {
  12769. return node && (expression_node<T>::e_strconcat == node->type());
  12770. }
  12771. template <typename T>
  12772. inline bool is_string_function_node(const expression_node<T>* node)
  12773. {
  12774. return node && (expression_node<T>::e_strfunction == node->type());
  12775. }
  12776. template <typename T>
  12777. inline bool is_string_condition_node(const expression_node<T>* node)
  12778. {
  12779. return node && (expression_node<T>::e_strcondition == node->type());
  12780. }
  12781. template <typename T>
  12782. inline bool is_string_ccondition_node(const expression_node<T>* node)
  12783. {
  12784. return node && (expression_node<T>::e_strccondition == node->type());
  12785. }
  12786. template <typename T>
  12787. inline bool is_string_vararg_node(const expression_node<T>* node)
  12788. {
  12789. return node && (expression_node<T>::e_stringvararg == node->type());
  12790. }
  12791. template <typename T>
  12792. inline bool is_genricstring_range_node(const expression_node<T>* node)
  12793. {
  12794. return node && (expression_node<T>::e_strgenrange == node->type());
  12795. }
  12796. template <typename T>
  12797. inline bool is_generally_string_node(const expression_node<T>* node)
  12798. {
  12799. if (node)
  12800. {
  12801. switch (node->type())
  12802. {
  12803. case expression_node<T>::e_stringvar :
  12804. case expression_node<T>::e_stringconst :
  12805. case expression_node<T>::e_stringvarrng :
  12806. case expression_node<T>::e_cstringvarrng :
  12807. case expression_node<T>::e_strgenrange :
  12808. case expression_node<T>::e_strass :
  12809. case expression_node<T>::e_strconcat :
  12810. case expression_node<T>::e_strfunction :
  12811. case expression_node<T>::e_strcondition :
  12812. case expression_node<T>::e_strccondition :
  12813. case expression_node<T>::e_stringvararg : return true;
  12814. default : return false;
  12815. }
  12816. }
  12817. return false;
  12818. }
  12819. class node_allocator
  12820. {
  12821. public:
  12822. template <typename ResultNode, typename OpType, typename ExprNode>
  12823. inline expression_node<typename ResultNode::value_type>* allocate(OpType& operation, ExprNode (&branch)[1])
  12824. {
  12825. return allocate<ResultNode>(operation, branch[0]);
  12826. }
  12827. template <typename ResultNode, typename OpType, typename ExprNode>
  12828. inline expression_node<typename ResultNode::value_type>* allocate(OpType& operation, ExprNode (&branch)[2])
  12829. {
  12830. return allocate<ResultNode>(operation, branch[0], branch[1]);
  12831. }
  12832. template <typename ResultNode, typename OpType, typename ExprNode>
  12833. inline expression_node<typename ResultNode::value_type>* allocate(OpType& operation, ExprNode (&branch)[3])
  12834. {
  12835. return allocate<ResultNode>(operation, branch[0], branch[1], branch[2]);
  12836. }
  12837. template <typename ResultNode, typename OpType, typename ExprNode>
  12838. inline expression_node<typename ResultNode::value_type>* allocate(OpType& operation, ExprNode (&branch)[4])
  12839. {
  12840. return allocate<ResultNode>(operation, branch[0], branch[1], branch[2], branch[3]);
  12841. }
  12842. template <typename ResultNode, typename OpType, typename ExprNode>
  12843. inline expression_node<typename ResultNode::value_type>* allocate(OpType& operation, ExprNode (&branch)[5])
  12844. {
  12845. return allocate<ResultNode>(operation, branch[0],branch[1], branch[2], branch[3], branch[4]);
  12846. }
  12847. template <typename ResultNode, typename OpType, typename ExprNode>
  12848. inline expression_node<typename ResultNode::value_type>* allocate(OpType& operation, ExprNode (&branch)[6])
  12849. {
  12850. return allocate<ResultNode>(operation, branch[0], branch[1], branch[2], branch[3], branch[4], branch[5]);
  12851. }
  12852. template <typename node_type>
  12853. inline expression_node<typename node_type::value_type>* allocate() const
  12854. {
  12855. return (new node_type());
  12856. }
  12857. template <typename node_type,
  12858. typename Type,
  12859. typename Allocator,
  12860. template <typename, typename> class Sequence>
  12861. inline expression_node<typename node_type::value_type>* allocate(const Sequence<Type,Allocator>& seq) const
  12862. {
  12863. return (new node_type(seq));
  12864. }
  12865. template <typename node_type, typename T1>
  12866. inline expression_node<typename node_type::value_type>* allocate(T1& t1) const
  12867. {
  12868. return (new node_type(t1));
  12869. }
  12870. template <typename node_type, typename T1>
  12871. inline expression_node<typename node_type::value_type>* allocate_c(const T1& t1) const
  12872. {
  12873. return (new node_type(t1));
  12874. }
  12875. template <typename node_type,
  12876. typename T1, typename T2>
  12877. inline expression_node<typename node_type::value_type>* allocate(const T1& t1, const T2& t2) const
  12878. {
  12879. return (new node_type(t1, t2));
  12880. }
  12881. template <typename node_type,
  12882. typename T1, typename T2>
  12883. inline expression_node<typename node_type::value_type>* allocate_cr(const T1& t1, T2& t2) const
  12884. {
  12885. return (new node_type(t1, t2));
  12886. }
  12887. template <typename node_type,
  12888. typename T1, typename T2>
  12889. inline expression_node<typename node_type::value_type>* allocate_rc(T1& t1, const T2& t2) const
  12890. {
  12891. return (new node_type(t1, t2));
  12892. }
  12893. template <typename node_type,
  12894. typename T1, typename T2>
  12895. inline expression_node<typename node_type::value_type>* allocate_rr(T1& t1, T2& t2) const
  12896. {
  12897. return (new node_type(t1, t2));
  12898. }
  12899. template <typename node_type,
  12900. typename T1, typename T2>
  12901. inline expression_node<typename node_type::value_type>* allocate_tt(T1 t1, T2 t2) const
  12902. {
  12903. return (new node_type(t1, t2));
  12904. }
  12905. template <typename node_type,
  12906. typename T1, typename T2, typename T3>
  12907. inline expression_node<typename node_type::value_type>* allocate_ttt(T1 t1, T2 t2, T3 t3) const
  12908. {
  12909. return (new node_type(t1, t2, t3));
  12910. }
  12911. template <typename node_type,
  12912. typename T1, typename T2, typename T3, typename T4>
  12913. inline expression_node<typename node_type::value_type>* allocate_tttt(T1 t1, T2 t2, T3 t3, T4 t4) const
  12914. {
  12915. return (new node_type(t1, t2, t3, t4));
  12916. }
  12917. template <typename node_type,
  12918. typename T1, typename T2, typename T3>
  12919. inline expression_node<typename node_type::value_type>* allocate_rrr(T1& t1, T2& t2, T3& t3) const
  12920. {
  12921. return (new node_type(t1, t2, t3));
  12922. }
  12923. template <typename node_type,
  12924. typename T1, typename T2, typename T3, typename T4>
  12925. inline expression_node<typename node_type::value_type>* allocate_rrrr(T1& t1, T2& t2, T3& t3, T4& t4) const
  12926. {
  12927. return (new node_type(t1, t2, t3, t4));
  12928. }
  12929. template <typename node_type,
  12930. typename T1, typename T2, typename T3, typename T4, typename T5>
  12931. inline expression_node<typename node_type::value_type>* allocate_rrrrr(T1& t1, T2& t2, T3& t3, T4& t4, T5& t5) const
  12932. {
  12933. return (new node_type(t1, t2, t3, t4, t5));
  12934. }
  12935. template <typename node_type,
  12936. typename T1, typename T2, typename T3>
  12937. inline expression_node<typename node_type::value_type>* allocate(const T1& t1, const T2& t2,
  12938. const T3& t3) const
  12939. {
  12940. return (new node_type(t1, t2, t3));
  12941. }
  12942. template <typename node_type,
  12943. typename T1, typename T2,
  12944. typename T3, typename T4>
  12945. inline expression_node<typename node_type::value_type>* allocate(const T1& t1, const T2& t2,
  12946. const T3& t3, const T4& t4) const
  12947. {
  12948. return (new node_type(t1, t2, t3, t4));
  12949. }
  12950. template <typename node_type,
  12951. typename T1, typename T2,
  12952. typename T3, typename T4, typename T5>
  12953. inline expression_node<typename node_type::value_type>* allocate(const T1& t1, const T2& t2,
  12954. const T3& t3, const T4& t4,
  12955. const T5& t5) const
  12956. {
  12957. return (new node_type(t1, t2, t3, t4, t5));
  12958. }
  12959. template <typename node_type,
  12960. typename T1, typename T2,
  12961. typename T3, typename T4, typename T5, typename T6>
  12962. inline expression_node<typename node_type::value_type>* allocate(const T1& t1, const T2& t2,
  12963. const T3& t3, const T4& t4,
  12964. const T5& t5, const T6& t6) const
  12965. {
  12966. return (new node_type(t1, t2, t3, t4, t5, t6));
  12967. }
  12968. template <typename node_type,
  12969. typename T1, typename T2,
  12970. typename T3, typename T4,
  12971. typename T5, typename T6, typename T7>
  12972. inline expression_node<typename node_type::value_type>* allocate(const T1& t1, const T2& t2,
  12973. const T3& t3, const T4& t4,
  12974. const T5& t5, const T6& t6,
  12975. const T7& t7) const
  12976. {
  12977. return (new node_type(t1, t2, t3, t4, t5, t6, t7));
  12978. }
  12979. template <typename node_type,
  12980. typename T1, typename T2,
  12981. typename T3, typename T4,
  12982. typename T5, typename T6,
  12983. typename T7, typename T8>
  12984. inline expression_node<typename node_type::value_type>* allocate(const T1& t1, const T2& t2,
  12985. const T3& t3, const T4& t4,
  12986. const T5& t5, const T6& t6,
  12987. const T7& t7, const T8& t8) const
  12988. {
  12989. return (new node_type(t1, t2, t3, t4, t5, t6, t7, t8));
  12990. }
  12991. template <typename node_type,
  12992. typename T1, typename T2,
  12993. typename T3, typename T4,
  12994. typename T5, typename T6,
  12995. typename T7, typename T8, typename T9>
  12996. inline expression_node<typename node_type::value_type>* allocate(const T1& t1, const T2& t2,
  12997. const T3& t3, const T4& t4,
  12998. const T5& t5, const T6& t6,
  12999. const T7& t7, const T8& t8,
  13000. const T9& t9) const
  13001. {
  13002. return (new node_type(t1, t2, t3, t4, t5, t6, t7, t8, t9));
  13003. }
  13004. template <typename node_type,
  13005. typename T1, typename T2,
  13006. typename T3, typename T4,
  13007. typename T5, typename T6,
  13008. typename T7, typename T8,
  13009. typename T9, typename T10>
  13010. inline expression_node<typename node_type::value_type>* allocate(const T1& t1, const T2& t2,
  13011. const T3& t3, const T4& t4,
  13012. const T5& t5, const T6& t6,
  13013. const T7& t7, const T8& t8,
  13014. const T9& t9, const T10& t10) const
  13015. {
  13016. return (new node_type(t1, t2, t3, t4, t5, t6, t7, t8, t9, t10));
  13017. }
  13018. template <typename node_type,
  13019. typename T1, typename T2, typename T3>
  13020. inline expression_node<typename node_type::value_type>* allocate_type(T1 t1, T2 t2, T3 t3) const
  13021. {
  13022. return (new node_type(t1, t2, t3));
  13023. }
  13024. template <typename node_type,
  13025. typename T1, typename T2,
  13026. typename T3, typename T4>
  13027. inline expression_node<typename node_type::value_type>* allocate_type(T1 t1, T2 t2,
  13028. T3 t3, T4 t4) const
  13029. {
  13030. return (new node_type(t1, t2, t3, t4));
  13031. }
  13032. template <typename node_type,
  13033. typename T1, typename T2,
  13034. typename T3, typename T4,
  13035. typename T5>
  13036. inline expression_node<typename node_type::value_type>* allocate_type(T1 t1, T2 t2,
  13037. T3 t3, T4 t4,
  13038. T5 t5) const
  13039. {
  13040. return (new node_type(t1, t2, t3, t4, t5));
  13041. }
  13042. template <typename node_type,
  13043. typename T1, typename T2,
  13044. typename T3, typename T4,
  13045. typename T5, typename T6>
  13046. inline expression_node<typename node_type::value_type>* allocate_type(T1 t1, T2 t2,
  13047. T3 t3, T4 t4,
  13048. T5 t5, T6 t6) const
  13049. {
  13050. return (new node_type(t1, t2, t3, t4, t5, t6));
  13051. }
  13052. template <typename node_type,
  13053. typename T1, typename T2,
  13054. typename T3, typename T4,
  13055. typename T5, typename T6, typename T7>
  13056. inline expression_node<typename node_type::value_type>* allocate_type(T1 t1, T2 t2,
  13057. T3 t3, T4 t4,
  13058. T5 t5, T6 t6,
  13059. T7 t7) const
  13060. {
  13061. return (new node_type(t1, t2, t3, t4, t5, t6, t7));
  13062. }
  13063. template <typename T>
  13064. void inline free(expression_node<T>*& e) const
  13065. {
  13066. delete e;
  13067. e = 0;
  13068. }
  13069. };
  13070. inline void load_operations_map(std::multimap<std::string,details::base_operation_t,details::ilesscompare>& m)
  13071. {
  13072. #define register_op(Symbol,Type,Args) \
  13073. m.insert(std::make_pair(std::string(Symbol),details::base_operation_t(Type,Args))); \
  13074. register_op( "abs", e_abs , 1)
  13075. register_op( "acos", e_acos , 1)
  13076. register_op( "acosh", e_acosh , 1)
  13077. register_op( "asin", e_asin , 1)
  13078. register_op( "asinh", e_asinh , 1)
  13079. register_op( "atan", e_atan , 1)
  13080. register_op( "atanh", e_atanh , 1)
  13081. register_op( "ceil", e_ceil , 1)
  13082. register_op( "cos", e_cos , 1)
  13083. register_op( "cosh", e_cosh , 1)
  13084. register_op( "exp", e_exp , 1)
  13085. register_op( "expm1", e_expm1 , 1)
  13086. register_op( "floor", e_floor , 1)
  13087. register_op( "log", e_log , 1)
  13088. register_op( "log10", e_log10 , 1)
  13089. register_op( "log2", e_log2 , 1)
  13090. register_op( "log1p", e_log1p , 1)
  13091. register_op( "round", e_round , 1)
  13092. register_op( "sin", e_sin , 1)
  13093. register_op( "sinc", e_sinc , 1)
  13094. register_op( "sinh", e_sinh , 1)
  13095. register_op( "sec", e_sec , 1)
  13096. register_op( "csc", e_csc , 1)
  13097. register_op( "sqrt", e_sqrt , 1)
  13098. register_op( "tan", e_tan , 1)
  13099. register_op( "tanh", e_tanh , 1)
  13100. register_op( "cot", e_cot , 1)
  13101. register_op( "rad2deg", e_r2d , 1)
  13102. register_op( "deg2rad", e_d2r , 1)
  13103. register_op( "deg2grad", e_d2g , 1)
  13104. register_op( "grad2deg", e_g2d , 1)
  13105. register_op( "sgn", e_sgn , 1)
  13106. register_op( "not", e_notl , 1)
  13107. register_op( "erf", e_erf , 1)
  13108. register_op( "erfc", e_erfc , 1)
  13109. register_op( "ncdf", e_ncdf , 1)
  13110. register_op( "frac", e_frac , 1)
  13111. register_op( "trunc", e_trunc , 1)
  13112. register_op( "atan2", e_atan2 , 2)
  13113. register_op( "mod", e_mod , 2)
  13114. register_op( "logn", e_logn , 2)
  13115. register_op( "pow", e_pow , 2)
  13116. register_op( "root", e_root , 2)
  13117. register_op( "roundn", e_roundn , 2)
  13118. register_op( "equal", e_equal , 2)
  13119. register_op("not_equal", e_nequal , 2)
  13120. register_op( "hypot", e_hypot , 2)
  13121. register_op( "shr", e_shr , 2)
  13122. register_op( "shl", e_shl , 2)
  13123. register_op( "clamp", e_clamp , 3)
  13124. register_op( "iclamp", e_iclamp , 3)
  13125. register_op( "inrange", e_inrange , 3)
  13126. #undef register_op
  13127. }
  13128. } // namespace details
  13129. class function_traits
  13130. {
  13131. public:
  13132. function_traits()
  13133. : allow_zero_parameters_(false),
  13134. has_side_effects_(true),
  13135. min_num_args_(0),
  13136. max_num_args_(std::numeric_limits<std::size_t>::max())
  13137. {}
  13138. inline bool& allow_zero_parameters()
  13139. {
  13140. return allow_zero_parameters_;
  13141. }
  13142. inline bool& has_side_effects()
  13143. {
  13144. return has_side_effects_;
  13145. }
  13146. std::size_t& min_num_args()
  13147. {
  13148. return min_num_args_;
  13149. }
  13150. std::size_t& max_num_args()
  13151. {
  13152. return max_num_args_;
  13153. }
  13154. private:
  13155. bool allow_zero_parameters_;
  13156. bool has_side_effects_;
  13157. std::size_t min_num_args_;
  13158. std::size_t max_num_args_;
  13159. };
  13160. template <typename FunctionType>
  13161. void enable_zero_parameters(FunctionType& func)
  13162. {
  13163. func.allow_zero_parameters() = true;
  13164. if (0 != func.min_num_args())
  13165. {
  13166. func.min_num_args() = 0;
  13167. }
  13168. }
  13169. template <typename FunctionType>
  13170. void disable_zero_parameters(FunctionType& func)
  13171. {
  13172. func.allow_zero_parameters() = false;
  13173. }
  13174. template <typename FunctionType>
  13175. void enable_has_side_effects(FunctionType& func)
  13176. {
  13177. func.has_side_effects() = true;
  13178. }
  13179. template <typename FunctionType>
  13180. void disable_has_side_effects(FunctionType& func)
  13181. {
  13182. func.has_side_effects() = false;
  13183. }
  13184. template <typename FunctionType>
  13185. void set_min_num_args(FunctionType& func, const std::size_t& num_args)
  13186. {
  13187. func.min_num_args() = num_args;
  13188. if ((0 != func.min_num_args()) && func.allow_zero_parameters())
  13189. func.allow_zero_parameters() = false;
  13190. }
  13191. template <typename FunctionType>
  13192. void set_max_num_args(FunctionType& func, const std::size_t& num_args)
  13193. {
  13194. func.max_num_args() = num_args;
  13195. }
  13196. template <typename T>
  13197. class ifunction : public function_traits
  13198. {
  13199. public:
  13200. explicit ifunction(const std::size_t& pc)
  13201. : param_count(pc)
  13202. {}
  13203. virtual ~ifunction()
  13204. {}
  13205. #define empty_method_body \
  13206. { \
  13207. return std::numeric_limits<T>::quiet_NaN(); \
  13208. } \
  13209. inline virtual T operator() ()
  13210. empty_method_body
  13211. inline virtual T operator() (const T&)
  13212. empty_method_body
  13213. inline virtual T operator() (const T&,const T&)
  13214. empty_method_body
  13215. inline virtual T operator() (const T&, const T&, const T&)
  13216. empty_method_body
  13217. inline virtual T operator() (const T&, const T&, const T&, const T&)
  13218. empty_method_body
  13219. inline virtual T operator() (const T&, const T&, const T&, const T&, const T&)
  13220. empty_method_body
  13221. inline virtual T operator() (const T&, const T&, const T&, const T&, const T&, const T&)
  13222. empty_method_body
  13223. inline virtual T operator() (const T&, const T&, const T&, const T&, const T&, const T&, const T&)
  13224. empty_method_body
  13225. inline virtual T operator() (const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&)
  13226. empty_method_body
  13227. inline virtual T operator() (const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&)
  13228. empty_method_body
  13229. inline virtual T operator() (const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&)
  13230. empty_method_body
  13231. inline virtual T operator() (const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&,
  13232. const T&)
  13233. empty_method_body
  13234. inline virtual T operator() (const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&,
  13235. const T&, const T&)
  13236. empty_method_body
  13237. inline virtual T operator() (const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&,
  13238. const T&, const T&, const T&)
  13239. empty_method_body
  13240. inline virtual T operator() (const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&,
  13241. const T&, const T&, const T&, const T&)
  13242. empty_method_body
  13243. inline virtual T operator() (const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&,
  13244. const T&, const T&, const T&, const T&, const T&)
  13245. empty_method_body
  13246. inline virtual T operator() (const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&,
  13247. const T&, const T&, const T&, const T&, const T&, const T&)
  13248. empty_method_body
  13249. inline virtual T operator() (const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&,
  13250. const T&, const T&, const T&, const T&, const T&, const T&, const T&)
  13251. empty_method_body
  13252. inline virtual T operator() (const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&,
  13253. const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&)
  13254. empty_method_body
  13255. inline virtual T operator() (const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&,
  13256. const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&)
  13257. empty_method_body
  13258. inline virtual T operator() (const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&,
  13259. const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&, const T&)
  13260. empty_method_body
  13261. #undef empty_method_body
  13262. std::size_t param_count;
  13263. };
  13264. template <typename T>
  13265. class ivararg_function : public function_traits
  13266. {
  13267. public:
  13268. virtual ~ivararg_function()
  13269. {}
  13270. inline virtual T operator() (const std::vector<T>&)
  13271. {
  13272. exprtk_debug(("ivararg_function::operator() - Operator has not been overridden.\n"));
  13273. return std::numeric_limits<T>::quiet_NaN();
  13274. }
  13275. };
  13276. template <typename T>
  13277. class igeneric_function : public function_traits
  13278. {
  13279. public:
  13280. enum return_type
  13281. {
  13282. e_rtrn_scalar = 0,
  13283. e_rtrn_string = 1,
  13284. e_rtrn_overload = 2
  13285. };
  13286. typedef T type;
  13287. typedef type_store<T> generic_type;
  13288. typedef typename generic_type::parameter_list parameter_list_t;
  13289. igeneric_function(const std::string& param_seq = "", const return_type rtr_type = e_rtrn_scalar)
  13290. : parameter_sequence(param_seq),
  13291. rtrn_type(rtr_type)
  13292. {}
  13293. virtual ~igeneric_function()
  13294. {}
  13295. #define igeneric_function_empty_body(N) \
  13296. { \
  13297. exprtk_debug(("igeneric_function::operator() - Operator has not been overridden. ["#N"]\n")); \
  13298. return std::numeric_limits<T>::quiet_NaN(); \
  13299. } \
  13300. // f(i_0,i_1,....,i_N) --> Scalar
  13301. inline virtual T operator() (parameter_list_t)
  13302. igeneric_function_empty_body(1)
  13303. // f(i_0,i_1,....,i_N) --> String
  13304. inline virtual T operator() (std::string&, parameter_list_t)
  13305. igeneric_function_empty_body(2)
  13306. // f(psi,i_0,i_1,....,i_N) --> Scalar
  13307. inline virtual T operator() (const std::size_t&, parameter_list_t)
  13308. igeneric_function_empty_body(3)
  13309. // f(psi,i_0,i_1,....,i_N) --> String
  13310. inline virtual T operator() (const std::size_t&, std::string&, parameter_list_t)
  13311. igeneric_function_empty_body(4)
  13312. std::string parameter_sequence;
  13313. return_type rtrn_type;
  13314. };
  13315. template <typename T> class parser;
  13316. template <typename T> class expression_helper;
  13317. template <typename T>
  13318. class symbol_table
  13319. {
  13320. public:
  13321. typedef T (*ff00_functor)();
  13322. typedef T (*ff01_functor)(T);
  13323. typedef T (*ff02_functor)(T, T);
  13324. typedef T (*ff03_functor)(T, T, T);
  13325. typedef T (*ff04_functor)(T, T, T, T);
  13326. typedef T (*ff05_functor)(T, T, T, T, T);
  13327. typedef T (*ff06_functor)(T, T, T, T, T, T);
  13328. typedef T (*ff07_functor)(T, T, T, T, T, T, T);
  13329. typedef T (*ff08_functor)(T, T, T, T, T, T, T, T);
  13330. typedef T (*ff09_functor)(T, T, T, T, T, T, T, T, T);
  13331. typedef T (*ff10_functor)(T, T, T, T, T, T, T, T, T, T);
  13332. typedef T (*ff11_functor)(T, T, T, T, T, T, T, T, T, T, T);
  13333. typedef T (*ff12_functor)(T, T, T, T, T, T, T, T, T, T, T, T);
  13334. typedef T (*ff13_functor)(T, T, T, T, T, T, T, T, T, T, T, T, T);
  13335. typedef T (*ff14_functor)(T, T, T, T, T, T, T, T, T, T, T, T, T, T);
  13336. typedef T (*ff15_functor)(T, T, T, T, T, T, T, T, T, T, T, T, T, T, T);
  13337. protected:
  13338. struct freefunc00 : public exprtk::ifunction<T>
  13339. {
  13340. using exprtk::ifunction<T>::operator();
  13341. explicit freefunc00(ff00_functor ff) : exprtk::ifunction<T>(0), f(ff) {}
  13342. inline T operator() ()
  13343. { return f(); }
  13344. ff00_functor f;
  13345. };
  13346. struct freefunc01 : public exprtk::ifunction<T>
  13347. {
  13348. using exprtk::ifunction<T>::operator();
  13349. explicit freefunc01(ff01_functor ff) : exprtk::ifunction<T>(1), f(ff) {}
  13350. inline T operator() (const T& v0)
  13351. { return f(v0); }
  13352. ff01_functor f;
  13353. };
  13354. struct freefunc02 : public exprtk::ifunction<T>
  13355. {
  13356. using exprtk::ifunction<T>::operator();
  13357. explicit freefunc02(ff02_functor ff) : exprtk::ifunction<T>(2), f(ff) {}
  13358. inline T operator() (const T& v0, const T& v1)
  13359. { return f(v0, v1); }
  13360. ff02_functor f;
  13361. };
  13362. struct freefunc03 : public exprtk::ifunction<T>
  13363. {
  13364. using exprtk::ifunction<T>::operator();
  13365. explicit freefunc03(ff03_functor ff) : exprtk::ifunction<T>(3), f(ff) {}
  13366. inline T operator() (const T& v0, const T& v1, const T& v2)
  13367. { return f(v0, v1, v2); }
  13368. ff03_functor f;
  13369. };
  13370. struct freefunc04 : public exprtk::ifunction<T>
  13371. {
  13372. using exprtk::ifunction<T>::operator();
  13373. explicit freefunc04(ff04_functor ff) : exprtk::ifunction<T>(4), f(ff) {}
  13374. inline T operator() (const T& v0, const T& v1, const T& v2, const T& v3)
  13375. { return f(v0, v1, v2, v3); }
  13376. ff04_functor f;
  13377. };
  13378. struct freefunc05 : public exprtk::ifunction<T>
  13379. {
  13380. using exprtk::ifunction<T>::operator();
  13381. explicit freefunc05(ff05_functor ff) : exprtk::ifunction<T>(5), f(ff) {}
  13382. inline T operator() (const T& v0, const T& v1, const T& v2, const T& v3, const T& v4)
  13383. { return f(v0, v1, v2, v3, v4); }
  13384. ff05_functor f;
  13385. };
  13386. struct freefunc06 : public exprtk::ifunction<T>
  13387. {
  13388. using exprtk::ifunction<T>::operator();
  13389. explicit freefunc06(ff06_functor ff) : exprtk::ifunction<T>(6), f(ff) {}
  13390. inline T operator() (const T& v0, const T& v1, const T& v2, const T& v3, const T& v4, const T& v5)
  13391. { return f(v0, v1, v2, v3, v4, v5); }
  13392. ff06_functor f;
  13393. };
  13394. struct freefunc07 : public exprtk::ifunction<T>
  13395. {
  13396. using exprtk::ifunction<T>::operator();
  13397. explicit freefunc07(ff07_functor ff) : exprtk::ifunction<T>(7), f(ff) {}
  13398. inline T operator() (const T& v0, const T& v1, const T& v2, const T& v3, const T& v4,
  13399. const T& v5, const T& v6)
  13400. { return f(v0, v1, v2, v3, v4, v5, v6); }
  13401. ff07_functor f;
  13402. };
  13403. struct freefunc08 : public exprtk::ifunction<T>
  13404. {
  13405. using exprtk::ifunction<T>::operator();
  13406. explicit freefunc08(ff08_functor ff) : exprtk::ifunction<T>(8), f(ff) {}
  13407. inline T operator() (const T& v0, const T& v1, const T& v2, const T& v3, const T& v4,
  13408. const T& v5, const T& v6, const T& v7)
  13409. { return f(v0, v1, v2, v3, v4, v5, v6, v7); }
  13410. ff08_functor f;
  13411. };
  13412. struct freefunc09 : public exprtk::ifunction<T>
  13413. {
  13414. using exprtk::ifunction<T>::operator();
  13415. explicit freefunc09(ff09_functor ff) : exprtk::ifunction<T>(9), f(ff) {}
  13416. inline T operator() (const T& v0, const T& v1, const T& v2, const T& v3, const T& v4,
  13417. const T& v5, const T& v6, const T& v7, const T& v8)
  13418. { return f(v0, v1, v2, v3, v4, v5, v6, v7, v8); }
  13419. ff09_functor f;
  13420. };
  13421. struct freefunc10 : public exprtk::ifunction<T>
  13422. {
  13423. using exprtk::ifunction<T>::operator();
  13424. explicit freefunc10(ff10_functor ff) : exprtk::ifunction<T>(10), f(ff) {}
  13425. inline T operator() (const T& v0, const T& v1, const T& v2, const T& v3, const T& v4,
  13426. const T& v5, const T& v6, const T& v7, const T& v8, const T& v9)
  13427. { return f(v0, v1, v2, v3, v4, v5, v6, v7, v8, v9); }
  13428. ff10_functor f;
  13429. };
  13430. struct freefunc11 : public exprtk::ifunction<T>
  13431. {
  13432. using exprtk::ifunction<T>::operator();
  13433. explicit freefunc11(ff11_functor ff) : exprtk::ifunction<T>(11), f(ff) {}
  13434. inline T operator() (const T& v0, const T& v1, const T& v2, const T& v3, const T& v4,
  13435. const T& v5, const T& v6, const T& v7, const T& v8, const T& v9, const T& v10)
  13436. { return f(v0, v1, v2, v3, v4, v5, v6, v7, v8, v9, v10); }
  13437. ff11_functor f;
  13438. };
  13439. struct freefunc12 : public exprtk::ifunction<T>
  13440. {
  13441. using exprtk::ifunction<T>::operator();
  13442. explicit freefunc12(ff12_functor ff) : exprtk::ifunction<T>(12), f(ff) {}
  13443. inline T operator() (const T& v00, const T& v01, const T& v02, const T& v03, const T& v04,
  13444. const T& v05, const T& v06, const T& v07, const T& v08, const T& v09,
  13445. const T& v10, const T& v11)
  13446. { return f(v00, v01, v02, v03, v04, v05, v06, v07, v08, v09, v10, v11); }
  13447. ff12_functor f;
  13448. };
  13449. struct freefunc13 : public exprtk::ifunction<T>
  13450. {
  13451. using exprtk::ifunction<T>::operator();
  13452. explicit freefunc13(ff13_functor ff) : exprtk::ifunction<T>(13), f(ff) {}
  13453. inline T operator() (const T& v00, const T& v01, const T& v02, const T& v03, const T& v04,
  13454. const T& v05, const T& v06, const T& v07, const T& v08, const T& v09,
  13455. const T& v10, const T& v11, const T& v12)
  13456. { return f(v00, v01, v02, v03, v04, v05, v06, v07, v08, v09, v10, v11, v12); }
  13457. ff13_functor f;
  13458. };
  13459. struct freefunc14 : public exprtk::ifunction<T>
  13460. {
  13461. using exprtk::ifunction<T>::operator();
  13462. explicit freefunc14(ff14_functor ff) : exprtk::ifunction<T>(14), f(ff) {}
  13463. inline T operator() (const T& v00, const T& v01, const T& v02, const T& v03, const T& v04,
  13464. const T& v05, const T& v06, const T& v07, const T& v08, const T& v09,
  13465. const T& v10, const T& v11, const T& v12, const T& v13)
  13466. { return f(v00, v01, v02, v03, v04, v05, v06, v07, v08, v09, v10, v11, v12, v13); }
  13467. ff14_functor f;
  13468. };
  13469. struct freefunc15 : public exprtk::ifunction<T>
  13470. {
  13471. using exprtk::ifunction<T>::operator();
  13472. explicit freefunc15(ff15_functor ff) : exprtk::ifunction<T>(15), f(ff) {}
  13473. inline T operator() (const T& v00, const T& v01, const T& v02, const T& v03, const T& v04,
  13474. const T& v05, const T& v06, const T& v07, const T& v08, const T& v09,
  13475. const T& v10, const T& v11, const T& v12, const T& v13, const T& v14)
  13476. { return f(v00, v01, v02, v03, v04, v05, v06, v07, v08, v09, v10, v11, v12, v13, v14); }
  13477. ff15_functor f;
  13478. };
  13479. template <typename Type, typename RawType>
  13480. struct type_store
  13481. {
  13482. typedef details::expression_node<T>* expression_ptr;
  13483. typedef typename details::variable_node<T> variable_node_t;
  13484. typedef ifunction<T> ifunction_t;
  13485. typedef ivararg_function<T> ivararg_function_t;
  13486. typedef igeneric_function<T> igeneric_function_t;
  13487. typedef details::vector_holder<T> vector_t;
  13488. #ifndef exprtk_disable_string_capabilities
  13489. typedef typename details::stringvar_node<T> stringvar_node_t;
  13490. #endif
  13491. typedef Type type_t;
  13492. typedef type_t* type_ptr;
  13493. typedef std::pair<bool,type_ptr> type_pair_t;
  13494. typedef std::map<std::string,type_pair_t,details::ilesscompare> type_map_t;
  13495. typedef typename type_map_t::iterator tm_itr_t;
  13496. typedef typename type_map_t::const_iterator tm_const_itr_t;
  13497. enum { lut_size = 256 };
  13498. type_map_t map;
  13499. std::size_t size;
  13500. type_store()
  13501. : size(0)
  13502. {}
  13503. inline bool symbol_exists(const std::string& symbol_name) const
  13504. {
  13505. if (symbol_name.empty())
  13506. return false;
  13507. else if (map.end() != map.find(symbol_name))
  13508. return true;
  13509. else
  13510. return false;
  13511. }
  13512. template <typename PtrType>
  13513. inline std::string entity_name(const PtrType& ptr) const
  13514. {
  13515. if (map.empty())
  13516. return std::string();
  13517. tm_const_itr_t itr = map.begin();
  13518. while (map.end() != itr)
  13519. {
  13520. if (itr->second.second == ptr)
  13521. {
  13522. return itr->first;
  13523. }
  13524. else
  13525. ++itr;
  13526. }
  13527. return std::string();
  13528. }
  13529. inline bool is_constant(const std::string& symbol_name) const
  13530. {
  13531. if (symbol_name.empty())
  13532. return false;
  13533. else
  13534. {
  13535. const tm_const_itr_t itr = map.find(symbol_name);
  13536. if (map.end() == itr)
  13537. return false;
  13538. else
  13539. return (*itr).second.first;
  13540. }
  13541. }
  13542. template <typename Tie, typename RType>
  13543. inline bool add_impl(const std::string& symbol_name, RType t, const bool is_const)
  13544. {
  13545. if (symbol_name.size() > 1)
  13546. {
  13547. for (std::size_t i = 0; i < details::reserved_symbols_size; ++i)
  13548. {
  13549. if (details::imatch(symbol_name, details::reserved_symbols[i]))
  13550. {
  13551. return false;
  13552. }
  13553. }
  13554. }
  13555. const tm_itr_t itr = map.find(symbol_name);
  13556. if (map.end() == itr)
  13557. {
  13558. map[symbol_name] = Tie::make(t,is_const);
  13559. ++size;
  13560. }
  13561. return true;
  13562. }
  13563. struct tie_array
  13564. {
  13565. static inline std::pair<bool,vector_t*> make(std::pair<T*,std::size_t> v, const bool is_const = false)
  13566. {
  13567. return std::make_pair(is_const, new vector_t(v.first, v.second));
  13568. }
  13569. };
  13570. struct tie_stdvec
  13571. {
  13572. template <typename Allocator>
  13573. static inline std::pair<bool,vector_t*> make(std::vector<T,Allocator>& v, const bool is_const = false)
  13574. {
  13575. return std::make_pair(is_const, new vector_t(v));
  13576. }
  13577. };
  13578. struct tie_vecview
  13579. {
  13580. static inline std::pair<bool,vector_t*> make(exprtk::vector_view<T>& v, const bool is_const = false)
  13581. {
  13582. return std::make_pair(is_const, new vector_t(v));
  13583. }
  13584. };
  13585. struct tie_stddeq
  13586. {
  13587. template <typename Allocator>
  13588. static inline std::pair<bool,vector_t*> make(std::deque<T,Allocator>& v, const bool is_const = false)
  13589. {
  13590. return std::make_pair(is_const, new vector_t(v));
  13591. }
  13592. };
  13593. template <std::size_t v_size>
  13594. inline bool add(const std::string& symbol_name, T (&v)[v_size], const bool is_const = false)
  13595. {
  13596. return add_impl<tie_array,std::pair<T*,std::size_t> >
  13597. (symbol_name, std::make_pair(v,v_size), is_const);
  13598. }
  13599. inline bool add(const std::string& symbol_name, T* v, const std::size_t v_size, const bool is_const = false)
  13600. {
  13601. return add_impl<tie_array,std::pair<T*,std::size_t> >
  13602. (symbol_name, std::make_pair(v,v_size), is_const);
  13603. }
  13604. template <typename Allocator>
  13605. inline bool add(const std::string& symbol_name, std::vector<T,Allocator>& v, const bool is_const = false)
  13606. {
  13607. return add_impl<tie_stdvec,std::vector<T,Allocator>&>
  13608. (symbol_name, v, is_const);
  13609. }
  13610. inline bool add(const std::string& symbol_name, exprtk::vector_view<T>& v, const bool is_const = false)
  13611. {
  13612. return add_impl<tie_vecview,exprtk::vector_view<T>&>
  13613. (symbol_name, v, is_const);
  13614. }
  13615. template <typename Allocator>
  13616. inline bool add(const std::string& symbol_name, std::deque<T,Allocator>& v, const bool is_const = false)
  13617. {
  13618. return add_impl<tie_stddeq,std::deque<T,Allocator>&>
  13619. (symbol_name, v, is_const);
  13620. }
  13621. inline bool add(const std::string& symbol_name, RawType& t, const bool is_const = false)
  13622. {
  13623. struct tie
  13624. {
  13625. static inline std::pair<bool,variable_node_t*> make(T& t,const bool is_const = false)
  13626. {
  13627. return std::make_pair(is_const, new variable_node_t(t));
  13628. }
  13629. #ifndef exprtk_disable_string_capabilities
  13630. static inline std::pair<bool,stringvar_node_t*> make(std::string& t,const bool is_const = false)
  13631. {
  13632. return std::make_pair(is_const, new stringvar_node_t(t));
  13633. }
  13634. #endif
  13635. static inline std::pair<bool,function_t*> make(function_t& t, const bool is_constant = false)
  13636. {
  13637. return std::make_pair(is_constant,&t);
  13638. }
  13639. static inline std::pair<bool,vararg_function_t*> make(vararg_function_t& t, const bool is_const = false)
  13640. {
  13641. return std::make_pair(is_const,&t);
  13642. }
  13643. static inline std::pair<bool,generic_function_t*> make(generic_function_t& t, const bool is_constant = false)
  13644. {
  13645. return std::make_pair(is_constant,&t);
  13646. }
  13647. };
  13648. const tm_itr_t itr = map.find(symbol_name);
  13649. if (map.end() == itr)
  13650. {
  13651. map[symbol_name] = tie::make(t,is_const);
  13652. ++size;
  13653. }
  13654. return true;
  13655. }
  13656. inline type_ptr get(const std::string& symbol_name) const
  13657. {
  13658. const tm_const_itr_t itr = map.find(symbol_name);
  13659. if (map.end() == itr)
  13660. return reinterpret_cast<type_ptr>(0);
  13661. else
  13662. return itr->second.second;
  13663. }
  13664. template <typename TType, typename TRawType, typename PtrType>
  13665. struct ptr_match
  13666. {
  13667. static inline bool test(const PtrType, const void*)
  13668. {
  13669. return false;
  13670. }
  13671. };
  13672. template <typename TType, typename TRawType>
  13673. struct ptr_match<TType,TRawType,variable_node_t*>
  13674. {
  13675. static inline bool test(const variable_node_t* p, const void* ptr)
  13676. {
  13677. exprtk_debug(("ptr_match::test() - %p <--> %p\n",(void*)(&(p->ref())),ptr));
  13678. return (&(p->ref()) == ptr);
  13679. }
  13680. };
  13681. inline type_ptr get_from_varptr(const void* ptr) const
  13682. {
  13683. tm_const_itr_t itr = map.begin();
  13684. while (map.end() != itr)
  13685. {
  13686. type_ptr ret_ptr = itr->second.second;
  13687. if (ptr_match<Type,RawType,type_ptr>::test(ret_ptr,ptr))
  13688. {
  13689. return ret_ptr;
  13690. }
  13691. ++itr;
  13692. }
  13693. return type_ptr(0);
  13694. }
  13695. inline bool remove(const std::string& symbol_name, const bool delete_node = true)
  13696. {
  13697. const tm_itr_t itr = map.find(symbol_name);
  13698. if (map.end() != itr)
  13699. {
  13700. struct deleter
  13701. {
  13702. static inline void process(std::pair<bool,variable_node_t*>& n) { delete n.second; }
  13703. static inline void process(std::pair<bool,vector_t*>& n) { delete n.second; }
  13704. #ifndef exprtk_disable_string_capabilities
  13705. static inline void process(std::pair<bool,stringvar_node_t*>& n) { delete n.second; }
  13706. #endif
  13707. static inline void process(std::pair<bool,function_t*>&) { }
  13708. };
  13709. if (delete_node)
  13710. {
  13711. deleter::process((*itr).second);
  13712. }
  13713. map.erase(itr);
  13714. --size;
  13715. return true;
  13716. }
  13717. else
  13718. return false;
  13719. }
  13720. inline RawType& type_ref(const std::string& symbol_name)
  13721. {
  13722. struct init_type
  13723. {
  13724. static inline double set(double) { return (0.0); }
  13725. static inline double set(long double) { return (0.0); }
  13726. static inline float set(float) { return (0.0f); }
  13727. static inline std::string set(std::string) { return std::string(""); }
  13728. };
  13729. static RawType null_type = init_type::set(RawType());
  13730. const tm_const_itr_t itr = map.find(symbol_name);
  13731. if (map.end() == itr)
  13732. return null_type;
  13733. else
  13734. return itr->second.second->ref();
  13735. }
  13736. inline void clear(const bool delete_node = true)
  13737. {
  13738. struct deleter
  13739. {
  13740. static inline void process(std::pair<bool,variable_node_t*>& n) { delete n.second; }
  13741. static inline void process(std::pair<bool,vector_t*>& n) { delete n.second; }
  13742. static inline void process(std::pair<bool,function_t*>&) { }
  13743. #ifndef exprtk_disable_string_capabilities
  13744. static inline void process(std::pair<bool,stringvar_node_t*>& n) { delete n.second; }
  13745. #endif
  13746. };
  13747. if (!map.empty())
  13748. {
  13749. if (delete_node)
  13750. {
  13751. tm_itr_t itr = map.begin();
  13752. tm_itr_t end = map.end ();
  13753. while (end != itr)
  13754. {
  13755. deleter::process((*itr).second);
  13756. ++itr;
  13757. }
  13758. }
  13759. map.clear();
  13760. }
  13761. size = 0;
  13762. }
  13763. template <typename Allocator,
  13764. template <typename, typename> class Sequence>
  13765. inline std::size_t get_list(Sequence<std::pair<std::string,RawType>,Allocator>& list) const
  13766. {
  13767. std::size_t count = 0;
  13768. if (!map.empty())
  13769. {
  13770. tm_const_itr_t itr = map.begin();
  13771. tm_const_itr_t end = map.end ();
  13772. while (end != itr)
  13773. {
  13774. list.push_back(std::make_pair((*itr).first,itr->second.second->ref()));
  13775. ++itr;
  13776. ++count;
  13777. }
  13778. }
  13779. return count;
  13780. }
  13781. template <typename Allocator,
  13782. template <typename, typename> class Sequence>
  13783. inline std::size_t get_list(Sequence<std::string,Allocator>& vlist) const
  13784. {
  13785. std::size_t count = 0;
  13786. if (!map.empty())
  13787. {
  13788. tm_const_itr_t itr = map.begin();
  13789. tm_const_itr_t end = map.end ();
  13790. while (end != itr)
  13791. {
  13792. vlist.push_back((*itr).first);
  13793. ++itr;
  13794. ++count;
  13795. }
  13796. }
  13797. return count;
  13798. }
  13799. };
  13800. typedef details::expression_node<T>* expression_ptr;
  13801. typedef typename details::variable_node<T> variable_t;
  13802. typedef typename details::vector_holder<T> vector_holder_t;
  13803. typedef variable_t* variable_ptr;
  13804. #ifndef exprtk_disable_string_capabilities
  13805. typedef typename details::stringvar_node<T> stringvar_t;
  13806. typedef stringvar_t* stringvar_ptr;
  13807. #endif
  13808. typedef ifunction <T> function_t;
  13809. typedef ivararg_function <T> vararg_function_t;
  13810. typedef igeneric_function<T> generic_function_t;
  13811. typedef function_t* function_ptr;
  13812. typedef vararg_function_t* vararg_function_ptr;
  13813. typedef generic_function_t* generic_function_ptr;
  13814. static const std::size_t lut_size = 256;
  13815. // Symbol Table Holder
  13816. struct control_block
  13817. {
  13818. struct st_data
  13819. {
  13820. type_store<typename details::variable_node<T>,T> variable_store;
  13821. #ifndef exprtk_disable_string_capabilities
  13822. type_store<typename details::stringvar_node<T>,std::string> stringvar_store;
  13823. #endif
  13824. type_store<ifunction<T>,ifunction<T> > function_store;
  13825. type_store<ivararg_function <T>,ivararg_function <T> > vararg_function_store;
  13826. type_store<igeneric_function<T>,igeneric_function<T> > generic_function_store;
  13827. type_store<igeneric_function<T>,igeneric_function<T> > string_function_store;
  13828. type_store<igeneric_function<T>,igeneric_function<T> > overload_function_store;
  13829. type_store<vector_holder_t,vector_holder_t> vector_store;
  13830. st_data()
  13831. {
  13832. for (std::size_t i = 0; i < details::reserved_words_size; ++i)
  13833. {
  13834. reserved_symbol_table_.insert(details::reserved_words[i]);
  13835. }
  13836. for (std::size_t i = 0; i < details::reserved_symbols_size; ++i)
  13837. {
  13838. reserved_symbol_table_.insert(details::reserved_symbols[i]);
  13839. }
  13840. }
  13841. ~st_data()
  13842. {
  13843. for (std::size_t i = 0; i < free_function_list_.size(); ++i)
  13844. {
  13845. delete free_function_list_[i];
  13846. }
  13847. }
  13848. inline bool is_reserved_symbol(const std::string& symbol) const
  13849. {
  13850. return (reserved_symbol_table_.end() != reserved_symbol_table_.find(symbol));
  13851. }
  13852. static inline st_data* create()
  13853. {
  13854. return (new st_data);
  13855. }
  13856. static inline void destroy(st_data*& sd)
  13857. {
  13858. delete sd;
  13859. sd = reinterpret_cast<st_data*>(0);
  13860. }
  13861. std::list<T> local_symbol_list_;
  13862. std::list<std::string> local_stringvar_list_;
  13863. std::set<std::string> reserved_symbol_table_;
  13864. std::vector<ifunction<T>*> free_function_list_;
  13865. };
  13866. control_block()
  13867. : ref_count(1),
  13868. data_(st_data::create())
  13869. {}
  13870. explicit control_block(st_data* data)
  13871. : ref_count(1),
  13872. data_(data)
  13873. {}
  13874. ~control_block()
  13875. {
  13876. if (data_ && (0 == ref_count))
  13877. {
  13878. st_data::destroy(data_);
  13879. }
  13880. }
  13881. static inline control_block* create()
  13882. {
  13883. return (new control_block);
  13884. }
  13885. template <typename SymTab>
  13886. static inline void destroy(control_block*& cntrl_blck, SymTab* sym_tab)
  13887. {
  13888. if (cntrl_blck)
  13889. {
  13890. if (
  13891. (0 != cntrl_blck->ref_count) &&
  13892. (0 == --cntrl_blck->ref_count)
  13893. )
  13894. {
  13895. if (sym_tab)
  13896. sym_tab->clear();
  13897. delete cntrl_blck;
  13898. }
  13899. cntrl_blck = 0;
  13900. }
  13901. }
  13902. std::size_t ref_count;
  13903. st_data* data_;
  13904. };
  13905. public:
  13906. symbol_table()
  13907. : control_block_(control_block::create())
  13908. {
  13909. clear();
  13910. }
  13911. ~symbol_table()
  13912. {
  13913. control_block::destroy(control_block_,this);
  13914. }
  13915. symbol_table(const symbol_table<T>& st)
  13916. {
  13917. control_block_ = st.control_block_;
  13918. control_block_->ref_count++;
  13919. }
  13920. inline symbol_table<T>& operator=(const symbol_table<T>& st)
  13921. {
  13922. if (this != &st)
  13923. {
  13924. control_block::destroy(control_block_,reinterpret_cast<symbol_table<T>*>(0));
  13925. control_block_ = st.control_block_;
  13926. control_block_->ref_count++;
  13927. }
  13928. return (*this);
  13929. }
  13930. inline bool operator==(const symbol_table<T>& st) const
  13931. {
  13932. return (this == &st) || (control_block_ == st.control_block_);
  13933. }
  13934. inline void clear_variables(const bool delete_node = true)
  13935. {
  13936. local_data().variable_store.clear(delete_node);
  13937. }
  13938. inline void clear_functions()
  13939. {
  13940. local_data().function_store.clear();
  13941. }
  13942. inline void clear_strings()
  13943. {
  13944. #ifndef exprtk_disable_string_capabilities
  13945. local_data().stringvar_store.clear();
  13946. #endif
  13947. }
  13948. inline void clear_vectors()
  13949. {
  13950. local_data().vector_store.clear();
  13951. }
  13952. inline void clear_local_constants()
  13953. {
  13954. local_data().local_symbol_list_.clear();
  13955. }
  13956. inline void clear()
  13957. {
  13958. if (!valid()) return;
  13959. clear_variables ();
  13960. clear_functions ();
  13961. clear_strings ();
  13962. clear_vectors ();
  13963. clear_local_constants();
  13964. }
  13965. inline std::size_t variable_count() const
  13966. {
  13967. if (valid())
  13968. return local_data().variable_store.size;
  13969. else
  13970. return 0;
  13971. }
  13972. #ifndef exprtk_disable_string_capabilities
  13973. inline std::size_t stringvar_count() const
  13974. {
  13975. if (valid())
  13976. return local_data().stringvar_store.size;
  13977. else
  13978. return 0;
  13979. }
  13980. #endif
  13981. inline std::size_t function_count() const
  13982. {
  13983. if (valid())
  13984. return local_data().function_store.size;
  13985. else
  13986. return 0;
  13987. }
  13988. inline std::size_t vector_count() const
  13989. {
  13990. if (valid())
  13991. return local_data().vector_store.size;
  13992. else
  13993. return 0;
  13994. }
  13995. inline variable_ptr get_variable(const std::string& variable_name) const
  13996. {
  13997. if (!valid())
  13998. return reinterpret_cast<variable_ptr>(0);
  13999. else if (!valid_symbol(variable_name))
  14000. return reinterpret_cast<variable_ptr>(0);
  14001. else
  14002. return local_data().variable_store.get(variable_name);
  14003. }
  14004. inline variable_ptr get_variable(const T& var_ref) const
  14005. {
  14006. if (!valid())
  14007. return reinterpret_cast<variable_ptr>(0);
  14008. else
  14009. return local_data().variable_store.get_from_varptr(
  14010. reinterpret_cast<const void*>(&var_ref));
  14011. }
  14012. #ifndef exprtk_disable_string_capabilities
  14013. inline stringvar_ptr get_stringvar(const std::string& string_name) const
  14014. {
  14015. if (!valid())
  14016. return reinterpret_cast<stringvar_ptr>(0);
  14017. else if (!valid_symbol(string_name))
  14018. return reinterpret_cast<stringvar_ptr>(0);
  14019. else
  14020. return local_data().stringvar_store.get(string_name);
  14021. }
  14022. #endif
  14023. inline function_ptr get_function(const std::string& function_name) const
  14024. {
  14025. if (!valid())
  14026. return reinterpret_cast<function_ptr>(0);
  14027. else if (!valid_symbol(function_name))
  14028. return reinterpret_cast<function_ptr>(0);
  14029. else
  14030. return local_data().function_store.get(function_name);
  14031. }
  14032. inline vararg_function_ptr get_vararg_function(const std::string& vararg_function_name) const
  14033. {
  14034. if (!valid())
  14035. return reinterpret_cast<vararg_function_ptr>(0);
  14036. else if (!valid_symbol(vararg_function_name))
  14037. return reinterpret_cast<vararg_function_ptr>(0);
  14038. else
  14039. return local_data().vararg_function_store.get(vararg_function_name);
  14040. }
  14041. inline generic_function_ptr get_generic_function(const std::string& function_name) const
  14042. {
  14043. if (!valid())
  14044. return reinterpret_cast<generic_function_ptr>(0);
  14045. else if (!valid_symbol(function_name))
  14046. return reinterpret_cast<generic_function_ptr>(0);
  14047. else
  14048. return local_data().generic_function_store.get(function_name);
  14049. }
  14050. inline generic_function_ptr get_string_function(const std::string& function_name) const
  14051. {
  14052. if (!valid())
  14053. return reinterpret_cast<generic_function_ptr>(0);
  14054. else if (!valid_symbol(function_name))
  14055. return reinterpret_cast<generic_function_ptr>(0);
  14056. else
  14057. return local_data().string_function_store.get(function_name);
  14058. }
  14059. inline generic_function_ptr get_overload_function(const std::string& function_name) const
  14060. {
  14061. if (!valid())
  14062. return reinterpret_cast<generic_function_ptr>(0);
  14063. else if (!valid_symbol(function_name))
  14064. return reinterpret_cast<generic_function_ptr>(0);
  14065. else
  14066. return local_data().overload_function_store.get(function_name);
  14067. }
  14068. typedef vector_holder_t* vector_holder_ptr;
  14069. inline vector_holder_ptr get_vector(const std::string& vector_name) const
  14070. {
  14071. if (!valid())
  14072. return reinterpret_cast<vector_holder_ptr>(0);
  14073. else if (!valid_symbol(vector_name))
  14074. return reinterpret_cast<vector_holder_ptr>(0);
  14075. else
  14076. return local_data().vector_store.get(vector_name);
  14077. }
  14078. inline T& variable_ref(const std::string& symbol_name)
  14079. {
  14080. static T null_var = T(0);
  14081. if (!valid())
  14082. return null_var;
  14083. else if (!valid_symbol(symbol_name))
  14084. return null_var;
  14085. else
  14086. return local_data().variable_store.type_ref(symbol_name);
  14087. }
  14088. #ifndef exprtk_disable_string_capabilities
  14089. inline std::string& stringvar_ref(const std::string& symbol_name)
  14090. {
  14091. static std::string null_stringvar;
  14092. if (!valid())
  14093. return null_stringvar;
  14094. else if (!valid_symbol(symbol_name))
  14095. return null_stringvar;
  14096. else
  14097. return local_data().stringvar_store.type_ref(symbol_name);
  14098. }
  14099. #endif
  14100. inline bool is_constant_node(const std::string& symbol_name) const
  14101. {
  14102. if (!valid())
  14103. return false;
  14104. else if (!valid_symbol(symbol_name))
  14105. return false;
  14106. else
  14107. return local_data().variable_store.is_constant(symbol_name);
  14108. }
  14109. #ifndef exprtk_disable_string_capabilities
  14110. inline bool is_constant_string(const std::string& symbol_name) const
  14111. {
  14112. if (!valid())
  14113. return false;
  14114. else if (!valid_symbol(symbol_name))
  14115. return false;
  14116. else if (!local_data().stringvar_store.symbol_exists(symbol_name))
  14117. return false;
  14118. else
  14119. return local_data().stringvar_store.is_constant(symbol_name);
  14120. }
  14121. #endif
  14122. inline bool create_variable(const std::string& variable_name, const T& value = T(0))
  14123. {
  14124. if (!valid())
  14125. return false;
  14126. else if (!valid_symbol(variable_name))
  14127. return false;
  14128. else if (symbol_exists(variable_name))
  14129. return false;
  14130. local_data().local_symbol_list_.push_back(value);
  14131. T& t = local_data().local_symbol_list_.back();
  14132. return add_variable(variable_name,t);
  14133. }
  14134. #ifndef exprtk_disable_string_capabilities
  14135. inline bool create_stringvar(const std::string& stringvar_name, const std::string& value = std::string(""))
  14136. {
  14137. if (!valid())
  14138. return false;
  14139. else if (!valid_symbol(stringvar_name))
  14140. return false;
  14141. else if (symbol_exists(stringvar_name))
  14142. return false;
  14143. local_data().local_stringvar_list_.push_back(value);
  14144. std::string& s = local_data().local_stringvar_list_.back();
  14145. return add_stringvar(stringvar_name,s);
  14146. }
  14147. #endif
  14148. inline bool add_variable(const std::string& variable_name, T& t, const bool is_constant = false)
  14149. {
  14150. if (!valid())
  14151. return false;
  14152. else if (!valid_symbol(variable_name))
  14153. return false;
  14154. else if (symbol_exists(variable_name))
  14155. return false;
  14156. else
  14157. return local_data().variable_store.add(variable_name, t, is_constant);
  14158. }
  14159. inline bool add_constant(const std::string& constant_name, const T& value)
  14160. {
  14161. if (!valid())
  14162. return false;
  14163. else if (!valid_symbol(constant_name))
  14164. return false;
  14165. else if (symbol_exists(constant_name))
  14166. return false;
  14167. local_data().local_symbol_list_.push_back(value);
  14168. T& t = local_data().local_symbol_list_.back();
  14169. return add_variable(constant_name, t, true);
  14170. }
  14171. #ifndef exprtk_disable_string_capabilities
  14172. inline bool add_stringvar(const std::string& stringvar_name, std::string& s, const bool is_constant = false)
  14173. {
  14174. if (!valid())
  14175. return false;
  14176. else if (!valid_symbol(stringvar_name))
  14177. return false;
  14178. else if (symbol_exists(stringvar_name))
  14179. return false;
  14180. else
  14181. return local_data().stringvar_store.add(stringvar_name, s, is_constant);
  14182. }
  14183. #endif
  14184. inline bool add_function(const std::string& function_name, function_t& function)
  14185. {
  14186. if (!valid())
  14187. return false;
  14188. else if (!valid_symbol(function_name))
  14189. return false;
  14190. else if (symbol_exists(function_name))
  14191. return false;
  14192. else
  14193. return local_data().function_store.add(function_name,function);
  14194. }
  14195. inline bool add_function(const std::string& vararg_function_name, vararg_function_t& vararg_function)
  14196. {
  14197. if (!valid())
  14198. return false;
  14199. else if (!valid_symbol(vararg_function_name))
  14200. return false;
  14201. else if (symbol_exists(vararg_function_name))
  14202. return false;
  14203. else
  14204. return local_data().vararg_function_store.add(vararg_function_name,vararg_function);
  14205. }
  14206. inline bool add_function(const std::string& function_name, generic_function_t& function)
  14207. {
  14208. if (!valid())
  14209. return false;
  14210. else if (!valid_symbol(function_name))
  14211. return false;
  14212. else if (symbol_exists(function_name))
  14213. return false;
  14214. else if (
  14215. (
  14216. (generic_function_t::e_rtrn_scalar == function.rtrn_type) ||
  14217. (generic_function_t::e_rtrn_string == function.rtrn_type)
  14218. ) &&
  14219. std::string::npos != function.parameter_sequence.find_first_not_of("STVZ*?|")
  14220. )
  14221. return false;
  14222. else if (
  14223. (generic_function_t::e_rtrn_overload == function.rtrn_type) &&
  14224. std::string::npos != function.parameter_sequence.find_first_not_of("STVZ*?|:")
  14225. )
  14226. return false;
  14227. switch (function.rtrn_type)
  14228. {
  14229. case generic_function_t::e_rtrn_scalar :
  14230. return local_data().generic_function_store.add(function_name,function);
  14231. case generic_function_t::e_rtrn_string :
  14232. return local_data().string_function_store.add(function_name,function);
  14233. case generic_function_t::e_rtrn_overload :
  14234. return local_data().overload_function_store.add(function_name,function);
  14235. }
  14236. return false;
  14237. }
  14238. #define exprtk_define_freefunction(NN) \
  14239. inline bool add_function(const std::string& function_name, ff##NN##_functor function) \
  14240. { \
  14241. if (!valid()) \
  14242. { return false; } \
  14243. if (!valid_symbol(function_name)) \
  14244. { return false; } \
  14245. if (symbol_exists(function_name)) \
  14246. { return false; } \
  14247. \
  14248. exprtk::ifunction<T>* ifunc = new freefunc##NN(function); \
  14249. \
  14250. local_data().free_function_list_.push_back(ifunc); \
  14251. \
  14252. return add_function(function_name,(*local_data().free_function_list_.back())); \
  14253. } \
  14254. exprtk_define_freefunction(00) exprtk_define_freefunction(01)
  14255. exprtk_define_freefunction(02) exprtk_define_freefunction(03)
  14256. exprtk_define_freefunction(04) exprtk_define_freefunction(05)
  14257. exprtk_define_freefunction(06) exprtk_define_freefunction(07)
  14258. exprtk_define_freefunction(08) exprtk_define_freefunction(09)
  14259. exprtk_define_freefunction(10) exprtk_define_freefunction(11)
  14260. exprtk_define_freefunction(12) exprtk_define_freefunction(13)
  14261. exprtk_define_freefunction(14) exprtk_define_freefunction(15)
  14262. #undef exprtk_define_freefunction
  14263. inline bool add_reserved_function(const std::string& function_name, function_t& function)
  14264. {
  14265. if (!valid())
  14266. return false;
  14267. else if (!valid_symbol(function_name,false))
  14268. return false;
  14269. else if (symbol_exists(function_name,false))
  14270. return false;
  14271. else
  14272. return local_data().function_store.add(function_name,function);
  14273. }
  14274. inline bool add_reserved_function(const std::string& vararg_function_name, vararg_function_t& vararg_function)
  14275. {
  14276. if (!valid())
  14277. return false;
  14278. else if (!valid_symbol(vararg_function_name,false))
  14279. return false;
  14280. else if (symbol_exists(vararg_function_name,false))
  14281. return false;
  14282. else
  14283. return local_data().vararg_function_store.add(vararg_function_name,vararg_function);
  14284. }
  14285. inline bool add_reserved_function(const std::string& function_name, generic_function_t& function)
  14286. {
  14287. if (!valid())
  14288. return false;
  14289. else if (!valid_symbol(function_name,false))
  14290. return false;
  14291. else if (symbol_exists(function_name,false))
  14292. return false;
  14293. else if (
  14294. (
  14295. (generic_function_t::e_rtrn_scalar == function.rtrn_type) ||
  14296. (generic_function_t::e_rtrn_string == function.rtrn_type)
  14297. ) &&
  14298. std::string::npos != function.parameter_sequence.find_first_not_of("STV*?|")
  14299. )
  14300. return false;
  14301. else if (
  14302. generic_function_t::e_rtrn_overload &&
  14303. std::string::npos != function.parameter_sequence.find_first_not_of("STV*?|:")
  14304. )
  14305. return false;
  14306. switch (function.rtrn_type)
  14307. {
  14308. case generic_function_t::e_rtrn_scalar :
  14309. return local_data().generic_function_store.add(function_name,function);
  14310. case generic_function_t::e_rtrn_string :
  14311. return local_data().string_function_store.add(function_name,function);
  14312. case generic_function_t::e_rtrn_overload :
  14313. return local_data().overload_function_store.add(function_name,function);
  14314. }
  14315. return false;
  14316. }
  14317. template <std::size_t N>
  14318. inline bool add_vector(const std::string& vector_name, T (&v)[N])
  14319. {
  14320. if (!valid())
  14321. return false;
  14322. else if (!valid_symbol(vector_name))
  14323. return false;
  14324. else if (symbol_exists(vector_name))
  14325. return false;
  14326. else
  14327. return local_data().vector_store.add(vector_name,v);
  14328. }
  14329. inline bool add_vector(const std::string& vector_name, T* v, const std::size_t& v_size)
  14330. {
  14331. if (!valid())
  14332. return false;
  14333. else if (!valid_symbol(vector_name))
  14334. return false;
  14335. else if (symbol_exists(vector_name))
  14336. return false;
  14337. else if (0 == v_size)
  14338. return false;
  14339. else
  14340. return local_data().vector_store.add(vector_name, v, v_size);
  14341. }
  14342. template <typename Allocator>
  14343. inline bool add_vector(const std::string& vector_name, std::vector<T,Allocator>& v)
  14344. {
  14345. if (!valid())
  14346. return false;
  14347. else if (!valid_symbol(vector_name))
  14348. return false;
  14349. else if (symbol_exists(vector_name))
  14350. return false;
  14351. else if (0 == v.size())
  14352. return false;
  14353. else
  14354. return local_data().vector_store.add(vector_name,v);
  14355. }
  14356. inline bool add_vector(const std::string& vector_name, exprtk::vector_view<T>& v)
  14357. {
  14358. if (!valid())
  14359. return false;
  14360. else if (!valid_symbol(vector_name))
  14361. return false;
  14362. else if (symbol_exists(vector_name))
  14363. return false;
  14364. else if (0 == v.size())
  14365. return false;
  14366. else
  14367. return local_data().vector_store.add(vector_name,v);
  14368. }
  14369. inline bool remove_variable(const std::string& variable_name, const bool delete_node = true)
  14370. {
  14371. if (!valid())
  14372. return false;
  14373. else
  14374. return local_data().variable_store.remove(variable_name, delete_node);
  14375. }
  14376. #ifndef exprtk_disable_string_capabilities
  14377. inline bool remove_stringvar(const std::string& string_name)
  14378. {
  14379. if (!valid())
  14380. return false;
  14381. else
  14382. return local_data().stringvar_store.remove(string_name);
  14383. }
  14384. #endif
  14385. inline bool remove_function(const std::string& function_name)
  14386. {
  14387. if (!valid())
  14388. return false;
  14389. else
  14390. return local_data().function_store.remove(function_name);
  14391. }
  14392. inline bool remove_vararg_function(const std::string& vararg_function_name)
  14393. {
  14394. if (!valid())
  14395. return false;
  14396. else
  14397. return local_data().vararg_function_store.remove(vararg_function_name);
  14398. }
  14399. inline bool remove_vector(const std::string& vector_name)
  14400. {
  14401. if (!valid())
  14402. return false;
  14403. else
  14404. return local_data().vector_store.remove(vector_name);
  14405. }
  14406. inline bool add_constants()
  14407. {
  14408. return add_pi () &&
  14409. add_epsilon () &&
  14410. add_infinity() ;
  14411. }
  14412. inline bool add_pi()
  14413. {
  14414. const typename details::numeric::details::number_type<T>::type num_type;
  14415. static const T local_pi = details::numeric::details::const_pi_impl<T>(num_type);
  14416. return add_constant("pi",local_pi);
  14417. }
  14418. inline bool add_epsilon()
  14419. {
  14420. static const T local_epsilon = details::numeric::details::epsilon_type<T>::value();
  14421. return add_constant("epsilon",local_epsilon);
  14422. }
  14423. inline bool add_infinity()
  14424. {
  14425. static const T local_infinity = std::numeric_limits<T>::infinity();
  14426. return add_constant("inf",local_infinity);
  14427. }
  14428. template <typename Package>
  14429. inline bool add_package(Package& package)
  14430. {
  14431. return package.register_package(*this);
  14432. }
  14433. template <typename Allocator,
  14434. template <typename, typename> class Sequence>
  14435. inline std::size_t get_variable_list(Sequence<std::pair<std::string,T>,Allocator>& vlist) const
  14436. {
  14437. if (!valid())
  14438. return 0;
  14439. else
  14440. return local_data().variable_store.get_list(vlist);
  14441. }
  14442. template <typename Allocator,
  14443. template <typename, typename> class Sequence>
  14444. inline std::size_t get_variable_list(Sequence<std::string,Allocator>& vlist) const
  14445. {
  14446. if (!valid())
  14447. return 0;
  14448. else
  14449. return local_data().variable_store.get_list(vlist);
  14450. }
  14451. #ifndef exprtk_disable_string_capabilities
  14452. template <typename Allocator,
  14453. template <typename, typename> class Sequence>
  14454. inline std::size_t get_stringvar_list(Sequence<std::pair<std::string,std::string>,Allocator>& svlist) const
  14455. {
  14456. if (!valid())
  14457. return 0;
  14458. else
  14459. return local_data().stringvar_store.get_list(svlist);
  14460. }
  14461. template <typename Allocator,
  14462. template <typename, typename> class Sequence>
  14463. inline std::size_t get_stringvar_list(Sequence<std::string,Allocator>& svlist) const
  14464. {
  14465. if (!valid())
  14466. return 0;
  14467. else
  14468. return local_data().stringvar_store.get_list(svlist);
  14469. }
  14470. #endif
  14471. template <typename Allocator,
  14472. template <typename, typename> class Sequence>
  14473. inline std::size_t get_vector_list(Sequence<std::string,Allocator>& vlist) const
  14474. {
  14475. if (!valid())
  14476. return 0;
  14477. else
  14478. return local_data().vector_store.get_list(vlist);
  14479. }
  14480. inline bool symbol_exists(const std::string& symbol_name, const bool check_reserved_symb = true) const
  14481. {
  14482. /*
  14483. Function will return true if symbol_name exists as either a
  14484. reserved symbol, variable, stringvar, vector or function name
  14485. in any of the type stores.
  14486. */
  14487. if (!valid())
  14488. return false;
  14489. else if (local_data().variable_store.symbol_exists(symbol_name))
  14490. return true;
  14491. #ifndef exprtk_disable_string_capabilities
  14492. else if (local_data().stringvar_store.symbol_exists(symbol_name))
  14493. return true;
  14494. #endif
  14495. else if (local_data().vector_store.symbol_exists(symbol_name))
  14496. return true;
  14497. else if (local_data().function_store.symbol_exists(symbol_name))
  14498. return true;
  14499. else if (check_reserved_symb && local_data().is_reserved_symbol(symbol_name))
  14500. return true;
  14501. else
  14502. return false;
  14503. }
  14504. inline bool is_variable(const std::string& variable_name) const
  14505. {
  14506. if (!valid())
  14507. return false;
  14508. else
  14509. return local_data().variable_store.symbol_exists(variable_name);
  14510. }
  14511. #ifndef exprtk_disable_string_capabilities
  14512. inline bool is_stringvar(const std::string& stringvar_name) const
  14513. {
  14514. if (!valid())
  14515. return false;
  14516. else
  14517. return local_data().stringvar_store.symbol_exists(stringvar_name);
  14518. }
  14519. inline bool is_conststr_stringvar(const std::string& symbol_name) const
  14520. {
  14521. if (!valid())
  14522. return false;
  14523. else if (!valid_symbol(symbol_name))
  14524. return false;
  14525. else if (!local_data().stringvar_store.symbol_exists(symbol_name))
  14526. return false;
  14527. return (
  14528. local_data().stringvar_store.symbol_exists(symbol_name) ||
  14529. local_data().stringvar_store.is_constant (symbol_name)
  14530. );
  14531. }
  14532. #endif
  14533. inline bool is_function(const std::string& function_name) const
  14534. {
  14535. if (!valid())
  14536. return false;
  14537. else
  14538. return local_data().function_store.symbol_exists(function_name);
  14539. }
  14540. inline bool is_vararg_function(const std::string& vararg_function_name) const
  14541. {
  14542. if (!valid())
  14543. return false;
  14544. else
  14545. return local_data().vararg_function_store.symbol_exists(vararg_function_name);
  14546. }
  14547. inline bool is_vector(const std::string& vector_name) const
  14548. {
  14549. if (!valid())
  14550. return false;
  14551. else
  14552. return local_data().vector_store.symbol_exists(vector_name);
  14553. }
  14554. inline std::string get_variable_name(const expression_ptr& ptr) const
  14555. {
  14556. return local_data().variable_store.entity_name(ptr);
  14557. }
  14558. inline std::string get_vector_name(const vector_holder_ptr& ptr) const
  14559. {
  14560. return local_data().vector_store.entity_name(ptr);
  14561. }
  14562. #ifndef exprtk_disable_string_capabilities
  14563. inline std::string get_stringvar_name(const expression_ptr& ptr) const
  14564. {
  14565. return local_data().stringvar_store.entity_name(ptr);
  14566. }
  14567. inline std::string get_conststr_stringvar_name(const expression_ptr& ptr) const
  14568. {
  14569. return local_data().stringvar_store.entity_name(ptr);
  14570. }
  14571. #endif
  14572. inline bool valid() const
  14573. {
  14574. // Symbol table sanity check.
  14575. return control_block_ && control_block_->data_;
  14576. }
  14577. inline void load_from(const symbol_table<T>& st)
  14578. {
  14579. {
  14580. std::vector<std::string> name_list;
  14581. st.local_data().function_store.get_list(name_list);
  14582. if (!name_list.empty())
  14583. {
  14584. for (std::size_t i = 0; i < name_list.size(); ++i)
  14585. {
  14586. exprtk::ifunction<T>& ifunc = *st.get_function(name_list[i]);
  14587. add_function(name_list[i],ifunc);
  14588. }
  14589. }
  14590. }
  14591. {
  14592. std::vector<std::string> name_list;
  14593. st.local_data().vararg_function_store.get_list(name_list);
  14594. if (!name_list.empty())
  14595. {
  14596. for (std::size_t i = 0; i < name_list.size(); ++i)
  14597. {
  14598. exprtk::ivararg_function<T>& ivafunc = *st.get_vararg_function(name_list[i]);
  14599. add_function(name_list[i],ivafunc);
  14600. }
  14601. }
  14602. }
  14603. {
  14604. std::vector<std::string> name_list;
  14605. st.local_data().generic_function_store.get_list(name_list);
  14606. if (!name_list.empty())
  14607. {
  14608. for (std::size_t i = 0; i < name_list.size(); ++i)
  14609. {
  14610. exprtk::igeneric_function<T>& ifunc = *st.get_generic_function(name_list[i]);
  14611. add_function(name_list[i],ifunc);
  14612. }
  14613. }
  14614. }
  14615. {
  14616. std::vector<std::string> name_list;
  14617. st.local_data().string_function_store.get_list(name_list);
  14618. if (!name_list.empty())
  14619. {
  14620. for (std::size_t i = 0; i < name_list.size(); ++i)
  14621. {
  14622. exprtk::igeneric_function<T>& ifunc = *st.get_string_function(name_list[i]);
  14623. add_function(name_list[i],ifunc);
  14624. }
  14625. }
  14626. }
  14627. {
  14628. std::vector<std::string> name_list;
  14629. st.local_data().overload_function_store.get_list(name_list);
  14630. if (!name_list.empty())
  14631. {
  14632. for (std::size_t i = 0; i < name_list.size(); ++i)
  14633. {
  14634. exprtk::igeneric_function<T>& ifunc = *st.get_overload_function(name_list[i]);
  14635. add_function(name_list[i],ifunc);
  14636. }
  14637. }
  14638. }
  14639. }
  14640. private:
  14641. inline bool valid_symbol(const std::string& symbol, const bool check_reserved_symb = true) const
  14642. {
  14643. if (symbol.empty())
  14644. return false;
  14645. else if (!details::is_letter(symbol[0]))
  14646. return false;
  14647. else if (symbol.size() > 1)
  14648. {
  14649. for (std::size_t i = 1; i < symbol.size(); ++i)
  14650. {
  14651. if (
  14652. !details::is_letter_or_digit(symbol[i]) &&
  14653. ('_' != symbol[i])
  14654. )
  14655. {
  14656. if (('.' == symbol[i]) && (i < (symbol.size() - 1)))
  14657. continue;
  14658. else
  14659. return false;
  14660. }
  14661. }
  14662. }
  14663. return (check_reserved_symb) ? (!local_data().is_reserved_symbol(symbol)) : true;
  14664. }
  14665. inline bool valid_function(const std::string& symbol) const
  14666. {
  14667. if (symbol.empty())
  14668. return false;
  14669. else if (!details::is_letter(symbol[0]))
  14670. return false;
  14671. else if (symbol.size() > 1)
  14672. {
  14673. for (std::size_t i = 1; i < symbol.size(); ++i)
  14674. {
  14675. if (
  14676. !details::is_letter_or_digit(symbol[i]) &&
  14677. ('_' != symbol[i])
  14678. )
  14679. {
  14680. if (('.' == symbol[i]) && (i < (symbol.size() - 1)))
  14681. continue;
  14682. else
  14683. return false;
  14684. }
  14685. }
  14686. }
  14687. return true;
  14688. }
  14689. typedef typename control_block::st_data local_data_t;
  14690. inline local_data_t& local_data()
  14691. {
  14692. return *(control_block_->data_);
  14693. }
  14694. inline const local_data_t& local_data() const
  14695. {
  14696. return *(control_block_->data_);
  14697. }
  14698. control_block* control_block_;
  14699. friend class parser<T>;
  14700. };
  14701. template <typename T>
  14702. class function_compositor;
  14703. template <typename T>
  14704. class expression
  14705. {
  14706. private:
  14707. typedef details::expression_node<T>* expression_ptr;
  14708. typedef details::vector_holder<T>* vector_holder_ptr;
  14709. typedef std::vector<symbol_table<T> > symtab_list_t;
  14710. struct control_block
  14711. {
  14712. enum data_type
  14713. {
  14714. e_unknown ,
  14715. e_expr ,
  14716. e_vecholder,
  14717. e_data ,
  14718. e_vecdata ,
  14719. e_string
  14720. };
  14721. struct data_pack
  14722. {
  14723. data_pack()
  14724. : pointer(0),
  14725. type(e_unknown),
  14726. size(0)
  14727. {}
  14728. data_pack(void* ptr, const data_type dt, const std::size_t sz = 0)
  14729. : pointer(ptr),
  14730. type(dt),
  14731. size(sz)
  14732. {}
  14733. void* pointer;
  14734. data_type type;
  14735. std::size_t size;
  14736. };
  14737. typedef std::vector<data_pack> local_data_list_t;
  14738. typedef results_context<T> results_context_t;
  14739. control_block()
  14740. : ref_count(0),
  14741. expr (0),
  14742. results (0),
  14743. retinv_null(false),
  14744. return_invoked(&retinv_null)
  14745. {}
  14746. explicit control_block(expression_ptr e)
  14747. : ref_count(1),
  14748. expr (e),
  14749. results (0),
  14750. retinv_null(false),
  14751. return_invoked(&retinv_null)
  14752. {}
  14753. ~control_block()
  14754. {
  14755. if (expr && details::branch_deletable(expr))
  14756. {
  14757. destroy_node(expr);
  14758. }
  14759. if (!local_data_list.empty())
  14760. {
  14761. for (std::size_t i = 0; i < local_data_list.size(); ++i)
  14762. {
  14763. switch (local_data_list[i].type)
  14764. {
  14765. case e_expr : delete reinterpret_cast<expression_ptr>(local_data_list[i].pointer);
  14766. break;
  14767. case e_vecholder : delete reinterpret_cast<vector_holder_ptr>(local_data_list[i].pointer);
  14768. break;
  14769. case e_data : delete (T*)(local_data_list[i].pointer);
  14770. break;
  14771. case e_vecdata : delete [] (T*)(local_data_list[i].pointer);
  14772. break;
  14773. case e_string : delete (std::string*)(local_data_list[i].pointer);
  14774. break;
  14775. default : break;
  14776. }
  14777. }
  14778. }
  14779. if (results)
  14780. {
  14781. delete results;
  14782. }
  14783. }
  14784. static inline control_block* create(expression_ptr e)
  14785. {
  14786. return new control_block(e);
  14787. }
  14788. static inline void destroy(control_block*& cntrl_blck)
  14789. {
  14790. if (cntrl_blck)
  14791. {
  14792. if (
  14793. (0 != cntrl_blck->ref_count) &&
  14794. (0 == --cntrl_blck->ref_count)
  14795. )
  14796. {
  14797. delete cntrl_blck;
  14798. }
  14799. cntrl_blck = 0;
  14800. }
  14801. }
  14802. std::size_t ref_count;
  14803. expression_ptr expr;
  14804. local_data_list_t local_data_list;
  14805. results_context_t* results;
  14806. bool retinv_null;
  14807. bool* return_invoked;
  14808. friend class function_compositor<T>;
  14809. };
  14810. public:
  14811. expression()
  14812. : control_block_(0)
  14813. {
  14814. set_expression(new details::null_node<T>());
  14815. }
  14816. expression(const expression<T>& e)
  14817. : control_block_ (e.control_block_ ),
  14818. symbol_table_list_(e.symbol_table_list_)
  14819. {
  14820. control_block_->ref_count++;
  14821. }
  14822. explicit expression(const symbol_table<T>& symbol_table)
  14823. : control_block_(0)
  14824. {
  14825. set_expression(new details::null_node<T>());
  14826. symbol_table_list_.push_back(symbol_table);
  14827. }
  14828. inline expression<T>& operator=(const expression<T>& e)
  14829. {
  14830. if (this != &e)
  14831. {
  14832. if (control_block_)
  14833. {
  14834. if (
  14835. (0 != control_block_->ref_count) &&
  14836. (0 == --control_block_->ref_count)
  14837. )
  14838. {
  14839. delete control_block_;
  14840. }
  14841. control_block_ = 0;
  14842. }
  14843. control_block_ = e.control_block_;
  14844. control_block_->ref_count++;
  14845. symbol_table_list_ = e.symbol_table_list_;
  14846. }
  14847. return *this;
  14848. }
  14849. inline bool operator==(const expression<T>& e) const
  14850. {
  14851. return (this == &e);
  14852. }
  14853. inline bool operator!() const
  14854. {
  14855. return (
  14856. (0 == control_block_ ) ||
  14857. (0 == control_block_->expr)
  14858. );
  14859. }
  14860. inline expression<T>& release()
  14861. {
  14862. control_block::destroy(control_block_);
  14863. return (*this);
  14864. }
  14865. ~expression()
  14866. {
  14867. control_block::destroy(control_block_);
  14868. }
  14869. inline T value() const
  14870. {
  14871. return control_block_->expr->value();
  14872. }
  14873. inline T operator() () const
  14874. {
  14875. return value();
  14876. }
  14877. inline operator T() const
  14878. {
  14879. return value();
  14880. }
  14881. inline operator bool() const
  14882. {
  14883. return details::is_true(value());
  14884. }
  14885. inline void register_symbol_table(symbol_table<T>& st)
  14886. {
  14887. symbol_table_list_.push_back(st);
  14888. }
  14889. inline const symbol_table<T>& get_symbol_table(const std::size_t& index = 0) const
  14890. {
  14891. return symbol_table_list_[index];
  14892. }
  14893. inline symbol_table<T>& get_symbol_table(const std::size_t& index = 0)
  14894. {
  14895. return symbol_table_list_[index];
  14896. }
  14897. typedef results_context<T> results_context_t;
  14898. inline const results_context_t& results() const
  14899. {
  14900. if (control_block_->results)
  14901. return (*control_block_->results);
  14902. else
  14903. {
  14904. static const results_context_t null_results;
  14905. return null_results;
  14906. }
  14907. }
  14908. inline bool return_invoked() const
  14909. {
  14910. return (*control_block_->return_invoked);
  14911. }
  14912. private:
  14913. inline symtab_list_t get_symbol_table_list() const
  14914. {
  14915. return symbol_table_list_;
  14916. }
  14917. inline void set_expression(const expression_ptr expr)
  14918. {
  14919. if (expr)
  14920. {
  14921. if (control_block_)
  14922. {
  14923. if (0 == --control_block_->ref_count)
  14924. {
  14925. delete control_block_;
  14926. }
  14927. }
  14928. control_block_ = control_block::create(expr);
  14929. }
  14930. }
  14931. inline void register_local_var(expression_ptr expr)
  14932. {
  14933. if (expr)
  14934. {
  14935. if (control_block_)
  14936. {
  14937. control_block_->
  14938. local_data_list.push_back(
  14939. typename expression<T>::control_block::
  14940. data_pack(reinterpret_cast<void*>(expr),
  14941. control_block::e_expr));
  14942. }
  14943. }
  14944. }
  14945. inline void register_local_var(vector_holder_ptr vec_holder)
  14946. {
  14947. if (vec_holder)
  14948. {
  14949. if (control_block_)
  14950. {
  14951. control_block_->
  14952. local_data_list.push_back(
  14953. typename expression<T>::control_block::
  14954. data_pack(reinterpret_cast<void*>(vec_holder),
  14955. control_block::e_vecholder));
  14956. }
  14957. }
  14958. }
  14959. inline void register_local_data(void* data, const std::size_t& size = 0, const std::size_t data_mode = 0)
  14960. {
  14961. if (data)
  14962. {
  14963. if (control_block_)
  14964. {
  14965. typename control_block::data_type dt = control_block::e_data;
  14966. switch (data_mode)
  14967. {
  14968. case 0 : dt = control_block::e_data; break;
  14969. case 1 : dt = control_block::e_vecdata; break;
  14970. case 2 : dt = control_block::e_string; break;
  14971. }
  14972. control_block_->
  14973. local_data_list.push_back(
  14974. typename expression<T>::control_block::
  14975. data_pack(reinterpret_cast<void*>(data), dt, size));
  14976. }
  14977. }
  14978. }
  14979. inline const typename control_block::local_data_list_t& local_data_list()
  14980. {
  14981. if (control_block_)
  14982. {
  14983. return control_block_->local_data_list;
  14984. }
  14985. else
  14986. {
  14987. static typename control_block::local_data_list_t null_local_data_list;
  14988. return null_local_data_list;
  14989. }
  14990. }
  14991. inline void register_return_results(results_context_t* rc)
  14992. {
  14993. if (control_block_ && rc)
  14994. {
  14995. control_block_->results = rc;
  14996. }
  14997. }
  14998. inline void set_retinvk(bool* retinvk_ptr)
  14999. {
  15000. if (control_block_)
  15001. {
  15002. control_block_->return_invoked = retinvk_ptr;
  15003. }
  15004. }
  15005. control_block* control_block_;
  15006. symtab_list_t symbol_table_list_;
  15007. friend class parser<T>;
  15008. friend class expression_helper<T>;
  15009. friend class function_compositor<T>;
  15010. };
  15011. template <typename T>
  15012. class expression_helper
  15013. {
  15014. public:
  15015. static inline bool is_constant(const expression<T>& expr)
  15016. {
  15017. return details::is_constant_node(expr.control_block_->expr);
  15018. }
  15019. static inline bool is_variable(const expression<T>& expr)
  15020. {
  15021. return details::is_variable_node(expr.control_block_->expr);
  15022. }
  15023. static inline bool is_unary(const expression<T>& expr)
  15024. {
  15025. return details::is_unary_node(expr.control_block_->expr);
  15026. }
  15027. static inline bool is_binary(const expression<T>& expr)
  15028. {
  15029. return details::is_binary_node(expr.control_block_->expr);
  15030. }
  15031. static inline bool is_function(const expression<T>& expr)
  15032. {
  15033. return details::is_function(expr.control_block_->expr);
  15034. }
  15035. static inline bool is_null(const expression<T>& expr)
  15036. {
  15037. return details::is_null_node(expr.control_block_->expr);
  15038. }
  15039. };
  15040. template <typename T>
  15041. inline bool is_valid(const expression<T>& expr)
  15042. {
  15043. return !expression_helper<T>::is_null(expr);
  15044. }
  15045. namespace parser_error
  15046. {
  15047. enum error_mode
  15048. {
  15049. e_unknown = 0,
  15050. e_syntax = 1,
  15051. e_token = 2,
  15052. e_numeric = 4,
  15053. e_symtab = 5,
  15054. e_lexer = 6,
  15055. e_helper = 7
  15056. };
  15057. struct type
  15058. {
  15059. type()
  15060. : mode(parser_error::e_unknown),
  15061. line_no (0),
  15062. column_no(0)
  15063. {}
  15064. lexer::token token;
  15065. error_mode mode;
  15066. std::string diagnostic;
  15067. std::string src_location;
  15068. std::string error_line;
  15069. std::size_t line_no;
  15070. std::size_t column_no;
  15071. };
  15072. inline type make_error(const error_mode mode,
  15073. const std::string& diagnostic = "",
  15074. const std::string& src_location = "")
  15075. {
  15076. type t;
  15077. t.mode = mode;
  15078. t.token.type = lexer::token::e_error;
  15079. t.diagnostic = diagnostic;
  15080. t.src_location = src_location;
  15081. exprtk_debug(("%s\n",diagnostic .c_str()));
  15082. return t;
  15083. }
  15084. inline type make_error(const error_mode mode,
  15085. const lexer::token& tk,
  15086. const std::string& diagnostic = "",
  15087. const std::string& src_location = "")
  15088. {
  15089. type t;
  15090. t.mode = mode;
  15091. t.token = tk;
  15092. t.diagnostic = diagnostic;
  15093. t.src_location = src_location;
  15094. exprtk_debug(("%s\n",diagnostic .c_str()));
  15095. return t;
  15096. }
  15097. inline std::string to_str(error_mode mode)
  15098. {
  15099. switch (mode)
  15100. {
  15101. case e_unknown : return std::string("Unknown Error");
  15102. case e_syntax : return std::string("Syntax Error" );
  15103. case e_token : return std::string("Token Error" );
  15104. case e_numeric : return std::string("Numeric Error");
  15105. case e_symtab : return std::string("Symbol Error" );
  15106. case e_lexer : return std::string("Lexer Error" );
  15107. case e_helper : return std::string("Helper Error" );
  15108. default : return std::string("Unknown Error");
  15109. }
  15110. }
  15111. inline bool update_error(type& error, const std::string& expression)
  15112. {
  15113. if (
  15114. expression.empty() ||
  15115. (error.token.position > expression.size()) ||
  15116. (std::numeric_limits<std::size_t>::max() == error.token.position)
  15117. )
  15118. {
  15119. return false;
  15120. }
  15121. std::size_t error_line_start = 0;
  15122. for (std::size_t i = error.token.position; i > 0; --i)
  15123. {
  15124. const details::char_t c = expression[i];
  15125. if (('\n' == c) || ('\r' == c))
  15126. {
  15127. error_line_start = i + 1;
  15128. break;
  15129. }
  15130. }
  15131. std::size_t next_nl_position = std::min(expression.size(),
  15132. expression.find_first_of('\n',error.token.position + 1));
  15133. error.column_no = error.token.position - error_line_start;
  15134. error.error_line = expression.substr(error_line_start,
  15135. next_nl_position - error_line_start);
  15136. error.line_no = 0;
  15137. for (std::size_t i = 0; i < next_nl_position; ++i)
  15138. {
  15139. if ('\n' == expression[i])
  15140. ++error.line_no;
  15141. }
  15142. return true;
  15143. }
  15144. inline void dump_error(const type& error)
  15145. {
  15146. printf("Position: %02d Type: [%s] Msg: %s\n",
  15147. static_cast<int>(error.token.position),
  15148. exprtk::parser_error::to_str(error.mode).c_str(),
  15149. error.diagnostic.c_str());
  15150. }
  15151. }
  15152. namespace details
  15153. {
  15154. template <typename Parser>
  15155. inline void disable_type_checking(Parser& p)
  15156. {
  15157. p.state_.type_check_enabled = false;
  15158. }
  15159. }
  15160. template <typename T>
  15161. class parser : public lexer::parser_helper
  15162. {
  15163. private:
  15164. enum precedence_level
  15165. {
  15166. e_level00,
  15167. e_level01,
  15168. e_level02,
  15169. e_level03,
  15170. e_level04,
  15171. e_level05,
  15172. e_level06,
  15173. e_level07,
  15174. e_level08,
  15175. e_level09,
  15176. e_level10,
  15177. e_level11,
  15178. e_level12,
  15179. e_level13,
  15180. e_level14
  15181. };
  15182. typedef const T& cref_t;
  15183. typedef const T const_t;
  15184. typedef ifunction <T> F;
  15185. typedef ivararg_function <T> VAF;
  15186. typedef igeneric_function <T> GF;
  15187. typedef ifunction <T> ifunction_t;
  15188. typedef ivararg_function <T> ivararg_function_t;
  15189. typedef igeneric_function <T> igeneric_function_t;
  15190. typedef details::expression_node <T> expression_node_t;
  15191. typedef details::literal_node <T> literal_node_t;
  15192. typedef details::unary_node <T> unary_node_t;
  15193. typedef details::binary_node <T> binary_node_t;
  15194. typedef details::trinary_node <T> trinary_node_t;
  15195. typedef details::quaternary_node <T> quaternary_node_t;
  15196. typedef details::conditional_node<T> conditional_node_t;
  15197. typedef details::cons_conditional_node<T> cons_conditional_node_t;
  15198. typedef details::while_loop_node <T> while_loop_node_t;
  15199. typedef details::repeat_until_loop_node<T> repeat_until_loop_node_t;
  15200. typedef details::for_loop_node <T> for_loop_node_t;
  15201. #ifndef exprtk_disable_break_continue
  15202. typedef details::while_loop_bc_node <T> while_loop_bc_node_t;
  15203. typedef details::repeat_until_loop_bc_node<T> repeat_until_loop_bc_node_t;
  15204. typedef details::for_loop_bc_node<T> for_loop_bc_node_t;
  15205. #endif
  15206. typedef details::switch_node <T> switch_node_t;
  15207. typedef details::variable_node <T> variable_node_t;
  15208. typedef details::vector_elem_node<T> vector_elem_node_t;
  15209. typedef details::rebasevector_elem_node<T> rebasevector_elem_node_t;
  15210. typedef details::rebasevector_celem_node<T> rebasevector_celem_node_t;
  15211. typedef details::vector_node <T> vector_node_t;
  15212. typedef details::range_pack <T> range_t;
  15213. #ifndef exprtk_disable_string_capabilities
  15214. typedef details::stringvar_node <T> stringvar_node_t;
  15215. typedef details::string_literal_node<T> string_literal_node_t;
  15216. typedef details::string_range_node <T> string_range_node_t;
  15217. typedef details::const_string_range_node<T> const_string_range_node_t;
  15218. typedef details::generic_string_range_node<T> generic_string_range_node_t;
  15219. typedef details::string_concat_node <T> string_concat_node_t;
  15220. typedef details::assignment_string_node<T> assignment_string_node_t;
  15221. typedef details::assignment_string_range_node<T> assignment_string_range_node_t;
  15222. typedef details::conditional_string_node<T> conditional_string_node_t;
  15223. typedef details::cons_conditional_str_node<T> cons_conditional_str_node_t;
  15224. #endif
  15225. typedef details::assignment_node<T> assignment_node_t;
  15226. typedef details::assignment_vec_elem_node <T> assignment_vec_elem_node_t;
  15227. typedef details::assignment_rebasevec_elem_node <T> assignment_rebasevec_elem_node_t;
  15228. typedef details::assignment_rebasevec_celem_node<T> assignment_rebasevec_celem_node_t;
  15229. typedef details::assignment_vec_node <T> assignment_vec_node_t;
  15230. typedef details::assignment_vecvec_node <T> assignment_vecvec_node_t;
  15231. typedef details::scand_node<T> scand_node_t;
  15232. typedef details::scor_node<T> scor_node_t;
  15233. typedef lexer::token token_t;
  15234. typedef expression_node_t* expression_node_ptr;
  15235. typedef expression<T> expression_t;
  15236. typedef symbol_table<T> symbol_table_t;
  15237. typedef typename expression<T>::symtab_list_t symbol_table_list_t;
  15238. typedef details::vector_holder<T>* vector_holder_ptr;
  15239. typedef typename details::functor_t<T> functor_t;
  15240. typedef typename functor_t::qfunc_t quaternary_functor_t;
  15241. typedef typename functor_t::tfunc_t trinary_functor_t;
  15242. typedef typename functor_t::bfunc_t binary_functor_t;
  15243. typedef typename functor_t::ufunc_t unary_functor_t;
  15244. typedef details::operator_type operator_t;
  15245. typedef std::map<operator_t, unary_functor_t> unary_op_map_t;
  15246. typedef std::map<operator_t, binary_functor_t> binary_op_map_t;
  15247. typedef std::map<operator_t,trinary_functor_t> trinary_op_map_t;
  15248. typedef std::map<std::string,std::pair<trinary_functor_t ,operator_t> > sf3_map_t;
  15249. typedef std::map<std::string,std::pair<quaternary_functor_t,operator_t> > sf4_map_t;
  15250. typedef std::map<binary_functor_t,operator_t> inv_binary_op_map_t;
  15251. typedef std::multimap<std::string,details::base_operation_t,details::ilesscompare> base_ops_map_t;
  15252. typedef std::set<std::string,details::ilesscompare> disabled_func_set_t;
  15253. typedef details::T0oT1_define<T, cref_t, cref_t> vov_t;
  15254. typedef details::T0oT1_define<T, const_t, cref_t> cov_t;
  15255. typedef details::T0oT1_define<T, cref_t, const_t> voc_t;
  15256. typedef details::T0oT1oT2_define<T, cref_t, cref_t, cref_t> vovov_t;
  15257. typedef details::T0oT1oT2_define<T, cref_t, cref_t, const_t> vovoc_t;
  15258. typedef details::T0oT1oT2_define<T, cref_t, const_t, cref_t> vocov_t;
  15259. typedef details::T0oT1oT2_define<T, const_t, cref_t, cref_t> covov_t;
  15260. typedef details::T0oT1oT2_define<T, const_t, cref_t, const_t> covoc_t;
  15261. typedef details::T0oT1oT2_define<T, const_t, const_t, cref_t> cocov_t;
  15262. typedef details::T0oT1oT2_define<T, cref_t, const_t, const_t> vococ_t;
  15263. typedef details::T0oT1oT2oT3_define<T, cref_t, cref_t, cref_t, cref_t> vovovov_t;
  15264. typedef details::T0oT1oT2oT3_define<T, cref_t, cref_t, cref_t, const_t> vovovoc_t;
  15265. typedef details::T0oT1oT2oT3_define<T, cref_t, cref_t, const_t, cref_t> vovocov_t;
  15266. typedef details::T0oT1oT2oT3_define<T, cref_t, const_t, cref_t, cref_t> vocovov_t;
  15267. typedef details::T0oT1oT2oT3_define<T, const_t, cref_t, cref_t, cref_t> covovov_t;
  15268. typedef details::T0oT1oT2oT3_define<T, const_t, cref_t, const_t, cref_t> covocov_t;
  15269. typedef details::T0oT1oT2oT3_define<T, cref_t, const_t, cref_t, const_t> vocovoc_t;
  15270. typedef details::T0oT1oT2oT3_define<T, const_t, cref_t, cref_t, const_t> covovoc_t;
  15271. typedef details::T0oT1oT2oT3_define<T, cref_t, const_t, const_t, cref_t> vococov_t;
  15272. typedef results_context<T> results_context_t;
  15273. typedef parser_helper prsrhlpr_t;
  15274. struct scope_element
  15275. {
  15276. enum element_type
  15277. {
  15278. e_none ,
  15279. e_variable,
  15280. e_vector ,
  15281. e_vecelem ,
  15282. e_string
  15283. };
  15284. typedef details::vector_holder<T> vector_holder_t;
  15285. typedef variable_node_t* variable_node_ptr;
  15286. typedef vector_holder_t* vector_holder_ptr;
  15287. typedef expression_node_t* expression_node_ptr;
  15288. #ifndef exprtk_disable_string_capabilities
  15289. typedef stringvar_node_t* stringvar_node_ptr;
  15290. #endif
  15291. scope_element()
  15292. : name("???"),
  15293. size (std::numeric_limits<std::size_t>::max()),
  15294. index(std::numeric_limits<std::size_t>::max()),
  15295. depth(std::numeric_limits<std::size_t>::max()),
  15296. ref_count(0),
  15297. ip_index (0),
  15298. type (e_none),
  15299. active(false),
  15300. data (0),
  15301. var_node(0),
  15302. vec_node(0)
  15303. #ifndef exprtk_disable_string_capabilities
  15304. ,str_node(0)
  15305. #endif
  15306. {}
  15307. bool operator < (const scope_element& se) const
  15308. {
  15309. if (ip_index < se.ip_index)
  15310. return true;
  15311. else if (ip_index > se.ip_index)
  15312. return false;
  15313. else if (depth < se.depth)
  15314. return true;
  15315. else if (depth > se.depth)
  15316. return false;
  15317. else if (index < se.index)
  15318. return true;
  15319. else if (index > se.index)
  15320. return false;
  15321. else
  15322. return (name < se.name);
  15323. }
  15324. void clear()
  15325. {
  15326. name = "???";
  15327. size = std::numeric_limits<std::size_t>::max();
  15328. index = std::numeric_limits<std::size_t>::max();
  15329. depth = std::numeric_limits<std::size_t>::max();
  15330. type = e_none;
  15331. active = false;
  15332. ref_count = 0;
  15333. ip_index = 0;
  15334. data = 0;
  15335. var_node = 0;
  15336. vec_node = 0;
  15337. #ifndef exprtk_disable_string_capabilities
  15338. str_node = 0;
  15339. #endif
  15340. }
  15341. std::string name;
  15342. std::size_t size;
  15343. std::size_t index;
  15344. std::size_t depth;
  15345. std::size_t ref_count;
  15346. std::size_t ip_index;
  15347. element_type type;
  15348. bool active;
  15349. void* data;
  15350. expression_node_ptr var_node;
  15351. vector_holder_ptr vec_node;
  15352. #ifndef exprtk_disable_string_capabilities
  15353. stringvar_node_ptr str_node;
  15354. #endif
  15355. };
  15356. class scope_element_manager
  15357. {
  15358. public:
  15359. typedef expression_node_t* expression_node_ptr;
  15360. typedef variable_node_t* variable_node_ptr;
  15361. typedef parser<T> parser_t;
  15362. explicit scope_element_manager(parser<T>& p)
  15363. : parser_(p),
  15364. input_param_cnt_(0)
  15365. {}
  15366. inline std::size_t size() const
  15367. {
  15368. return element_.size();
  15369. }
  15370. inline bool empty() const
  15371. {
  15372. return element_.empty();
  15373. }
  15374. inline scope_element& get_element(const std::size_t& index)
  15375. {
  15376. if (index < element_.size())
  15377. return element_[index];
  15378. else
  15379. return null_element_;
  15380. }
  15381. inline scope_element& get_element(const std::string& var_name,
  15382. const std::size_t index = std::numeric_limits<std::size_t>::max())
  15383. {
  15384. const std::size_t current_depth = parser_.state_.scope_depth;
  15385. for (std::size_t i = 0; i < element_.size(); ++i)
  15386. {
  15387. scope_element& se = element_[i];
  15388. if (se.depth > current_depth)
  15389. continue;
  15390. else if (
  15391. details::imatch(se.name, var_name) &&
  15392. (se.index == index)
  15393. )
  15394. return se;
  15395. }
  15396. return null_element_;
  15397. }
  15398. inline scope_element& get_active_element(const std::string& var_name,
  15399. const std::size_t index = std::numeric_limits<std::size_t>::max())
  15400. {
  15401. const std::size_t current_depth = parser_.state_.scope_depth;
  15402. for (std::size_t i = 0; i < element_.size(); ++i)
  15403. {
  15404. scope_element& se = element_[i];
  15405. if (se.depth > current_depth)
  15406. continue;
  15407. else if (
  15408. details::imatch(se.name, var_name) &&
  15409. (se.index == index) &&
  15410. (se.active)
  15411. )
  15412. return se;
  15413. }
  15414. return null_element_;
  15415. }
  15416. inline bool add_element(const scope_element& se)
  15417. {
  15418. for (std::size_t i = 0; i < element_.size(); ++i)
  15419. {
  15420. scope_element& cse = element_[i];
  15421. if (
  15422. details::imatch(cse.name, se.name) &&
  15423. (cse.depth <= se.depth) &&
  15424. (cse.index == se.index) &&
  15425. (cse.size == se.size ) &&
  15426. (cse.type == se.type ) &&
  15427. (cse.active)
  15428. )
  15429. return false;
  15430. }
  15431. element_.push_back(se);
  15432. std::sort(element_.begin(),element_.end());
  15433. return true;
  15434. }
  15435. inline void deactivate(const std::size_t& scope_depth)
  15436. {
  15437. exprtk_debug(("deactivate() - Scope depth: %d\n",
  15438. static_cast<int>(parser_.state_.scope_depth)));
  15439. for (std::size_t i = 0; i < element_.size(); ++i)
  15440. {
  15441. scope_element& se = element_[i];
  15442. if (se.active && (se.depth >= scope_depth))
  15443. {
  15444. exprtk_debug(("deactivate() - element[%02d] '%s'\n",
  15445. static_cast<int>(i),
  15446. se.name.c_str()));
  15447. se.active = false;
  15448. }
  15449. }
  15450. }
  15451. inline void free_element(scope_element& se)
  15452. {
  15453. #ifdef exprtk_enable_debugging
  15454. exprtk_debug(("free_element() - se[%s]\n", se.name.c_str()));
  15455. #endif
  15456. switch (se.type)
  15457. {
  15458. case scope_element::e_variable : if (se.data ) delete (T*) se.data;
  15459. if (se.var_node) delete se.var_node;
  15460. break;
  15461. case scope_element::e_vector : if (se.data ) delete[] (T*) se.data;
  15462. if (se.vec_node) delete se.vec_node;
  15463. break;
  15464. case scope_element::e_vecelem : if (se.var_node) delete se.var_node;
  15465. break;
  15466. #ifndef exprtk_disable_string_capabilities
  15467. case scope_element::e_string : if (se.data ) delete (std::string*) se.data;
  15468. if (se.str_node) delete se.str_node;
  15469. break;
  15470. #endif
  15471. default : return;
  15472. }
  15473. se.clear();
  15474. }
  15475. inline void cleanup()
  15476. {
  15477. for (std::size_t i = 0; i < element_.size(); ++i)
  15478. {
  15479. free_element(element_[i]);
  15480. }
  15481. element_.clear();
  15482. input_param_cnt_ = 0;
  15483. }
  15484. inline std::size_t next_ip_index()
  15485. {
  15486. return ++input_param_cnt_;
  15487. }
  15488. inline expression_node_ptr get_variable(const T& v)
  15489. {
  15490. for (std::size_t i = 0; i < element_.size(); ++i)
  15491. {
  15492. scope_element& se = element_[i];
  15493. if (
  15494. se.active &&
  15495. se.var_node &&
  15496. details::is_variable_node(se.var_node)
  15497. )
  15498. {
  15499. variable_node_ptr vn = reinterpret_cast<variable_node_ptr>(se.var_node);
  15500. if (&(vn->ref()) == (&v))
  15501. {
  15502. return se.var_node;
  15503. }
  15504. }
  15505. }
  15506. return expression_node_ptr(0);
  15507. }
  15508. private:
  15509. scope_element_manager& operator=(const scope_element_manager&);
  15510. parser_t& parser_;
  15511. std::vector<scope_element> element_;
  15512. scope_element null_element_;
  15513. std::size_t input_param_cnt_;
  15514. };
  15515. class scope_handler
  15516. {
  15517. public:
  15518. typedef parser<T> parser_t;
  15519. explicit scope_handler(parser<T>& p)
  15520. : parser_(p)
  15521. {
  15522. parser_.state_.scope_depth++;
  15523. #ifdef exprtk_enable_debugging
  15524. const std::string depth(2 * parser_.state_.scope_depth,'-');
  15525. exprtk_debug(("%s> Scope Depth: %02d\n",
  15526. depth.c_str(),
  15527. static_cast<int>(parser_.state_.scope_depth)));
  15528. #endif
  15529. }
  15530. ~scope_handler()
  15531. {
  15532. parser_.sem_.deactivate(parser_.state_.scope_depth);
  15533. parser_.state_.scope_depth--;
  15534. #ifdef exprtk_enable_debugging
  15535. const std::string depth(2 * parser_.state_.scope_depth,'-');
  15536. exprtk_debug(("<%s Scope Depth: %02d\n",
  15537. depth.c_str(),
  15538. static_cast<int>(parser_.state_.scope_depth)));
  15539. #endif
  15540. }
  15541. private:
  15542. scope_handler& operator=(const scope_handler&);
  15543. parser_t& parser_;
  15544. };
  15545. struct symtab_store
  15546. {
  15547. symbol_table_list_t symtab_list_;
  15548. typedef typename symbol_table_t::local_data_t local_data_t;
  15549. typedef typename symbol_table_t::variable_ptr variable_ptr;
  15550. typedef typename symbol_table_t::function_ptr function_ptr;
  15551. #ifndef exprtk_disable_string_capabilities
  15552. typedef typename symbol_table_t::stringvar_ptr stringvar_ptr;
  15553. #endif
  15554. typedef typename symbol_table_t::vector_holder_ptr vector_holder_ptr;
  15555. typedef typename symbol_table_t::vararg_function_ptr vararg_function_ptr;
  15556. typedef typename symbol_table_t::generic_function_ptr generic_function_ptr;
  15557. inline bool empty() const
  15558. {
  15559. return symtab_list_.empty();
  15560. }
  15561. inline void clear()
  15562. {
  15563. symtab_list_.clear();
  15564. }
  15565. inline bool valid() const
  15566. {
  15567. if (!empty())
  15568. {
  15569. for (std::size_t i = 0; i < symtab_list_.size(); ++i)
  15570. {
  15571. if (symtab_list_[i].valid())
  15572. return true;
  15573. }
  15574. }
  15575. return false;
  15576. }
  15577. inline bool valid_symbol(const std::string& symbol) const
  15578. {
  15579. if (!symtab_list_.empty())
  15580. return symtab_list_[0].valid_symbol(symbol);
  15581. else
  15582. return false;
  15583. }
  15584. inline bool valid_function_name(const std::string& symbol) const
  15585. {
  15586. if (!symtab_list_.empty())
  15587. return symtab_list_[0].valid_function(symbol);
  15588. else
  15589. return false;
  15590. }
  15591. inline variable_ptr get_variable(const std::string& variable_name) const
  15592. {
  15593. if (!valid_symbol(variable_name))
  15594. return reinterpret_cast<variable_ptr>(0);
  15595. variable_ptr result = reinterpret_cast<variable_ptr>(0);
  15596. for (std::size_t i = 0; i < symtab_list_.size(); ++i)
  15597. {
  15598. if (!symtab_list_[i].valid())
  15599. continue;
  15600. else
  15601. result = local_data(i)
  15602. .variable_store.get(variable_name);
  15603. if (result) break;
  15604. }
  15605. return result;
  15606. }
  15607. inline variable_ptr get_variable(const T& var_ref) const
  15608. {
  15609. variable_ptr result = reinterpret_cast<variable_ptr>(0);
  15610. for (std::size_t i = 0; i < symtab_list_.size(); ++i)
  15611. {
  15612. if (!symtab_list_[i].valid())
  15613. continue;
  15614. else
  15615. result = local_data(i).variable_store
  15616. .get_from_varptr(reinterpret_cast<const void*>(&var_ref));
  15617. if (result) break;
  15618. }
  15619. return result;
  15620. }
  15621. #ifndef exprtk_disable_string_capabilities
  15622. inline stringvar_ptr get_stringvar(const std::string& string_name) const
  15623. {
  15624. if (!valid_symbol(string_name))
  15625. return reinterpret_cast<stringvar_ptr>(0);
  15626. stringvar_ptr result = reinterpret_cast<stringvar_ptr>(0);
  15627. for (std::size_t i = 0; i < symtab_list_.size(); ++i)
  15628. {
  15629. if (!symtab_list_[i].valid())
  15630. continue;
  15631. else
  15632. result = local_data(i)
  15633. .stringvar_store.get(string_name);
  15634. if (result) break;
  15635. }
  15636. return result;
  15637. }
  15638. #endif
  15639. inline function_ptr get_function(const std::string& function_name) const
  15640. {
  15641. if (!valid_function_name(function_name))
  15642. return reinterpret_cast<function_ptr>(0);
  15643. function_ptr result = reinterpret_cast<function_ptr>(0);
  15644. for (std::size_t i = 0; i < symtab_list_.size(); ++i)
  15645. {
  15646. if (!symtab_list_[i].valid())
  15647. continue;
  15648. else
  15649. result = local_data(i)
  15650. .function_store.get(function_name);
  15651. if (result) break;
  15652. }
  15653. return result;
  15654. }
  15655. inline vararg_function_ptr get_vararg_function(const std::string& vararg_function_name) const
  15656. {
  15657. if (!valid_function_name(vararg_function_name))
  15658. return reinterpret_cast<vararg_function_ptr>(0);
  15659. vararg_function_ptr result = reinterpret_cast<vararg_function_ptr>(0);
  15660. for (std::size_t i = 0; i < symtab_list_.size(); ++i)
  15661. {
  15662. if (!symtab_list_[i].valid())
  15663. continue;
  15664. else
  15665. result = local_data(i)
  15666. .vararg_function_store.get(vararg_function_name);
  15667. if (result) break;
  15668. }
  15669. return result;
  15670. }
  15671. inline generic_function_ptr get_generic_function(const std::string& function_name) const
  15672. {
  15673. if (!valid_function_name(function_name))
  15674. return reinterpret_cast<generic_function_ptr>(0);
  15675. generic_function_ptr result = reinterpret_cast<generic_function_ptr>(0);
  15676. for (std::size_t i = 0; i < symtab_list_.size(); ++i)
  15677. {
  15678. if (!symtab_list_[i].valid())
  15679. continue;
  15680. else
  15681. result = local_data(i)
  15682. .generic_function_store.get(function_name);
  15683. if (result) break;
  15684. }
  15685. return result;
  15686. }
  15687. inline generic_function_ptr get_string_function(const std::string& function_name) const
  15688. {
  15689. if (!valid_function_name(function_name))
  15690. return reinterpret_cast<generic_function_ptr>(0);
  15691. generic_function_ptr result = reinterpret_cast<generic_function_ptr>(0);
  15692. for (std::size_t i = 0; i < symtab_list_.size(); ++i)
  15693. {
  15694. if (!symtab_list_[i].valid())
  15695. continue;
  15696. else
  15697. result =
  15698. local_data(i).string_function_store.get(function_name);
  15699. if (result) break;
  15700. }
  15701. return result;
  15702. }
  15703. inline generic_function_ptr get_overload_function(const std::string& function_name) const
  15704. {
  15705. if (!valid_function_name(function_name))
  15706. return reinterpret_cast<generic_function_ptr>(0);
  15707. generic_function_ptr result = reinterpret_cast<generic_function_ptr>(0);
  15708. for (std::size_t i = 0; i < symtab_list_.size(); ++i)
  15709. {
  15710. if (!symtab_list_[i].valid())
  15711. continue;
  15712. else
  15713. result =
  15714. local_data(i).overload_function_store.get(function_name);
  15715. if (result) break;
  15716. }
  15717. return result;
  15718. }
  15719. inline vector_holder_ptr get_vector(const std::string& vector_name) const
  15720. {
  15721. if (!valid_symbol(vector_name))
  15722. return reinterpret_cast<vector_holder_ptr>(0);
  15723. vector_holder_ptr result = reinterpret_cast<vector_holder_ptr>(0);
  15724. for (std::size_t i = 0; i < symtab_list_.size(); ++i)
  15725. {
  15726. if (!symtab_list_[i].valid())
  15727. continue;
  15728. else
  15729. result =
  15730. local_data(i).vector_store.get(vector_name);
  15731. if (result) break;
  15732. }
  15733. return result;
  15734. }
  15735. inline bool is_constant_node(const std::string& symbol_name) const
  15736. {
  15737. if (!valid_symbol(symbol_name))
  15738. return false;
  15739. for (std::size_t i = 0; i < symtab_list_.size(); ++i)
  15740. {
  15741. if (!symtab_list_[i].valid())
  15742. continue;
  15743. else if (local_data(i).variable_store.is_constant(symbol_name))
  15744. return true;
  15745. }
  15746. return false;
  15747. }
  15748. #ifndef exprtk_disable_string_capabilities
  15749. inline bool is_constant_string(const std::string& symbol_name) const
  15750. {
  15751. if (!valid_symbol(symbol_name))
  15752. return false;
  15753. for (std::size_t i = 0; i < symtab_list_.size(); ++i)
  15754. {
  15755. if (!symtab_list_[i].valid())
  15756. continue;
  15757. else if (!local_data(i).stringvar_store.symbol_exists(symbol_name))
  15758. continue;
  15759. else if ( local_data(i).stringvar_store.is_constant(symbol_name))
  15760. return true;
  15761. }
  15762. return false;
  15763. }
  15764. #endif
  15765. inline bool symbol_exists(const std::string& symbol) const
  15766. {
  15767. for (std::size_t i = 0; i < symtab_list_.size(); ++i)
  15768. {
  15769. if (!symtab_list_[i].valid())
  15770. continue;
  15771. else if (symtab_list_[i].symbol_exists(symbol))
  15772. return true;
  15773. }
  15774. return false;
  15775. }
  15776. inline bool is_variable(const std::string& variable_name) const
  15777. {
  15778. for (std::size_t i = 0; i < symtab_list_.size(); ++i)
  15779. {
  15780. if (!symtab_list_[i].valid())
  15781. continue;
  15782. else if (
  15783. symtab_list_[i].local_data().variable_store
  15784. .symbol_exists(variable_name)
  15785. )
  15786. return true;
  15787. }
  15788. return false;
  15789. }
  15790. #ifndef exprtk_disable_string_capabilities
  15791. inline bool is_stringvar(const std::string& stringvar_name) const
  15792. {
  15793. for (std::size_t i = 0; i < symtab_list_.size(); ++i)
  15794. {
  15795. if (!symtab_list_[i].valid())
  15796. continue;
  15797. else if (
  15798. symtab_list_[i].local_data().stringvar_store
  15799. .symbol_exists(stringvar_name)
  15800. )
  15801. return true;
  15802. }
  15803. return false;
  15804. }
  15805. inline bool is_conststr_stringvar(const std::string& symbol_name) const
  15806. {
  15807. for (std::size_t i = 0; i < symtab_list_.size(); ++i)
  15808. {
  15809. if (!symtab_list_[i].valid())
  15810. continue;
  15811. else if (
  15812. symtab_list_[i].local_data().stringvar_store
  15813. .symbol_exists(symbol_name)
  15814. )
  15815. {
  15816. return (
  15817. local_data(i).stringvar_store.symbol_exists(symbol_name) ||
  15818. local_data(i).stringvar_store.is_constant (symbol_name)
  15819. );
  15820. }
  15821. }
  15822. return false;
  15823. }
  15824. #endif
  15825. inline bool is_function(const std::string& function_name) const
  15826. {
  15827. for (std::size_t i = 0; i < symtab_list_.size(); ++i)
  15828. {
  15829. if (!symtab_list_[i].valid())
  15830. continue;
  15831. else if (
  15832. local_data(i).vararg_function_store
  15833. .symbol_exists(function_name)
  15834. )
  15835. return true;
  15836. }
  15837. return false;
  15838. }
  15839. inline bool is_vararg_function(const std::string& vararg_function_name) const
  15840. {
  15841. for (std::size_t i = 0; i < symtab_list_.size(); ++i)
  15842. {
  15843. if (!symtab_list_[i].valid())
  15844. continue;
  15845. else if (
  15846. local_data(i).vararg_function_store
  15847. .symbol_exists(vararg_function_name)
  15848. )
  15849. return true;
  15850. }
  15851. return false;
  15852. }
  15853. inline bool is_vector(const std::string& vector_name) const
  15854. {
  15855. for (std::size_t i = 0; i < symtab_list_.size(); ++i)
  15856. {
  15857. if (!symtab_list_[i].valid())
  15858. continue;
  15859. else if (
  15860. local_data(i).vector_store
  15861. .symbol_exists(vector_name)
  15862. )
  15863. return true;
  15864. }
  15865. return false;
  15866. }
  15867. inline std::string get_variable_name(const expression_node_ptr& ptr) const
  15868. {
  15869. return local_data().variable_store.entity_name(ptr);
  15870. }
  15871. inline std::string get_vector_name(const vector_holder_ptr& ptr) const
  15872. {
  15873. return local_data().vector_store.entity_name(ptr);
  15874. }
  15875. #ifndef exprtk_disable_string_capabilities
  15876. inline std::string get_stringvar_name(const expression_node_ptr& ptr) const
  15877. {
  15878. return local_data().stringvar_store.entity_name(ptr);
  15879. }
  15880. inline std::string get_conststr_stringvar_name(const expression_node_ptr& ptr) const
  15881. {
  15882. return local_data().stringvar_store.entity_name(ptr);
  15883. }
  15884. #endif
  15885. inline local_data_t& local_data(const std::size_t& index = 0)
  15886. {
  15887. return symtab_list_[index].local_data();
  15888. }
  15889. inline const local_data_t& local_data(const std::size_t& index = 0) const
  15890. {
  15891. return symtab_list_[index].local_data();
  15892. }
  15893. inline symbol_table_t& get_symbol_table(const std::size_t& index = 0)
  15894. {
  15895. return symtab_list_[index];
  15896. }
  15897. };
  15898. struct parser_state
  15899. {
  15900. parser_state()
  15901. : type_check_enabled(true)
  15902. {
  15903. reset();
  15904. }
  15905. void reset()
  15906. {
  15907. parsing_return_stmt = false;
  15908. parsing_break_stmt = false;
  15909. return_stmt_present = false;
  15910. side_effect_present = false;
  15911. scope_depth = 0;
  15912. }
  15913. #ifndef exprtk_enable_debugging
  15914. void activate_side_effect(const std::string&)
  15915. #else
  15916. void activate_side_effect(const std::string& source)
  15917. #endif
  15918. {
  15919. if (!side_effect_present)
  15920. {
  15921. side_effect_present = true;
  15922. exprtk_debug(("activate_side_effect() - caller: %s\n",source.c_str()));
  15923. }
  15924. }
  15925. bool parsing_return_stmt;
  15926. bool parsing_break_stmt;
  15927. bool return_stmt_present;
  15928. bool side_effect_present;
  15929. bool type_check_enabled;
  15930. std::size_t scope_depth;
  15931. };
  15932. public:
  15933. struct unknown_symbol_resolver
  15934. {
  15935. enum usr_symbol_type
  15936. {
  15937. e_usr_unknown_type = 0,
  15938. e_usr_variable_type = 1,
  15939. e_usr_constant_type = 2
  15940. };
  15941. enum usr_mode
  15942. {
  15943. e_usrmode_default = 0,
  15944. e_usrmode_extended = 1
  15945. };
  15946. usr_mode mode;
  15947. unknown_symbol_resolver(const usr_mode m = e_usrmode_default)
  15948. : mode(m)
  15949. {}
  15950. virtual ~unknown_symbol_resolver()
  15951. {}
  15952. virtual bool process(const std::string& /*unknown_symbol*/,
  15953. usr_symbol_type& st,
  15954. T& default_value,
  15955. std::string& error_message)
  15956. {
  15957. if (e_usrmode_default != mode)
  15958. return false;
  15959. st = e_usr_variable_type;
  15960. default_value = T(0);
  15961. error_message.clear();
  15962. return true;
  15963. }
  15964. virtual bool process(const std::string& /* unknown_symbol */,
  15965. symbol_table_t& /* symbol_table */,
  15966. std::string& /* error_message */)
  15967. {
  15968. return false;
  15969. }
  15970. };
  15971. enum collect_type
  15972. {
  15973. e_ct_none = 0,
  15974. e_ct_variables = 1,
  15975. e_ct_functions = 2,
  15976. e_ct_assignments = 4
  15977. };
  15978. enum symbol_type
  15979. {
  15980. e_st_unknown = 0,
  15981. e_st_variable = 1,
  15982. e_st_vector = 2,
  15983. e_st_vecelem = 3,
  15984. e_st_string = 4,
  15985. e_st_function = 5,
  15986. e_st_local_variable = 6,
  15987. e_st_local_vector = 7,
  15988. e_st_local_string = 8
  15989. };
  15990. class dependent_entity_collector
  15991. {
  15992. public:
  15993. typedef std::pair<std::string,symbol_type> symbol_t;
  15994. typedef std::vector<symbol_t> symbol_list_t;
  15995. dependent_entity_collector(const std::size_t options = e_ct_none)
  15996. : options_(options),
  15997. collect_variables_ ((options_ & e_ct_variables ) == e_ct_variables ),
  15998. collect_functions_ ((options_ & e_ct_functions ) == e_ct_functions ),
  15999. collect_assignments_((options_ & e_ct_assignments) == e_ct_assignments),
  16000. return_present_ (false),
  16001. final_stmt_return_(false)
  16002. {}
  16003. template <typename Allocator,
  16004. template <typename, typename> class Sequence>
  16005. inline std::size_t symbols(Sequence<symbol_t,Allocator>& symbols_list)
  16006. {
  16007. if (!collect_variables_ && !collect_functions_)
  16008. return 0;
  16009. else if (symbol_name_list_.empty())
  16010. return 0;
  16011. for (std::size_t i = 0; i < symbol_name_list_.size(); ++i)
  16012. {
  16013. details::case_normalise(symbol_name_list_[i].first);
  16014. }
  16015. std::sort(symbol_name_list_.begin(),symbol_name_list_.end());
  16016. std::unique_copy(symbol_name_list_.begin(),
  16017. symbol_name_list_.end (),
  16018. std::back_inserter(symbols_list));
  16019. return symbols_list.size();
  16020. }
  16021. template <typename Allocator,
  16022. template <typename, typename> class Sequence>
  16023. inline std::size_t assignment_symbols(Sequence<symbol_t,Allocator>& assignment_list)
  16024. {
  16025. if (!collect_assignments_)
  16026. return 0;
  16027. else if (assignment_name_list_.empty())
  16028. return 0;
  16029. for (std::size_t i = 0; i < assignment_name_list_.size(); ++i)
  16030. {
  16031. details::case_normalise(assignment_name_list_[i].first);
  16032. }
  16033. std::sort(assignment_name_list_.begin(),assignment_name_list_.end());
  16034. std::unique_copy(assignment_name_list_.begin(),
  16035. assignment_name_list_.end (),
  16036. std::back_inserter(assignment_list));
  16037. return assignment_list.size();
  16038. }
  16039. void clear()
  16040. {
  16041. symbol_name_list_ .clear();
  16042. assignment_name_list_.clear();
  16043. retparam_list_ .clear();
  16044. return_present_ = false;
  16045. final_stmt_return_ = false;
  16046. }
  16047. bool& collect_variables()
  16048. {
  16049. return collect_variables_;
  16050. }
  16051. bool& collect_functions()
  16052. {
  16053. return collect_functions_;
  16054. }
  16055. bool& collect_assignments()
  16056. {
  16057. return collect_assignments_;
  16058. }
  16059. bool return_present() const
  16060. {
  16061. return return_present_;
  16062. }
  16063. bool final_stmt_return() const
  16064. {
  16065. return final_stmt_return_;
  16066. }
  16067. typedef std::vector<std::string> retparam_list_t;
  16068. retparam_list_t return_param_type_list() const
  16069. {
  16070. return retparam_list_;
  16071. }
  16072. private:
  16073. inline void add_symbol(const std::string& symbol, const symbol_type st)
  16074. {
  16075. switch (st)
  16076. {
  16077. case e_st_variable :
  16078. case e_st_vector :
  16079. case e_st_string :
  16080. case e_st_local_variable :
  16081. case e_st_local_vector :
  16082. case e_st_local_string : if (collect_variables_)
  16083. symbol_name_list_
  16084. .push_back(std::make_pair(symbol, st));
  16085. break;
  16086. case e_st_function : if (collect_functions_)
  16087. symbol_name_list_
  16088. .push_back(std::make_pair(symbol, st));
  16089. break;
  16090. default : return;
  16091. }
  16092. }
  16093. inline void add_assignment(const std::string& symbol, const symbol_type st)
  16094. {
  16095. switch (st)
  16096. {
  16097. case e_st_variable :
  16098. case e_st_vector :
  16099. case e_st_string : if (collect_assignments_)
  16100. assignment_name_list_
  16101. .push_back(std::make_pair(symbol, st));
  16102. break;
  16103. default : return;
  16104. }
  16105. }
  16106. std::size_t options_;
  16107. bool collect_variables_;
  16108. bool collect_functions_;
  16109. bool collect_assignments_;
  16110. bool return_present_;
  16111. bool final_stmt_return_;
  16112. symbol_list_t symbol_name_list_;
  16113. symbol_list_t assignment_name_list_;
  16114. retparam_list_t retparam_list_;
  16115. friend class parser<T>;
  16116. };
  16117. class settings_store
  16118. {
  16119. private:
  16120. typedef std::set<std::string,details::ilesscompare> disabled_entity_set_t;
  16121. typedef disabled_entity_set_t::iterator des_itr_t;
  16122. public:
  16123. enum settings_compilation_options
  16124. {
  16125. e_unknown = 0,
  16126. e_replacer = 1,
  16127. e_joiner = 2,
  16128. e_numeric_check = 4,
  16129. e_bracket_check = 8,
  16130. e_sequence_check = 16,
  16131. e_commutative_check = 32,
  16132. e_strength_reduction = 64,
  16133. e_disable_vardef = 128,
  16134. e_collect_vars = 256,
  16135. e_collect_funcs = 512,
  16136. e_collect_assings = 1024,
  16137. e_disable_usr_on_rsrvd = 2048,
  16138. e_disable_zero_return = 4096
  16139. };
  16140. enum settings_base_funcs
  16141. {
  16142. e_bf_unknown = 0,
  16143. e_bf_abs , e_bf_acos , e_bf_acosh , e_bf_asin ,
  16144. e_bf_asinh , e_bf_atan , e_bf_atan2 , e_bf_atanh ,
  16145. e_bf_avg , e_bf_ceil , e_bf_clamp , e_bf_cos ,
  16146. e_bf_cosh , e_bf_cot , e_bf_csc , e_bf_equal ,
  16147. e_bf_erf , e_bf_erfc , e_bf_exp , e_bf_expm1 ,
  16148. e_bf_floor , e_bf_frac , e_bf_hypot , e_bf_iclamp ,
  16149. e_bf_like , e_bf_log , e_bf_log10 , e_bf_log1p ,
  16150. e_bf_log2 , e_bf_logn , e_bf_mand , e_bf_max ,
  16151. e_bf_min , e_bf_mod , e_bf_mor , e_bf_mul ,
  16152. e_bf_ncdf , e_bf_pow , e_bf_root , e_bf_round ,
  16153. e_bf_roundn , e_bf_sec , e_bf_sgn , e_bf_sin ,
  16154. e_bf_sinc , e_bf_sinh , e_bf_sqrt , e_bf_sum ,
  16155. e_bf_swap , e_bf_tan , e_bf_tanh , e_bf_trunc ,
  16156. e_bf_not_equal , e_bf_inrange , e_bf_deg2grad , e_bf_deg2rad,
  16157. e_bf_rad2deg , e_bf_grad2deg
  16158. };
  16159. enum settings_control_structs
  16160. {
  16161. e_ctrl_unknown = 0,
  16162. e_ctrl_ifelse,
  16163. e_ctrl_switch,
  16164. e_ctrl_for_loop,
  16165. e_ctrl_while_loop,
  16166. e_ctrl_repeat_loop,
  16167. e_ctrl_return
  16168. };
  16169. enum settings_logic_opr
  16170. {
  16171. e_logic_unknown = 0,
  16172. e_logic_and, e_logic_nand, e_logic_nor,
  16173. e_logic_not, e_logic_or, e_logic_xnor,
  16174. e_logic_xor, e_logic_scand, e_logic_scor
  16175. };
  16176. enum settings_arithmetic_opr
  16177. {
  16178. e_arith_unknown = 0,
  16179. e_arith_add, e_arith_sub, e_arith_mul,
  16180. e_arith_div, e_arith_mod, e_arith_pow
  16181. };
  16182. enum settings_assignment_opr
  16183. {
  16184. e_assign_unknown = 0,
  16185. e_assign_assign, e_assign_addass, e_assign_subass,
  16186. e_assign_mulass, e_assign_divass, e_assign_modass
  16187. };
  16188. enum settings_inequality_opr
  16189. {
  16190. e_ineq_unknown = 0,
  16191. e_ineq_lt, e_ineq_lte, e_ineq_eq,
  16192. e_ineq_equal, e_ineq_ne, e_ineq_nequal,
  16193. e_ineq_gte, e_ineq_gt
  16194. };
  16195. static const std::size_t compile_all_opts = e_replacer +
  16196. e_joiner +
  16197. e_numeric_check +
  16198. e_bracket_check +
  16199. e_sequence_check +
  16200. e_commutative_check +
  16201. e_strength_reduction;
  16202. settings_store(const std::size_t compile_options = compile_all_opts)
  16203. {
  16204. load_compile_options(compile_options);
  16205. }
  16206. settings_store& enable_all_base_functions()
  16207. {
  16208. disabled_func_set_.clear();
  16209. return (*this);
  16210. }
  16211. settings_store& enable_all_control_structures()
  16212. {
  16213. disabled_ctrl_set_.clear();
  16214. return (*this);
  16215. }
  16216. settings_store& enable_all_logic_ops()
  16217. {
  16218. disabled_logic_set_.clear();
  16219. return (*this);
  16220. }
  16221. settings_store& enable_all_arithmetic_ops()
  16222. {
  16223. disabled_arithmetic_set_.clear();
  16224. return (*this);
  16225. }
  16226. settings_store& enable_all_assignment_ops()
  16227. {
  16228. disabled_assignment_set_.clear();
  16229. return (*this);
  16230. }
  16231. settings_store& enable_all_inequality_ops()
  16232. {
  16233. disabled_inequality_set_.clear();
  16234. return (*this);
  16235. }
  16236. settings_store& enable_local_vardef()
  16237. {
  16238. disable_vardef_ = false;
  16239. return (*this);
  16240. }
  16241. settings_store& disable_all_base_functions()
  16242. {
  16243. std::copy(details::base_function_list,
  16244. details::base_function_list + details::base_function_list_size,
  16245. std::insert_iterator<disabled_entity_set_t>
  16246. (disabled_func_set_, disabled_func_set_.begin()));
  16247. return (*this);
  16248. }
  16249. settings_store& disable_all_control_structures()
  16250. {
  16251. std::copy(details::cntrl_struct_list,
  16252. details::cntrl_struct_list + details::cntrl_struct_list_size,
  16253. std::insert_iterator<disabled_entity_set_t>
  16254. (disabled_ctrl_set_, disabled_ctrl_set_.begin()));
  16255. return (*this);
  16256. }
  16257. settings_store& disable_all_logic_ops()
  16258. {
  16259. std::copy(details::logic_ops_list,
  16260. details::logic_ops_list + details::logic_ops_list_size,
  16261. std::insert_iterator<disabled_entity_set_t>
  16262. (disabled_logic_set_, disabled_logic_set_.begin()));
  16263. return (*this);
  16264. }
  16265. settings_store& disable_all_arithmetic_ops()
  16266. {
  16267. std::copy(details::arithmetic_ops_list,
  16268. details::arithmetic_ops_list + details::arithmetic_ops_list_size,
  16269. std::insert_iterator<disabled_entity_set_t>
  16270. (disabled_arithmetic_set_, disabled_arithmetic_set_.begin()));
  16271. return (*this);
  16272. }
  16273. settings_store& disable_all_assignment_ops()
  16274. {
  16275. std::copy(details::assignment_ops_list,
  16276. details::assignment_ops_list + details::assignment_ops_list_size,
  16277. std::insert_iterator<disabled_entity_set_t>
  16278. (disabled_assignment_set_, disabled_assignment_set_.begin()));
  16279. return (*this);
  16280. }
  16281. settings_store& disable_all_inequality_ops()
  16282. {
  16283. std::copy(details::inequality_ops_list,
  16284. details::inequality_ops_list + details::inequality_ops_list_size,
  16285. std::insert_iterator<disabled_entity_set_t>
  16286. (disabled_inequality_set_, disabled_inequality_set_.begin()));
  16287. return (*this);
  16288. }
  16289. settings_store& disable_local_vardef()
  16290. {
  16291. disable_vardef_ = true;
  16292. return (*this);
  16293. }
  16294. bool replacer_enabled () const { return enable_replacer_; }
  16295. bool commutative_check_enabled () const { return enable_commutative_check_; }
  16296. bool joiner_enabled () const { return enable_joiner_; }
  16297. bool numeric_check_enabled () const { return enable_numeric_check_; }
  16298. bool bracket_check_enabled () const { return enable_bracket_check_; }
  16299. bool sequence_check_enabled () const { return enable_sequence_check_; }
  16300. bool strength_reduction_enabled () const { return enable_strength_reduction_; }
  16301. bool collect_variables_enabled () const { return enable_collect_vars_; }
  16302. bool collect_functions_enabled () const { return enable_collect_funcs_; }
  16303. bool collect_assignments_enabled() const { return enable_collect_assings_; }
  16304. bool vardef_disabled () const { return disable_vardef_; }
  16305. bool rsrvd_sym_usr_disabled () const { return disable_rsrvd_sym_usr_; }
  16306. bool zero_return_disabled () const { return disable_zero_return_; }
  16307. bool function_enabled(const std::string& function_name) const
  16308. {
  16309. if (disabled_func_set_.empty())
  16310. return true;
  16311. else
  16312. return (disabled_func_set_.end() == disabled_func_set_.find(function_name));
  16313. }
  16314. bool control_struct_enabled(const std::string& control_struct) const
  16315. {
  16316. if (disabled_ctrl_set_.empty())
  16317. return true;
  16318. else
  16319. return (disabled_ctrl_set_.end() == disabled_ctrl_set_.find(control_struct));
  16320. }
  16321. bool logic_enabled(const std::string& logic_operation) const
  16322. {
  16323. if (disabled_logic_set_.empty())
  16324. return true;
  16325. else
  16326. return (disabled_logic_set_.end() == disabled_logic_set_.find(logic_operation));
  16327. }
  16328. bool arithmetic_enabled(const details::operator_type& arithmetic_operation) const
  16329. {
  16330. if (disabled_logic_set_.empty())
  16331. return true;
  16332. else
  16333. return disabled_arithmetic_set_.end() == disabled_arithmetic_set_
  16334. .find(arith_opr_to_string(arithmetic_operation));
  16335. }
  16336. bool assignment_enabled(const details::operator_type& assignment) const
  16337. {
  16338. if (disabled_assignment_set_.empty())
  16339. return true;
  16340. else
  16341. return disabled_assignment_set_.end() == disabled_assignment_set_
  16342. .find(assign_opr_to_string(assignment));
  16343. }
  16344. bool inequality_enabled(const details::operator_type& inequality) const
  16345. {
  16346. if (disabled_inequality_set_.empty())
  16347. return true;
  16348. else
  16349. return disabled_inequality_set_.end() == disabled_inequality_set_
  16350. .find(inequality_opr_to_string(inequality));
  16351. }
  16352. bool function_disabled(const std::string& function_name) const
  16353. {
  16354. if (disabled_func_set_.empty())
  16355. return false;
  16356. else
  16357. return (disabled_func_set_.end() != disabled_func_set_.find(function_name));
  16358. }
  16359. bool control_struct_disabled(const std::string& control_struct) const
  16360. {
  16361. if (disabled_ctrl_set_.empty())
  16362. return false;
  16363. else
  16364. return (disabled_ctrl_set_.end() != disabled_ctrl_set_.find(control_struct));
  16365. }
  16366. bool logic_disabled(const std::string& logic_operation) const
  16367. {
  16368. if (disabled_logic_set_.empty())
  16369. return false;
  16370. else
  16371. return (disabled_logic_set_.end() != disabled_logic_set_.find(logic_operation));
  16372. }
  16373. bool assignment_disabled(const details::operator_type assignment_operation) const
  16374. {
  16375. if (disabled_assignment_set_.empty())
  16376. return false;
  16377. else
  16378. return disabled_assignment_set_.end() != disabled_assignment_set_
  16379. .find(assign_opr_to_string(assignment_operation));
  16380. }
  16381. bool logic_disabled(const details::operator_type logic_operation) const
  16382. {
  16383. if (disabled_logic_set_.empty())
  16384. return false;
  16385. else
  16386. return disabled_logic_set_.end() != disabled_logic_set_
  16387. .find(logic_opr_to_string(logic_operation));
  16388. }
  16389. bool arithmetic_disabled(const details::operator_type arithmetic_operation) const
  16390. {
  16391. if (disabled_arithmetic_set_.empty())
  16392. return false;
  16393. else
  16394. return disabled_arithmetic_set_.end() != disabled_arithmetic_set_
  16395. .find(arith_opr_to_string(arithmetic_operation));
  16396. }
  16397. bool inequality_disabled(const details::operator_type& inequality) const
  16398. {
  16399. if (disabled_inequality_set_.empty())
  16400. return false;
  16401. else
  16402. return disabled_inequality_set_.end() != disabled_inequality_set_
  16403. .find(inequality_opr_to_string(inequality));
  16404. }
  16405. settings_store& disable_base_function(settings_base_funcs bf)
  16406. {
  16407. if (
  16408. (e_bf_unknown != bf) &&
  16409. (static_cast<std::size_t>(bf) < (details::base_function_list_size + 1))
  16410. )
  16411. {
  16412. disabled_func_set_.insert(details::base_function_list[bf - 1]);
  16413. }
  16414. return (*this);
  16415. }
  16416. settings_store& disable_control_structure(settings_control_structs ctrl_struct)
  16417. {
  16418. if (
  16419. (e_ctrl_unknown != ctrl_struct) &&
  16420. (static_cast<std::size_t>(ctrl_struct) < (details::cntrl_struct_list_size + 1))
  16421. )
  16422. {
  16423. disabled_ctrl_set_.insert(details::cntrl_struct_list[ctrl_struct - 1]);
  16424. }
  16425. return (*this);
  16426. }
  16427. settings_store& disable_logic_operation(settings_logic_opr logic)
  16428. {
  16429. if (
  16430. (e_logic_unknown != logic) &&
  16431. (static_cast<std::size_t>(logic) < (details::logic_ops_list_size + 1))
  16432. )
  16433. {
  16434. disabled_logic_set_.insert(details::logic_ops_list[logic - 1]);
  16435. }
  16436. return (*this);
  16437. }
  16438. settings_store& disable_arithmetic_operation(settings_arithmetic_opr arithmetic)
  16439. {
  16440. if (
  16441. (e_arith_unknown != arithmetic) &&
  16442. (static_cast<std::size_t>(arithmetic) < (details::arithmetic_ops_list_size + 1))
  16443. )
  16444. {
  16445. disabled_arithmetic_set_.insert(details::arithmetic_ops_list[arithmetic - 1]);
  16446. }
  16447. return (*this);
  16448. }
  16449. settings_store& disable_assignment_operation(settings_assignment_opr assignment)
  16450. {
  16451. if (
  16452. (e_assign_unknown != assignment) &&
  16453. (static_cast<std::size_t>(assignment) < (details::assignment_ops_list_size + 1))
  16454. )
  16455. {
  16456. disabled_assignment_set_.insert(details::assignment_ops_list[assignment - 1]);
  16457. }
  16458. return (*this);
  16459. }
  16460. settings_store& disable_inequality_operation(settings_inequality_opr inequality)
  16461. {
  16462. if (
  16463. (e_ineq_unknown != inequality) &&
  16464. (static_cast<std::size_t>(inequality) < (details::inequality_ops_list_size + 1))
  16465. )
  16466. {
  16467. disabled_inequality_set_.insert(details::inequality_ops_list[inequality - 1]);
  16468. }
  16469. return (*this);
  16470. }
  16471. settings_store& enable_base_function(settings_base_funcs bf)
  16472. {
  16473. if (
  16474. (e_bf_unknown != bf) &&
  16475. (static_cast<std::size_t>(bf) < (details::base_function_list_size + 1))
  16476. )
  16477. {
  16478. const des_itr_t itr = disabled_func_set_.find(details::base_function_list[bf - 1]);
  16479. if (disabled_func_set_.end() != itr)
  16480. {
  16481. disabled_func_set_.erase(itr);
  16482. }
  16483. }
  16484. return (*this);
  16485. }
  16486. settings_store& enable_control_structure(settings_control_structs ctrl_struct)
  16487. {
  16488. if (
  16489. (e_ctrl_unknown != ctrl_struct) &&
  16490. (static_cast<std::size_t>(ctrl_struct) < (details::cntrl_struct_list_size + 1))
  16491. )
  16492. {
  16493. const des_itr_t itr = disabled_ctrl_set_.find(details::cntrl_struct_list[ctrl_struct - 1]);
  16494. if (disabled_ctrl_set_.end() != itr)
  16495. {
  16496. disabled_ctrl_set_.erase(itr);
  16497. }
  16498. }
  16499. return (*this);
  16500. }
  16501. settings_store& enable_logic_operation(settings_logic_opr logic)
  16502. {
  16503. if (
  16504. (e_logic_unknown != logic) &&
  16505. (static_cast<std::size_t>(logic) < (details::logic_ops_list_size + 1))
  16506. )
  16507. {
  16508. const des_itr_t itr = disabled_logic_set_.find(details::logic_ops_list[logic - 1]);
  16509. if (disabled_logic_set_.end() != itr)
  16510. {
  16511. disabled_logic_set_.erase(itr);
  16512. }
  16513. }
  16514. return (*this);
  16515. }
  16516. settings_store& enable_arithmetic_operation(settings_arithmetic_opr arithmetic)
  16517. {
  16518. if (
  16519. (e_arith_unknown != arithmetic) &&
  16520. (static_cast<std::size_t>(arithmetic) < (details::arithmetic_ops_list_size + 1))
  16521. )
  16522. {
  16523. const des_itr_t itr = disabled_arithmetic_set_.find(details::arithmetic_ops_list[arithmetic - 1]);
  16524. if (disabled_arithmetic_set_.end() != itr)
  16525. {
  16526. disabled_arithmetic_set_.erase(itr);
  16527. }
  16528. }
  16529. return (*this);
  16530. }
  16531. settings_store& enable_assignment_operation(settings_assignment_opr assignment)
  16532. {
  16533. if (
  16534. (e_assign_unknown != assignment) &&
  16535. (static_cast<std::size_t>(assignment) < (details::assignment_ops_list_size + 1))
  16536. )
  16537. {
  16538. const des_itr_t itr = disabled_assignment_set_.find(details::assignment_ops_list[assignment - 1]);
  16539. if (disabled_assignment_set_.end() != itr)
  16540. {
  16541. disabled_assignment_set_.erase(itr);
  16542. }
  16543. }
  16544. return (*this);
  16545. }
  16546. settings_store& enable_inequality_operation(settings_inequality_opr inequality)
  16547. {
  16548. if (
  16549. (e_ineq_unknown != inequality) &&
  16550. (static_cast<std::size_t>(inequality) < (details::inequality_ops_list_size + 1))
  16551. )
  16552. {
  16553. const des_itr_t itr = disabled_inequality_set_.find(details::inequality_ops_list[inequality - 1]);
  16554. if (disabled_inequality_set_.end() != itr)
  16555. {
  16556. disabled_inequality_set_.erase(itr);
  16557. }
  16558. }
  16559. return (*this);
  16560. }
  16561. private:
  16562. void load_compile_options(const std::size_t compile_options)
  16563. {
  16564. enable_replacer_ = (compile_options & e_replacer ) == e_replacer;
  16565. enable_joiner_ = (compile_options & e_joiner ) == e_joiner;
  16566. enable_numeric_check_ = (compile_options & e_numeric_check ) == e_numeric_check;
  16567. enable_bracket_check_ = (compile_options & e_bracket_check ) == e_bracket_check;
  16568. enable_sequence_check_ = (compile_options & e_sequence_check ) == e_sequence_check;
  16569. enable_commutative_check_ = (compile_options & e_commutative_check ) == e_commutative_check;
  16570. enable_strength_reduction_ = (compile_options & e_strength_reduction ) == e_strength_reduction;
  16571. enable_collect_vars_ = (compile_options & e_collect_vars ) == e_collect_vars;
  16572. enable_collect_funcs_ = (compile_options & e_collect_funcs ) == e_collect_funcs;
  16573. enable_collect_assings_ = (compile_options & e_collect_assings ) == e_collect_assings;
  16574. disable_vardef_ = (compile_options & e_disable_vardef ) == e_disable_vardef;
  16575. disable_rsrvd_sym_usr_ = (compile_options & e_disable_usr_on_rsrvd) == e_disable_usr_on_rsrvd;
  16576. disable_zero_return_ = (compile_options & e_disable_zero_return ) == e_disable_zero_return;
  16577. }
  16578. std::string assign_opr_to_string(details::operator_type opr) const
  16579. {
  16580. switch (opr)
  16581. {
  16582. case details::e_assign : return ":=";
  16583. case details::e_addass : return "+=";
  16584. case details::e_subass : return "-=";
  16585. case details::e_mulass : return "*=";
  16586. case details::e_divass : return "/=";
  16587. case details::e_modass : return "%=";
  16588. default : return "";
  16589. }
  16590. }
  16591. std::string arith_opr_to_string(details::operator_type opr) const
  16592. {
  16593. switch (opr)
  16594. {
  16595. case details::e_add : return "+";
  16596. case details::e_sub : return "-";
  16597. case details::e_mul : return "*";
  16598. case details::e_div : return "/";
  16599. case details::e_mod : return "%";
  16600. default : return "";
  16601. }
  16602. }
  16603. std::string inequality_opr_to_string(details::operator_type opr) const
  16604. {
  16605. switch (opr)
  16606. {
  16607. case details::e_lt : return "<";
  16608. case details::e_lte : return "<=";
  16609. case details::e_eq : return "==";
  16610. case details::e_equal : return "=";
  16611. case details::e_ne : return "!=";
  16612. case details::e_nequal: return "<>";
  16613. case details::e_gte : return ">=";
  16614. case details::e_gt : return ">";
  16615. default : return "";
  16616. }
  16617. }
  16618. std::string logic_opr_to_string(details::operator_type opr) const
  16619. {
  16620. switch (opr)
  16621. {
  16622. case details::e_and : return "and" ;
  16623. case details::e_or : return "or" ;
  16624. case details::e_xor : return "xor" ;
  16625. case details::e_nand : return "nand";
  16626. case details::e_nor : return "nor" ;
  16627. case details::e_xnor : return "xnor";
  16628. case details::e_notl : return "not" ;
  16629. default : return "" ;
  16630. }
  16631. }
  16632. bool enable_replacer_;
  16633. bool enable_joiner_;
  16634. bool enable_numeric_check_;
  16635. bool enable_bracket_check_;
  16636. bool enable_sequence_check_;
  16637. bool enable_commutative_check_;
  16638. bool enable_strength_reduction_;
  16639. bool enable_collect_vars_;
  16640. bool enable_collect_funcs_;
  16641. bool enable_collect_assings_;
  16642. bool disable_vardef_;
  16643. bool disable_rsrvd_sym_usr_;
  16644. bool disable_zero_return_;
  16645. disabled_entity_set_t disabled_func_set_ ;
  16646. disabled_entity_set_t disabled_ctrl_set_ ;
  16647. disabled_entity_set_t disabled_logic_set_;
  16648. disabled_entity_set_t disabled_arithmetic_set_;
  16649. disabled_entity_set_t disabled_assignment_set_;
  16650. disabled_entity_set_t disabled_inequality_set_;
  16651. friend class parser<T>;
  16652. };
  16653. typedef settings_store settings_t;
  16654. parser(const settings_t& settings = settings_t())
  16655. : settings_(settings),
  16656. resolve_unknown_symbol_(false),
  16657. results_context_(0),
  16658. unknown_symbol_resolver_(reinterpret_cast<unknown_symbol_resolver*>(0)),
  16659. #ifdef _MSC_VER
  16660. #pragma warning(push)
  16661. #pragma warning (disable:4355)
  16662. #endif
  16663. sem_(*this),
  16664. #ifdef _MSC_VER
  16665. #pragma warning(pop)
  16666. #endif
  16667. operator_joiner_2_(2),
  16668. operator_joiner_3_(3)
  16669. {
  16670. init_precompilation();
  16671. load_operations_map (base_ops_map_ );
  16672. load_unary_operations_map (unary_op_map_ );
  16673. load_binary_operations_map (binary_op_map_ );
  16674. load_inv_binary_operations_map(inv_binary_op_map_);
  16675. load_sf3_map (sf3_map_ );
  16676. load_sf4_map (sf4_map_ );
  16677. expression_generator_.init_synthesize_map();
  16678. expression_generator_.set_parser(*this);
  16679. expression_generator_.set_uom(unary_op_map_);
  16680. expression_generator_.set_bom(binary_op_map_);
  16681. expression_generator_.set_ibom(inv_binary_op_map_);
  16682. expression_generator_.set_sf3m(sf3_map_);
  16683. expression_generator_.set_sf4m(sf4_map_);
  16684. expression_generator_.set_strength_reduction_state(settings_.strength_reduction_enabled());
  16685. }
  16686. ~parser()
  16687. {}
  16688. inline void init_precompilation()
  16689. {
  16690. if (settings_.collect_variables_enabled())
  16691. dec_.collect_variables() = true;
  16692. if (settings_.collect_functions_enabled())
  16693. dec_.collect_functions() = true;
  16694. if (settings_.collect_assignments_enabled())
  16695. dec_.collect_assignments() = true;
  16696. if (settings_.replacer_enabled())
  16697. {
  16698. symbol_replacer_.clear();
  16699. symbol_replacer_.add_replace("true" , "1", lexer::token::e_number);
  16700. symbol_replacer_.add_replace("false", "0", lexer::token::e_number);
  16701. helper_assembly_.token_modifier_list.clear();
  16702. helper_assembly_.register_modifier(&symbol_replacer_);
  16703. }
  16704. if (settings_.commutative_check_enabled())
  16705. {
  16706. for (std::size_t i = 0; i < details::reserved_words_size; ++i)
  16707. {
  16708. commutative_inserter_.ignore_symbol(details::reserved_words[i]);
  16709. }
  16710. helper_assembly_.token_inserter_list.clear();
  16711. helper_assembly_.register_inserter(&commutative_inserter_);
  16712. }
  16713. if (settings_.joiner_enabled())
  16714. {
  16715. helper_assembly_.token_joiner_list.clear();
  16716. helper_assembly_.register_joiner(&operator_joiner_2_);
  16717. helper_assembly_.register_joiner(&operator_joiner_3_);
  16718. }
  16719. if (
  16720. settings_.numeric_check_enabled () ||
  16721. settings_.bracket_check_enabled () ||
  16722. settings_.sequence_check_enabled()
  16723. )
  16724. {
  16725. helper_assembly_.token_scanner_list.clear();
  16726. if (settings_.numeric_check_enabled())
  16727. {
  16728. helper_assembly_.register_scanner(&numeric_checker_);
  16729. }
  16730. if (settings_.bracket_check_enabled())
  16731. {
  16732. helper_assembly_.register_scanner(&bracket_checker_);
  16733. }
  16734. if (settings_.sequence_check_enabled())
  16735. {
  16736. helper_assembly_.register_scanner(&sequence_validator_ );
  16737. helper_assembly_.register_scanner(&sequence_validator_3tkns_);
  16738. }
  16739. }
  16740. }
  16741. inline bool compile(const std::string& expression_string, expression<T>& expr)
  16742. {
  16743. state_ .reset();
  16744. error_list_ .clear();
  16745. brkcnt_list_ .clear();
  16746. synthesis_error_.clear();
  16747. sem_ .cleanup();
  16748. return_cleanup();
  16749. expression_generator_.set_allocator(node_allocator_);
  16750. if (expression_string.empty())
  16751. {
  16752. set_error(
  16753. make_error(parser_error::e_syntax,
  16754. "ERR000 - Empty expression!",
  16755. exprtk_error_location));
  16756. return false;
  16757. }
  16758. if (!init(expression_string))
  16759. {
  16760. process_lexer_errors();
  16761. return false;
  16762. }
  16763. if (lexer().empty())
  16764. {
  16765. set_error(
  16766. make_error(parser_error::e_syntax,
  16767. "ERR001 - Empty expression!",
  16768. exprtk_error_location));
  16769. return false;
  16770. }
  16771. if (!run_assemblies())
  16772. {
  16773. return false;
  16774. }
  16775. symtab_store_.symtab_list_ = expr.get_symbol_table_list();
  16776. dec_.clear();
  16777. lexer().begin();
  16778. next_token();
  16779. expression_node_ptr e = parse_corpus();
  16780. if ((0 != e) && (token_t::e_eof == current_token().type))
  16781. {
  16782. bool* retinvk_ptr = 0;
  16783. if (state_.return_stmt_present)
  16784. {
  16785. dec_.return_present_ = true;
  16786. e = expression_generator_
  16787. .return_envelope(e, results_context_, retinvk_ptr);
  16788. }
  16789. expr.set_expression(e);
  16790. expr.set_retinvk(retinvk_ptr);
  16791. register_local_vars(expr);
  16792. register_return_results(expr);
  16793. return !(!expr);
  16794. }
  16795. else
  16796. {
  16797. if (error_list_.empty())
  16798. {
  16799. set_error(
  16800. make_error(parser_error::e_syntax,
  16801. current_token(),
  16802. "ERR002 - Invalid expression encountered",
  16803. exprtk_error_location));
  16804. }
  16805. if ((0 != e) && branch_deletable(e))
  16806. {
  16807. destroy_node(e);
  16808. }
  16809. dec_.clear ();
  16810. sem_.cleanup ();
  16811. return_cleanup();
  16812. return false;
  16813. }
  16814. }
  16815. inline expression_t compile(const std::string& expression_string, symbol_table_t& symtab)
  16816. {
  16817. expression_t expr;
  16818. expr.register_symbol_table(symtab);
  16819. compile(expression_string,expr);
  16820. return expr;
  16821. }
  16822. void process_lexer_errors()
  16823. {
  16824. for (std::size_t i = 0; i < lexer().size(); ++i)
  16825. {
  16826. if (lexer()[i].is_error())
  16827. {
  16828. std::string diagnostic = "ERR003 - ";
  16829. switch (lexer()[i].type)
  16830. {
  16831. case lexer::token::e_error : diagnostic += "General token error";
  16832. break;
  16833. case lexer::token::e_err_symbol : diagnostic += "Symbol error";
  16834. break;
  16835. case lexer::token::e_err_number : diagnostic += "Invalid numeric token";
  16836. break;
  16837. case lexer::token::e_err_string : diagnostic += "Invalid string token";
  16838. break;
  16839. case lexer::token::e_err_sfunc : diagnostic += "Invalid special function token";
  16840. break;
  16841. default : diagnostic += "Unknown compiler error";
  16842. }
  16843. set_error(
  16844. make_error(parser_error::e_lexer,
  16845. lexer()[i],
  16846. diagnostic + ": " + lexer()[i].value,
  16847. exprtk_error_location));
  16848. }
  16849. }
  16850. }
  16851. inline bool run_assemblies()
  16852. {
  16853. if (settings_.commutative_check_enabled())
  16854. {
  16855. helper_assembly_.run_inserters(lexer());
  16856. }
  16857. if (settings_.joiner_enabled())
  16858. {
  16859. helper_assembly_.run_joiners(lexer());
  16860. }
  16861. if (settings_.replacer_enabled())
  16862. {
  16863. helper_assembly_.run_modifiers(lexer());
  16864. }
  16865. if (
  16866. settings_.numeric_check_enabled () ||
  16867. settings_.bracket_check_enabled () ||
  16868. settings_.sequence_check_enabled()
  16869. )
  16870. {
  16871. if (!helper_assembly_.run_scanners(lexer()))
  16872. {
  16873. if (helper_assembly_.error_token_scanner)
  16874. {
  16875. lexer::helper::bracket_checker* bracket_checker_ptr = 0;
  16876. lexer::helper::numeric_checker* numeric_checker_ptr = 0;
  16877. lexer::helper::sequence_validator* sequence_validator_ptr = 0;
  16878. lexer::helper::sequence_validator_3tokens* sequence_validator3_ptr = 0;
  16879. if (0 != (bracket_checker_ptr = dynamic_cast<lexer::helper::bracket_checker*>(helper_assembly_.error_token_scanner)))
  16880. {
  16881. set_error(
  16882. make_error(parser_error::e_token,
  16883. bracket_checker_ptr->error_token(),
  16884. "ERR004 - Mismatched brackets: '" + bracket_checker_ptr->error_token().value + "'",
  16885. exprtk_error_location));
  16886. }
  16887. else if (0 != (numeric_checker_ptr = dynamic_cast<lexer::helper::numeric_checker*>(helper_assembly_.error_token_scanner)))
  16888. {
  16889. for (std::size_t i = 0; i < numeric_checker_ptr->error_count(); ++i)
  16890. {
  16891. lexer::token error_token = lexer()[numeric_checker_ptr->error_index(i)];
  16892. set_error(
  16893. make_error(parser_error::e_token,
  16894. error_token,
  16895. "ERR005 - Invalid numeric token: '" + error_token.value + "'",
  16896. exprtk_error_location));
  16897. }
  16898. if (numeric_checker_ptr->error_count())
  16899. {
  16900. numeric_checker_ptr->clear_errors();
  16901. }
  16902. }
  16903. else if (0 != (sequence_validator_ptr = dynamic_cast<lexer::helper::sequence_validator*>(helper_assembly_.error_token_scanner)))
  16904. {
  16905. for (std::size_t i = 0; i < sequence_validator_ptr->error_count(); ++i)
  16906. {
  16907. std::pair<lexer::token,lexer::token> error_token = sequence_validator_ptr->error(i);
  16908. set_error(
  16909. make_error(parser_error::e_token,
  16910. error_token.first,
  16911. "ERR006 - Invalid token sequence: '" +
  16912. error_token.first.value + "' and '" +
  16913. error_token.second.value + "'",
  16914. exprtk_error_location));
  16915. }
  16916. if (sequence_validator_ptr->error_count())
  16917. {
  16918. sequence_validator_ptr->clear_errors();
  16919. }
  16920. }
  16921. else if (0 != (sequence_validator3_ptr = dynamic_cast<lexer::helper::sequence_validator_3tokens*>(helper_assembly_.error_token_scanner)))
  16922. {
  16923. for (std::size_t i = 0; i < sequence_validator3_ptr->error_count(); ++i)
  16924. {
  16925. std::pair<lexer::token,lexer::token> error_token = sequence_validator3_ptr->error(i);
  16926. set_error(
  16927. make_error(parser_error::e_token,
  16928. error_token.first,
  16929. "ERR007 - Invalid token sequence: '" +
  16930. error_token.first.value + "' and '" +
  16931. error_token.second.value + "'",
  16932. exprtk_error_location));
  16933. }
  16934. if (sequence_validator3_ptr->error_count())
  16935. {
  16936. sequence_validator3_ptr->clear_errors();
  16937. }
  16938. }
  16939. }
  16940. return false;
  16941. }
  16942. }
  16943. return true;
  16944. }
  16945. inline settings_store& settings()
  16946. {
  16947. return settings_;
  16948. }
  16949. inline parser_error::type get_error(const std::size_t& index) const
  16950. {
  16951. if (index < error_list_.size())
  16952. return error_list_[index];
  16953. else
  16954. throw std::invalid_argument("parser::get_error() - Invalid error index specificed");
  16955. }
  16956. inline std::string error() const
  16957. {
  16958. if (!error_list_.empty())
  16959. {
  16960. return error_list_[0].diagnostic;
  16961. }
  16962. else
  16963. return std::string("No Error");
  16964. }
  16965. inline std::size_t error_count() const
  16966. {
  16967. return error_list_.size();
  16968. }
  16969. inline dependent_entity_collector& dec()
  16970. {
  16971. return dec_;
  16972. }
  16973. inline bool replace_symbol(const std::string& old_symbol, const std::string& new_symbol)
  16974. {
  16975. if (!settings_.replacer_enabled())
  16976. return false;
  16977. else if (details::is_reserved_word(old_symbol))
  16978. return false;
  16979. else
  16980. return symbol_replacer_.add_replace(old_symbol,new_symbol,lexer::token::e_symbol);
  16981. }
  16982. inline bool remove_replace_symbol(const std::string& symbol)
  16983. {
  16984. if (!settings_.replacer_enabled())
  16985. return false;
  16986. else if (details::is_reserved_word(symbol))
  16987. return false;
  16988. else
  16989. return symbol_replacer_.remove(symbol);
  16990. }
  16991. inline void enable_unknown_symbol_resolver(unknown_symbol_resolver* usr = reinterpret_cast<unknown_symbol_resolver*>(0))
  16992. {
  16993. resolve_unknown_symbol_ = true;
  16994. if (usr)
  16995. unknown_symbol_resolver_ = usr;
  16996. else
  16997. unknown_symbol_resolver_ = &default_usr_;
  16998. }
  16999. inline void enable_unknown_symbol_resolver(unknown_symbol_resolver& usr)
  17000. {
  17001. enable_unknown_symbol_resolver(&usr);
  17002. }
  17003. inline void disable_unknown_symbol_resolver()
  17004. {
  17005. resolve_unknown_symbol_ = false;
  17006. unknown_symbol_resolver_ = &default_usr_;
  17007. }
  17008. private:
  17009. inline bool valid_base_operation(const std::string& symbol) const
  17010. {
  17011. const std::size_t length = symbol.size();
  17012. if (
  17013. (length < 3) || // Shortest base op symbol length
  17014. (length > 9) // Longest base op symbol length
  17015. )
  17016. return false;
  17017. else
  17018. return settings_.function_enabled(symbol) &&
  17019. (base_ops_map_.end() != base_ops_map_.find(symbol));
  17020. }
  17021. inline bool valid_vararg_operation(const std::string& symbol) const
  17022. {
  17023. static const std::string s_sum = "sum" ;
  17024. static const std::string s_mul = "mul" ;
  17025. static const std::string s_avg = "avg" ;
  17026. static const std::string s_min = "min" ;
  17027. static const std::string s_max = "max" ;
  17028. static const std::string s_mand = "mand";
  17029. static const std::string s_mor = "mor" ;
  17030. static const std::string s_multi = "~" ;
  17031. static const std::string s_mswitch = "[*]" ;
  17032. return
  17033. (
  17034. details::imatch(symbol,s_sum ) ||
  17035. details::imatch(symbol,s_mul ) ||
  17036. details::imatch(symbol,s_avg ) ||
  17037. details::imatch(symbol,s_min ) ||
  17038. details::imatch(symbol,s_max ) ||
  17039. details::imatch(symbol,s_mand ) ||
  17040. details::imatch(symbol,s_mor ) ||
  17041. details::imatch(symbol,s_multi ) ||
  17042. details::imatch(symbol,s_mswitch)
  17043. ) &&
  17044. settings_.function_enabled(symbol);
  17045. }
  17046. bool is_invalid_logic_operation(const details::operator_type operation) const
  17047. {
  17048. return settings_.logic_disabled(operation);
  17049. }
  17050. bool is_invalid_arithmetic_operation(const details::operator_type operation) const
  17051. {
  17052. return settings_.arithmetic_disabled(operation);
  17053. }
  17054. bool is_invalid_assignment_operation(const details::operator_type operation) const
  17055. {
  17056. return settings_.assignment_disabled(operation);
  17057. }
  17058. bool is_invalid_inequality_operation(const details::operator_type operation) const
  17059. {
  17060. return settings_.inequality_disabled(operation);
  17061. }
  17062. #ifdef exprtk_enable_debugging
  17063. inline void next_token()
  17064. {
  17065. const std::string ct_str = current_token().value;
  17066. parser_helper::next_token();
  17067. const std::string depth(2 * state_.scope_depth,' ');
  17068. exprtk_debug(("%s"
  17069. "prev[%s] --> curr[%s]\n",
  17070. depth.c_str(),
  17071. ct_str.c_str(),
  17072. current_token().value.c_str()));
  17073. }
  17074. #endif
  17075. inline expression_node_ptr parse_corpus()
  17076. {
  17077. std::vector<expression_node_ptr> arg_list;
  17078. std::vector<bool> side_effect_list;
  17079. scoped_vec_delete<expression_node_t> sdd((*this),arg_list);
  17080. lexer::token begin_token;
  17081. lexer::token end_token;
  17082. for ( ; ; )
  17083. {
  17084. state_.side_effect_present = false;
  17085. begin_token = current_token();
  17086. expression_node_ptr arg = parse_expression();
  17087. if (0 == arg)
  17088. {
  17089. if (error_list_.empty())
  17090. {
  17091. set_error(
  17092. make_error(parser_error::e_syntax,
  17093. current_token(),
  17094. "ERR008 - Invalid expression encountered",
  17095. exprtk_error_location));
  17096. }
  17097. return error_node();
  17098. }
  17099. else
  17100. {
  17101. arg_list.push_back(arg);
  17102. side_effect_list.push_back(state_.side_effect_present);
  17103. end_token = current_token();
  17104. const std::string sub_expr = construct_subexpr(begin_token, end_token);
  17105. exprtk_debug(("parse_corpus(%02d) Subexpr: %s\n",
  17106. static_cast<int>(arg_list.size() - 1),
  17107. sub_expr.c_str()));
  17108. exprtk_debug(("parse_corpus(%02d) - Side effect present: %s\n",
  17109. static_cast<int>(arg_list.size() - 1),
  17110. state_.side_effect_present ? "true" : "false"));
  17111. exprtk_debug(("-------------------------------------------------\n"));
  17112. }
  17113. if (lexer().finished())
  17114. break;
  17115. else if (token_is(token_t::e_eof,prsrhlpr_t::e_hold))
  17116. {
  17117. if (lexer().finished())
  17118. break;
  17119. else
  17120. next_token();
  17121. }
  17122. }
  17123. if (
  17124. !arg_list.empty() &&
  17125. is_return_node(arg_list.back())
  17126. )
  17127. {
  17128. dec_.final_stmt_return_ = true;
  17129. }
  17130. const expression_node_ptr result = simplify(arg_list,side_effect_list);
  17131. sdd.delete_ptr = (0 == result);
  17132. return result;
  17133. }
  17134. std::string construct_subexpr(lexer::token& begin_token, lexer::token& end_token)
  17135. {
  17136. std::string result = lexer().substr(begin_token.position,end_token.position);
  17137. for (std::size_t i = 0; i < result.size(); ++i)
  17138. {
  17139. if (details::is_whitespace(result[i])) result[i] = ' ';
  17140. }
  17141. return result;
  17142. }
  17143. static const precedence_level default_precedence = e_level00;
  17144. struct state_t
  17145. {
  17146. inline void set(const precedence_level& l,
  17147. const precedence_level& r,
  17148. const details::operator_type& o)
  17149. {
  17150. left = l;
  17151. right = r;
  17152. operation = o;
  17153. }
  17154. inline void reset()
  17155. {
  17156. left = e_level00;
  17157. right = e_level00;
  17158. operation = details::e_default;
  17159. }
  17160. precedence_level left;
  17161. precedence_level right;
  17162. details::operator_type operation;
  17163. };
  17164. inline expression_node_ptr parse_expression(precedence_level precedence = e_level00)
  17165. {
  17166. expression_node_ptr expression = parse_branch(precedence);
  17167. if (0 == expression)
  17168. {
  17169. return error_node();
  17170. }
  17171. bool break_loop = false;
  17172. state_t current_state;
  17173. for ( ; ; )
  17174. {
  17175. current_state.reset();
  17176. switch (current_token().type)
  17177. {
  17178. case token_t::e_assign : current_state.set(e_level00,e_level00, details::e_assign); break;
  17179. case token_t::e_addass : current_state.set(e_level00,e_level00, details::e_addass); break;
  17180. case token_t::e_subass : current_state.set(e_level00,e_level00, details::e_subass); break;
  17181. case token_t::e_mulass : current_state.set(e_level00,e_level00, details::e_mulass); break;
  17182. case token_t::e_divass : current_state.set(e_level00,e_level00, details::e_divass); break;
  17183. case token_t::e_modass : current_state.set(e_level00,e_level00, details::e_modass); break;
  17184. case token_t::e_swap : current_state.set(e_level00,e_level00, details::e_swap ); break;
  17185. case token_t::e_lt : current_state.set(e_level05,e_level06, details:: e_lt); break;
  17186. case token_t::e_lte : current_state.set(e_level05,e_level06, details:: e_lte); break;
  17187. case token_t::e_eq : current_state.set(e_level05,e_level06, details:: e_eq); break;
  17188. case token_t::e_ne : current_state.set(e_level05,e_level06, details:: e_ne); break;
  17189. case token_t::e_gte : current_state.set(e_level05,e_level06, details:: e_gte); break;
  17190. case token_t::e_gt : current_state.set(e_level05,e_level06, details:: e_gt); break;
  17191. case token_t::e_add : current_state.set(e_level07,e_level08, details:: e_add); break;
  17192. case token_t::e_sub : current_state.set(e_level07,e_level08, details:: e_sub); break;
  17193. case token_t::e_div : current_state.set(e_level10,e_level11, details:: e_div); break;
  17194. case token_t::e_mul : current_state.set(e_level10,e_level11, details:: e_mul); break;
  17195. case token_t::e_mod : current_state.set(e_level10,e_level11, details:: e_mod); break;
  17196. case token_t::e_pow : current_state.set(e_level12,e_level12, details:: e_pow); break;
  17197. default : if (token_t::e_symbol == current_token().type)
  17198. {
  17199. static const std::string s_and = "and";
  17200. static const std::string s_nand = "nand";
  17201. static const std::string s_or = "or";
  17202. static const std::string s_nor = "nor";
  17203. static const std::string s_xor = "xor";
  17204. static const std::string s_xnor = "xnor";
  17205. static const std::string s_in = "in";
  17206. static const std::string s_like = "like";
  17207. static const std::string s_ilike = "ilike";
  17208. static const std::string s_and1 = "&";
  17209. static const std::string s_or1 = "|";
  17210. static const std::string s_not = "not";
  17211. if (details::imatch(current_token().value,s_and))
  17212. {
  17213. current_state.set(e_level03, e_level04, details::e_and);
  17214. break;
  17215. }
  17216. else if (details::imatch(current_token().value,s_and1))
  17217. {
  17218. #ifndef exprtk_disable_sc_andor
  17219. current_state.set(e_level03, e_level04, details::e_scand);
  17220. #else
  17221. current_state.set(e_level03, e_level04, details::e_and);
  17222. #endif
  17223. break;
  17224. }
  17225. else if (details::imatch(current_token().value,s_nand))
  17226. {
  17227. current_state.set(e_level03, e_level04, details::e_nand);
  17228. break;
  17229. }
  17230. else if (details::imatch(current_token().value,s_or))
  17231. {
  17232. current_state.set(e_level01, e_level02, details::e_or);
  17233. break;
  17234. }
  17235. else if (details::imatch(current_token().value,s_or1))
  17236. {
  17237. #ifndef exprtk_disable_sc_andor
  17238. current_state.set(e_level01, e_level02, details::e_scor);
  17239. #else
  17240. current_state.set(e_level01, e_level02, details::e_or);
  17241. #endif
  17242. break;
  17243. }
  17244. else if (details::imatch(current_token().value,s_nor))
  17245. {
  17246. current_state.set(e_level01, e_level02, details::e_nor);
  17247. break;
  17248. }
  17249. else if (details::imatch(current_token().value,s_xor))
  17250. {
  17251. current_state.set(e_level01, e_level02, details::e_xor);
  17252. break;
  17253. }
  17254. else if (details::imatch(current_token().value,s_xnor))
  17255. {
  17256. current_state.set(e_level01, e_level02, details::e_xnor);
  17257. break;
  17258. }
  17259. else if (details::imatch(current_token().value,s_in))
  17260. {
  17261. current_state.set(e_level04, e_level04, details::e_in);
  17262. break;
  17263. }
  17264. else if (details::imatch(current_token().value,s_like))
  17265. {
  17266. current_state.set(e_level04, e_level04, details::e_like);
  17267. break;
  17268. }
  17269. else if (details::imatch(current_token().value,s_ilike))
  17270. {
  17271. current_state.set(e_level04, e_level04, details::e_ilike);
  17272. break;
  17273. }
  17274. else if (details::imatch(current_token().value,s_not))
  17275. {
  17276. break;
  17277. }
  17278. }
  17279. break_loop = true;
  17280. }
  17281. if (break_loop)
  17282. {
  17283. parse_pending_string_rangesize(expression);
  17284. break;
  17285. }
  17286. else if (current_state.left < precedence)
  17287. break;
  17288. const lexer::token prev_token = current_token();
  17289. next_token();
  17290. expression_node_ptr right_branch = error_node();
  17291. expression_node_ptr new_expression = error_node();
  17292. if (is_invalid_logic_operation(current_state.operation))
  17293. {
  17294. free_node(node_allocator_,expression);
  17295. set_error(
  17296. make_error(parser_error::e_syntax,
  17297. prev_token,
  17298. "ERR009 - Invalid or disabled logic operation '" + details::to_str(current_state.operation) + "'",
  17299. exprtk_error_location));
  17300. return error_node();
  17301. }
  17302. else if (is_invalid_arithmetic_operation(current_state.operation))
  17303. {
  17304. free_node(node_allocator_,expression);
  17305. set_error(
  17306. make_error(parser_error::e_syntax,
  17307. prev_token,
  17308. "ERR010 - Invalid or disabled arithmetic operation '" + details::to_str(current_state.operation) + "'",
  17309. exprtk_error_location));
  17310. return error_node();
  17311. }
  17312. else if (is_invalid_inequality_operation(current_state.operation))
  17313. {
  17314. free_node(node_allocator_,expression);
  17315. set_error(
  17316. make_error(parser_error::e_syntax,
  17317. prev_token,
  17318. "ERR011 - Invalid inequality operation '" + details::to_str(current_state.operation) + "'",
  17319. exprtk_error_location));
  17320. return error_node();
  17321. }
  17322. else if (is_invalid_assignment_operation(current_state.operation))
  17323. {
  17324. free_node(node_allocator_,expression);
  17325. set_error(
  17326. make_error(parser_error::e_syntax,
  17327. prev_token,
  17328. "ERR012 - Invalid or disabled assignment operation '" + details::to_str(current_state.operation) + "'",
  17329. exprtk_error_location));
  17330. return error_node();
  17331. }
  17332. if (0 != (right_branch = parse_expression(current_state.right)))
  17333. {
  17334. if (
  17335. details::is_return_node( expression) ||
  17336. details::is_return_node(right_branch)
  17337. )
  17338. {
  17339. free_node(node_allocator_, expression);
  17340. free_node(node_allocator_, right_branch);
  17341. set_error(
  17342. make_error(parser_error::e_syntax,
  17343. prev_token,
  17344. "ERR013 - Return statements cannot be part of sub-expressions",
  17345. exprtk_error_location));
  17346. return error_node();
  17347. }
  17348. new_expression = expression_generator_
  17349. (
  17350. current_state.operation,
  17351. expression,
  17352. right_branch
  17353. );
  17354. }
  17355. if (0 == new_expression)
  17356. {
  17357. if (error_list_.empty())
  17358. {
  17359. set_error(
  17360. make_error(parser_error::e_syntax,
  17361. prev_token,
  17362. !synthesis_error_.empty() ?
  17363. synthesis_error_ :
  17364. "ERR014 - General parsing error at token: '" + prev_token.value + "'",
  17365. exprtk_error_location));
  17366. }
  17367. free_node(node_allocator_, expression);
  17368. free_node(node_allocator_, right_branch);
  17369. return error_node();
  17370. }
  17371. else
  17372. {
  17373. if (
  17374. token_is(token_t::e_ternary,prsrhlpr_t::e_hold) &&
  17375. (precedence == e_level00)
  17376. )
  17377. {
  17378. expression = parse_ternary_conditional_statement(new_expression);
  17379. }
  17380. else
  17381. expression = new_expression;
  17382. parse_pending_string_rangesize(expression);
  17383. }
  17384. }
  17385. return expression;
  17386. }
  17387. bool simplify_unary_negation_branch(expression_node_ptr& node)
  17388. {
  17389. {
  17390. typedef details::unary_branch_node<T,details::neg_op<T> > ubn_t;
  17391. ubn_t* n = dynamic_cast<ubn_t*>(node);
  17392. if (n)
  17393. {
  17394. expression_node_ptr un_r = n->branch(0);
  17395. n->release();
  17396. free_node(node_allocator_,node);
  17397. node = un_r;
  17398. return true;
  17399. }
  17400. }
  17401. {
  17402. typedef details::unary_variable_node<T,details::neg_op<T> > uvn_t;
  17403. uvn_t* n = dynamic_cast<uvn_t*>(node);
  17404. if (n)
  17405. {
  17406. const T& v = n->v();
  17407. expression_node_ptr return_node = error_node();
  17408. if (
  17409. (0 != (return_node = symtab_store_.get_variable(v))) ||
  17410. (0 != (return_node = sem_ .get_variable(v)))
  17411. )
  17412. {
  17413. free_node(node_allocator_,node);
  17414. node = return_node;
  17415. return true;
  17416. }
  17417. else
  17418. {
  17419. set_error(
  17420. make_error(parser_error::e_syntax,
  17421. current_token(),
  17422. "ERR015 - Failed to find variable node in symbol table",
  17423. exprtk_error_location));
  17424. free_node(node_allocator_,node);
  17425. return false;
  17426. }
  17427. }
  17428. }
  17429. return false;
  17430. }
  17431. static inline expression_node_ptr error_node()
  17432. {
  17433. return reinterpret_cast<expression_node_ptr>(0);
  17434. }
  17435. template <typename Type, std::size_t N>
  17436. struct scoped_delete
  17437. {
  17438. typedef Type* ptr_t;
  17439. scoped_delete(parser<T>& pr, ptr_t& p)
  17440. : delete_ptr(true),
  17441. parser_(pr),
  17442. p_(&p)
  17443. {}
  17444. scoped_delete(parser<T>& pr, ptr_t (&p)[N])
  17445. : delete_ptr(true),
  17446. parser_(pr),
  17447. p_(&p[0])
  17448. {}
  17449. ~scoped_delete()
  17450. {
  17451. if (delete_ptr)
  17452. {
  17453. for (std::size_t i = 0; i < N; ++i)
  17454. {
  17455. free_node(parser_.node_allocator_,p_[i]);
  17456. }
  17457. }
  17458. }
  17459. bool delete_ptr;
  17460. parser<T>& parser_;
  17461. ptr_t* p_;
  17462. private:
  17463. scoped_delete<Type,N>& operator=(const scoped_delete<Type,N>&);
  17464. };
  17465. template <typename Type>
  17466. struct scoped_deq_delete
  17467. {
  17468. typedef Type* ptr_t;
  17469. scoped_deq_delete(parser<T>& pr, std::deque<ptr_t>& deq)
  17470. : delete_ptr(true),
  17471. parser_(pr),
  17472. deq_(deq)
  17473. {}
  17474. ~scoped_deq_delete()
  17475. {
  17476. if (delete_ptr && !deq_.empty())
  17477. {
  17478. for (std::size_t i = 0; i < deq_.size(); ++i)
  17479. {
  17480. free_node(parser_.node_allocator_,deq_[i]);
  17481. }
  17482. deq_.clear();
  17483. }
  17484. }
  17485. bool delete_ptr;
  17486. parser<T>& parser_;
  17487. std::deque<ptr_t>& deq_;
  17488. private:
  17489. scoped_deq_delete<Type>& operator=(const scoped_deq_delete<Type>&);
  17490. };
  17491. template <typename Type>
  17492. struct scoped_vec_delete
  17493. {
  17494. typedef Type* ptr_t;
  17495. scoped_vec_delete(parser<T>& pr, std::vector<ptr_t>& vec)
  17496. : delete_ptr(true),
  17497. parser_(pr),
  17498. vec_(vec)
  17499. {}
  17500. ~scoped_vec_delete()
  17501. {
  17502. if (delete_ptr && !vec_.empty())
  17503. {
  17504. for (std::size_t i = 0; i < vec_.size(); ++i)
  17505. {
  17506. free_node(parser_.node_allocator_,vec_[i]);
  17507. }
  17508. vec_.clear();
  17509. }
  17510. }
  17511. bool delete_ptr;
  17512. parser<T>& parser_;
  17513. std::vector<ptr_t>& vec_;
  17514. private:
  17515. scoped_vec_delete<Type>& operator=(const scoped_vec_delete<Type>&);
  17516. };
  17517. struct scoped_bool_negator
  17518. {
  17519. explicit scoped_bool_negator(bool& bb)
  17520. : b(bb)
  17521. { b = !b; }
  17522. ~scoped_bool_negator()
  17523. { b = !b; }
  17524. bool& b;
  17525. };
  17526. struct scoped_bool_or_restorer
  17527. {
  17528. explicit scoped_bool_or_restorer(bool& bb)
  17529. : b(bb),
  17530. original_value_(bb)
  17531. {}
  17532. ~scoped_bool_or_restorer()
  17533. {
  17534. b = b || original_value_;
  17535. }
  17536. bool& b;
  17537. bool original_value_;
  17538. };
  17539. inline expression_node_ptr parse_function_invocation(ifunction<T>* function, const std::string& function_name)
  17540. {
  17541. expression_node_ptr func_node = reinterpret_cast<expression_node_ptr>(0);
  17542. switch (function->param_count)
  17543. {
  17544. case 0 : func_node = parse_function_call_0 (function,function_name); break;
  17545. case 1 : func_node = parse_function_call< 1>(function,function_name); break;
  17546. case 2 : func_node = parse_function_call< 2>(function,function_name); break;
  17547. case 3 : func_node = parse_function_call< 3>(function,function_name); break;
  17548. case 4 : func_node = parse_function_call< 4>(function,function_name); break;
  17549. case 5 : func_node = parse_function_call< 5>(function,function_name); break;
  17550. case 6 : func_node = parse_function_call< 6>(function,function_name); break;
  17551. case 7 : func_node = parse_function_call< 7>(function,function_name); break;
  17552. case 8 : func_node = parse_function_call< 8>(function,function_name); break;
  17553. case 9 : func_node = parse_function_call< 9>(function,function_name); break;
  17554. case 10 : func_node = parse_function_call<10>(function,function_name); break;
  17555. case 11 : func_node = parse_function_call<11>(function,function_name); break;
  17556. case 12 : func_node = parse_function_call<12>(function,function_name); break;
  17557. case 13 : func_node = parse_function_call<13>(function,function_name); break;
  17558. case 14 : func_node = parse_function_call<14>(function,function_name); break;
  17559. case 15 : func_node = parse_function_call<15>(function,function_name); break;
  17560. case 16 : func_node = parse_function_call<16>(function,function_name); break;
  17561. case 17 : func_node = parse_function_call<17>(function,function_name); break;
  17562. case 18 : func_node = parse_function_call<18>(function,function_name); break;
  17563. case 19 : func_node = parse_function_call<19>(function,function_name); break;
  17564. case 20 : func_node = parse_function_call<20>(function,function_name); break;
  17565. default : {
  17566. set_error(
  17567. make_error(parser_error::e_syntax,
  17568. current_token(),
  17569. "ERR016 - Invalid number of parameters for function: '" + function_name + "'",
  17570. exprtk_error_location));
  17571. return error_node();
  17572. }
  17573. }
  17574. if (func_node)
  17575. return func_node;
  17576. else
  17577. {
  17578. set_error(
  17579. make_error(parser_error::e_syntax,
  17580. current_token(),
  17581. "ERR017 - Failed to generate call to function: '" + function_name + "'",
  17582. exprtk_error_location));
  17583. return error_node();
  17584. }
  17585. }
  17586. template <std::size_t NumberofParameters>
  17587. inline expression_node_ptr parse_function_call(ifunction<T>* function, const std::string& function_name)
  17588. {
  17589. #ifdef _MSC_VER
  17590. #pragma warning(push)
  17591. #pragma warning(disable: 4127)
  17592. #endif
  17593. if (0 == NumberofParameters)
  17594. {
  17595. set_error(
  17596. make_error(parser_error::e_syntax,
  17597. current_token(),
  17598. "ERR018 - Expecting ifunction '" + function_name + "' to have non-zero parameter count",
  17599. exprtk_error_location));
  17600. return error_node();
  17601. }
  17602. #ifdef _MSC_VER
  17603. #pragma warning(pop)
  17604. #endif
  17605. expression_node_ptr branch[NumberofParameters];
  17606. expression_node_ptr result = error_node();
  17607. std::fill_n(branch, NumberofParameters, reinterpret_cast<expression_node_ptr>(0));
  17608. scoped_delete<expression_node_t,NumberofParameters> sd((*this),branch);
  17609. next_token();
  17610. if (!token_is(token_t::e_lbracket))
  17611. {
  17612. set_error(
  17613. make_error(parser_error::e_syntax,
  17614. current_token(),
  17615. "ERR019 - Expecting argument list for function: '" + function_name + "'",
  17616. exprtk_error_location));
  17617. return error_node();
  17618. }
  17619. for (int i = 0; i < static_cast<int>(NumberofParameters); ++i)
  17620. {
  17621. branch[i] = parse_expression();
  17622. if (0 == branch[i])
  17623. {
  17624. set_error(
  17625. make_error(parser_error::e_syntax,
  17626. current_token(),
  17627. "ERR020 - Failed to parse argument " + details::to_str(i) + " for function: '" + function_name + "'",
  17628. exprtk_error_location));
  17629. return error_node();
  17630. }
  17631. else if (i < static_cast<int>(NumberofParameters - 1))
  17632. {
  17633. if (!token_is(token_t::e_comma))
  17634. {
  17635. set_error(
  17636. make_error(parser_error::e_syntax,
  17637. current_token(),
  17638. "ERR021 - Invalid number of arguments for function: '" + function_name + "'",
  17639. exprtk_error_location));
  17640. return error_node();
  17641. }
  17642. }
  17643. }
  17644. if (!token_is(token_t::e_rbracket))
  17645. {
  17646. set_error(
  17647. make_error(parser_error::e_syntax,
  17648. current_token(),
  17649. "ERR022 - Invalid number of arguments for function: '" + function_name + "'",
  17650. exprtk_error_location));
  17651. return error_node();
  17652. }
  17653. else
  17654. result = expression_generator_.function(function,branch);
  17655. sd.delete_ptr = false;
  17656. return result;
  17657. }
  17658. inline expression_node_ptr parse_function_call_0(ifunction<T>* function, const std::string& function_name)
  17659. {
  17660. expression_node_ptr result = expression_generator_.function(function);
  17661. state_.side_effect_present = function->has_side_effects();
  17662. next_token();
  17663. if (
  17664. token_is(token_t::e_lbracket) &&
  17665. !token_is(token_t::e_rbracket)
  17666. )
  17667. {
  17668. set_error(
  17669. make_error(parser_error::e_syntax,
  17670. current_token(),
  17671. "ERR023 - Expecting '()' to proceed call to function: '" + function_name + "'",
  17672. exprtk_error_location));
  17673. free_node(node_allocator_,result);
  17674. return error_node();
  17675. }
  17676. else
  17677. return result;
  17678. }
  17679. template <std::size_t MaxNumberofParameters>
  17680. inline std::size_t parse_base_function_call(expression_node_ptr (&param_list)[MaxNumberofParameters], const std::string& function_name = "")
  17681. {
  17682. std::fill_n(param_list, MaxNumberofParameters, reinterpret_cast<expression_node_ptr>(0));
  17683. scoped_delete<expression_node_t,MaxNumberofParameters> sd((*this),param_list);
  17684. next_token();
  17685. if (!token_is(token_t::e_lbracket))
  17686. {
  17687. set_error(
  17688. make_error(parser_error::e_syntax,
  17689. current_token(),
  17690. "ERR024 - Expected a '(' at start of function call to '" + function_name +
  17691. "', instead got: '" + current_token().value + "'",
  17692. exprtk_error_location));
  17693. return 0;
  17694. }
  17695. if (token_is(token_t::e_rbracket, e_hold))
  17696. {
  17697. set_error(
  17698. make_error(parser_error::e_syntax,
  17699. current_token(),
  17700. "ERR025 - Expected at least one input parameter for function call '" + function_name + "'",
  17701. exprtk_error_location));
  17702. return 0;
  17703. }
  17704. std::size_t param_index = 0;
  17705. for (; param_index < MaxNumberofParameters; ++param_index)
  17706. {
  17707. param_list[param_index] = parse_expression();
  17708. if (0 == param_list[param_index])
  17709. return 0;
  17710. else if (token_is(token_t::e_rbracket))
  17711. {
  17712. sd.delete_ptr = false;
  17713. break;
  17714. }
  17715. else if (token_is(token_t::e_comma))
  17716. continue;
  17717. else
  17718. {
  17719. set_error(
  17720. make_error(parser_error::e_syntax,
  17721. current_token(),
  17722. "ERR026 - Expected a ',' between function input parameters, instead got: '" + current_token().value + "'",
  17723. exprtk_error_location));
  17724. return 0;
  17725. }
  17726. }
  17727. if (sd.delete_ptr)
  17728. {
  17729. set_error(
  17730. make_error(parser_error::e_syntax,
  17731. current_token(),
  17732. "ERR027 - Invalid number of input parameters passed to function '" + function_name + "'",
  17733. exprtk_error_location));
  17734. return 0;
  17735. }
  17736. return (param_index + 1);
  17737. }
  17738. inline expression_node_ptr parse_base_operation()
  17739. {
  17740. typedef std::pair<base_ops_map_t::iterator,base_ops_map_t::iterator> map_range_t;
  17741. const std::string operation_name = current_token().value;
  17742. const token_t diagnostic_token = current_token();
  17743. map_range_t itr_range = base_ops_map_.equal_range(operation_name);
  17744. if (0 == std::distance(itr_range.first,itr_range.second))
  17745. {
  17746. set_error(
  17747. make_error(parser_error::e_syntax,
  17748. diagnostic_token,
  17749. "ERR028 - No entry found for base operation: " + operation_name,
  17750. exprtk_error_location));
  17751. return error_node();
  17752. }
  17753. static const std::size_t MaxNumberofParameters = 4;
  17754. expression_node_ptr param_list[MaxNumberofParameters] = {0};
  17755. const std::size_t parameter_count = parse_base_function_call(param_list, operation_name);
  17756. if ((parameter_count > 0) && (parameter_count <= MaxNumberofParameters))
  17757. {
  17758. for (base_ops_map_t::iterator itr = itr_range.first; itr != itr_range.second; ++itr)
  17759. {
  17760. const details::base_operation_t& operation = itr->second;
  17761. if (operation.num_params == parameter_count)
  17762. {
  17763. switch (parameter_count)
  17764. {
  17765. #define base_opr_case(N) \
  17766. case N : { \
  17767. expression_node_ptr pl##N[N] = {0}; \
  17768. std::copy(param_list, param_list + N, pl##N); \
  17769. lodge_symbol(operation_name, e_st_function); \
  17770. return expression_generator_(operation.type, pl##N); \
  17771. } \
  17772. base_opr_case(1)
  17773. base_opr_case(2)
  17774. base_opr_case(3)
  17775. base_opr_case(4)
  17776. #undef base_opr_case
  17777. }
  17778. }
  17779. }
  17780. }
  17781. for (std::size_t i = 0; i < MaxNumberofParameters; ++i)
  17782. {
  17783. free_node(node_allocator_, param_list[i]);
  17784. }
  17785. set_error(
  17786. make_error(parser_error::e_syntax,
  17787. diagnostic_token,
  17788. "ERR029 - Invalid number of input parameters for call to function: '" + operation_name + "'",
  17789. exprtk_error_location));
  17790. return error_node();
  17791. }
  17792. inline expression_node_ptr parse_conditional_statement_01(expression_node_ptr condition)
  17793. {
  17794. // Parse: [if][(][condition][,][consequent][,][alternative][)]
  17795. expression_node_ptr consequent = error_node();
  17796. expression_node_ptr alternative = error_node();
  17797. bool result = true;
  17798. if (!token_is(token_t::e_comma))
  17799. {
  17800. set_error(
  17801. make_error(parser_error::e_syntax,
  17802. current_token(),
  17803. "ERR030 - Expected ',' between if-statement condition and consequent",
  17804. exprtk_error_location));
  17805. result = false;
  17806. }
  17807. else if (0 == (consequent = parse_expression()))
  17808. {
  17809. set_error(
  17810. make_error(parser_error::e_syntax,
  17811. current_token(),
  17812. "ERR031 - Failed to parse consequent for if-statement",
  17813. exprtk_error_location));
  17814. result = false;
  17815. }
  17816. else if (!token_is(token_t::e_comma))
  17817. {
  17818. set_error(
  17819. make_error(parser_error::e_syntax,
  17820. current_token(),
  17821. "ERR032 - Expected ',' between if-statement consequent and alternative",
  17822. exprtk_error_location));
  17823. result = false;
  17824. }
  17825. else if (0 == (alternative = parse_expression()))
  17826. {
  17827. set_error(
  17828. make_error(parser_error::e_syntax,
  17829. current_token(),
  17830. "ERR033 - Failed to parse alternative for if-statement",
  17831. exprtk_error_location));
  17832. result = false;
  17833. }
  17834. else if (!token_is(token_t::e_rbracket))
  17835. {
  17836. set_error(
  17837. make_error(parser_error::e_syntax,
  17838. current_token(),
  17839. "ERR034 - Expected ')' at the end of if-statement",
  17840. exprtk_error_location));
  17841. result = false;
  17842. }
  17843. #ifndef exprtk_disable_string_capabilities
  17844. if (result)
  17845. {
  17846. const bool consq_is_str = is_generally_string_node( consequent);
  17847. const bool alter_is_str = is_generally_string_node(alternative);
  17848. if (consq_is_str || alter_is_str)
  17849. {
  17850. if (consq_is_str && alter_is_str)
  17851. {
  17852. return expression_generator_
  17853. .conditional_string(condition, consequent, alternative);
  17854. }
  17855. set_error(
  17856. make_error(parser_error::e_syntax,
  17857. current_token(),
  17858. "ERR035 - Return types of ternary if-statement differ",
  17859. exprtk_error_location));
  17860. result = false;
  17861. }
  17862. }
  17863. #endif
  17864. if (!result)
  17865. {
  17866. free_node(node_allocator_, condition);
  17867. free_node(node_allocator_, consequent);
  17868. free_node(node_allocator_,alternative);
  17869. return error_node();
  17870. }
  17871. else
  17872. return expression_generator_
  17873. .conditional(condition, consequent, alternative);
  17874. }
  17875. inline expression_node_ptr parse_conditional_statement_02(expression_node_ptr condition)
  17876. {
  17877. expression_node_ptr consequent = error_node();
  17878. expression_node_ptr alternative = error_node();
  17879. bool result = true;
  17880. if (token_is(token_t::e_lcrlbracket,prsrhlpr_t::e_hold))
  17881. {
  17882. if (0 == (consequent = parse_multi_sequence("if-statement-01")))
  17883. {
  17884. set_error(
  17885. make_error(parser_error::e_syntax,
  17886. current_token(),
  17887. "ERR036 - Failed to parse body of consequent for if-statement",
  17888. exprtk_error_location));
  17889. result = false;
  17890. }
  17891. }
  17892. else
  17893. {
  17894. if (
  17895. settings_.commutative_check_enabled() &&
  17896. token_is(token_t::e_mul,prsrhlpr_t::e_hold)
  17897. )
  17898. {
  17899. next_token();
  17900. }
  17901. if (0 != (consequent = parse_expression()))
  17902. {
  17903. if (!token_is(token_t::e_eof))
  17904. {
  17905. set_error(
  17906. make_error(parser_error::e_syntax,
  17907. current_token(),
  17908. "ERR037 - Expected ';' at the end of the consequent for if-statement",
  17909. exprtk_error_location));
  17910. result = false;
  17911. }
  17912. }
  17913. else
  17914. {
  17915. set_error(
  17916. make_error(parser_error::e_syntax,
  17917. current_token(),
  17918. "ERR038 - Failed to parse body of consequent for if-statement",
  17919. exprtk_error_location));
  17920. result = false;
  17921. }
  17922. }
  17923. if (result)
  17924. {
  17925. if (details::imatch(current_token().value,"else"))
  17926. {
  17927. next_token();
  17928. if (token_is(token_t::e_lcrlbracket,prsrhlpr_t::e_hold))
  17929. {
  17930. if (0 == (alternative = parse_multi_sequence("else-statement-01")))
  17931. {
  17932. set_error(
  17933. make_error(parser_error::e_syntax,
  17934. current_token(),
  17935. "ERR039 - Failed to parse body of the 'else' for if-statement",
  17936. exprtk_error_location));
  17937. result = false;
  17938. }
  17939. }
  17940. else if (details::imatch(current_token().value,"if"))
  17941. {
  17942. if (0 == (alternative = parse_conditional_statement()))
  17943. {
  17944. set_error(
  17945. make_error(parser_error::e_syntax,
  17946. current_token(),
  17947. "ERR040 - Failed to parse body of if-else statement",
  17948. exprtk_error_location));
  17949. result = false;
  17950. }
  17951. }
  17952. else if (0 != (alternative = parse_expression()))
  17953. {
  17954. if (!token_is(token_t::e_eof))
  17955. {
  17956. set_error(
  17957. make_error(parser_error::e_syntax,
  17958. current_token(),
  17959. "ERR041 - Expected ';' at the end of the 'else-if' for the if-statement",
  17960. exprtk_error_location));
  17961. result = false;
  17962. }
  17963. }
  17964. else
  17965. {
  17966. set_error(
  17967. make_error(parser_error::e_syntax,
  17968. current_token(),
  17969. "ERR042 - Failed to parse body of the 'else' for if-statement",
  17970. exprtk_error_location));
  17971. result = false;
  17972. }
  17973. }
  17974. }
  17975. #ifndef exprtk_disable_string_capabilities
  17976. if (result)
  17977. {
  17978. const bool consq_is_str = is_generally_string_node( consequent);
  17979. const bool alter_is_str = is_generally_string_node(alternative);
  17980. if (consq_is_str || alter_is_str)
  17981. {
  17982. if (consq_is_str && alter_is_str)
  17983. {
  17984. return expression_generator_
  17985. .conditional_string(condition, consequent, alternative);
  17986. }
  17987. set_error(
  17988. make_error(parser_error::e_syntax,
  17989. current_token(),
  17990. "ERR043 - Return types of ternary if-statement differ",
  17991. exprtk_error_location));
  17992. result = false;
  17993. }
  17994. }
  17995. #endif
  17996. if (!result)
  17997. {
  17998. free_node(node_allocator_, condition);
  17999. free_node(node_allocator_, consequent);
  18000. free_node(node_allocator_, alternative);
  18001. return error_node();
  18002. }
  18003. else
  18004. return expression_generator_
  18005. .conditional(condition, consequent, alternative);
  18006. }
  18007. inline expression_node_ptr parse_conditional_statement()
  18008. {
  18009. expression_node_ptr condition = error_node();
  18010. next_token();
  18011. if (!token_is(token_t::e_lbracket))
  18012. {
  18013. set_error(
  18014. make_error(parser_error::e_syntax,
  18015. current_token(),
  18016. "ERR044 - Expected '(' at start of if-statement, instead got: '" + current_token().value + "'",
  18017. exprtk_error_location));
  18018. return error_node();
  18019. }
  18020. else if (0 == (condition = parse_expression()))
  18021. {
  18022. set_error(
  18023. make_error(parser_error::e_syntax,
  18024. current_token(),
  18025. "ERR045 - Failed to parse condition for if-statement",
  18026. exprtk_error_location));
  18027. return error_node();
  18028. }
  18029. else if (token_is(token_t::e_comma,prsrhlpr_t::e_hold))
  18030. {
  18031. // if (x,y,z)
  18032. return parse_conditional_statement_01(condition);
  18033. }
  18034. else if (token_is(token_t::e_rbracket))
  18035. {
  18036. // 00. if (x) y;
  18037. // 01. if (x) y; else z;
  18038. // 02. if (x) y; else {z0; ... zn;}
  18039. // 03. if (x) y; else if (z) w;
  18040. // 04. if (x) y; else if (z) w; else u;
  18041. // 05. if (x) y; else if (z) w; else {u0; ... un;}
  18042. // 06. if (x) y; else if (z) {w0; ... wn;}
  18043. // 07. if (x) {y0; ... yn;}
  18044. // 08. if (x) {y0; ... yn;} else z;
  18045. // 09. if (x) {y0; ... yn;} else {z0; ... zn;};
  18046. // 10. if (x) {y0; ... yn;} else if (z) w;
  18047. // 11. if (x) {y0; ... yn;} else if (z) w; else u;
  18048. // 12. if (x) {y0; ... nex;} else if (z) w; else {u0 ... un;}
  18049. // 13. if (x) {y0; ... yn;} else if (z) {w0; ... wn;}
  18050. return parse_conditional_statement_02(condition);
  18051. }
  18052. set_error(
  18053. make_error(parser_error::e_syntax,
  18054. current_token(),
  18055. "ERR046 - Invalid if-statement",
  18056. exprtk_error_location));
  18057. free_node(node_allocator_,condition);
  18058. return error_node();
  18059. }
  18060. inline expression_node_ptr parse_ternary_conditional_statement(expression_node_ptr condition)
  18061. {
  18062. // Parse: [condition][?][consequent][:][alternative]
  18063. expression_node_ptr consequent = error_node();
  18064. expression_node_ptr alternative = error_node();
  18065. bool result = true;
  18066. if (0 == condition)
  18067. {
  18068. set_error(
  18069. make_error(parser_error::e_syntax,
  18070. current_token(),
  18071. "ERR047 - Encountered invalid condition branch for ternary if-statement",
  18072. exprtk_error_location));
  18073. return error_node();
  18074. }
  18075. else if (!token_is(token_t::e_ternary))
  18076. {
  18077. set_error(
  18078. make_error(parser_error::e_syntax,
  18079. current_token(),
  18080. "ERR048 - Expected '?' after condition of ternary if-statement",
  18081. exprtk_error_location));
  18082. result = false;
  18083. }
  18084. else if (0 == (consequent = parse_expression()))
  18085. {
  18086. set_error(
  18087. make_error(parser_error::e_syntax,
  18088. current_token(),
  18089. "ERR049 - Failed to parse consequent for ternary if-statement",
  18090. exprtk_error_location));
  18091. result = false;
  18092. }
  18093. else if (!token_is(token_t::e_colon))
  18094. {
  18095. set_error(
  18096. make_error(parser_error::e_syntax,
  18097. current_token(),
  18098. "ERR050 - Expected ':' between ternary if-statement consequent and alternative",
  18099. exprtk_error_location));
  18100. result = false;
  18101. }
  18102. else if (0 == (alternative = parse_expression()))
  18103. {
  18104. set_error(
  18105. make_error(parser_error::e_syntax,
  18106. current_token(),
  18107. "ERR051 - Failed to parse alternative for ternary if-statement",
  18108. exprtk_error_location));
  18109. result = false;
  18110. }
  18111. #ifndef exprtk_disable_string_capabilities
  18112. if (result)
  18113. {
  18114. const bool consq_is_str = is_generally_string_node( consequent);
  18115. const bool alter_is_str = is_generally_string_node(alternative);
  18116. if (consq_is_str || alter_is_str)
  18117. {
  18118. if (consq_is_str && alter_is_str)
  18119. {
  18120. return expression_generator_
  18121. .conditional_string(condition, consequent, alternative);
  18122. }
  18123. set_error(
  18124. make_error(parser_error::e_syntax,
  18125. current_token(),
  18126. "ERR052 - Return types of ternary if-statement differ",
  18127. exprtk_error_location));
  18128. result = false;
  18129. }
  18130. }
  18131. #endif
  18132. if (!result)
  18133. {
  18134. free_node(node_allocator_, condition);
  18135. free_node(node_allocator_, consequent);
  18136. free_node(node_allocator_, alternative);
  18137. return error_node();
  18138. }
  18139. else
  18140. return expression_generator_
  18141. .conditional(condition, consequent, alternative);
  18142. }
  18143. inline expression_node_ptr parse_not_statement()
  18144. {
  18145. if (settings_.logic_disabled("not"))
  18146. {
  18147. set_error(
  18148. make_error(parser_error::e_syntax,
  18149. current_token(),
  18150. "ERR053 - Invalid or disabled logic operation 'not'",
  18151. exprtk_error_location));
  18152. return error_node();
  18153. }
  18154. return parse_base_operation();
  18155. }
  18156. inline expression_node_ptr parse_while_loop()
  18157. {
  18158. // Parse: [while][(][test expr][)][{][expression][}]
  18159. expression_node_ptr condition = error_node();
  18160. expression_node_ptr branch = error_node();
  18161. expression_node_ptr result_node = error_node();
  18162. bool result = true;
  18163. next_token();
  18164. if (!token_is(token_t::e_lbracket))
  18165. {
  18166. set_error(
  18167. make_error(parser_error::e_syntax,
  18168. current_token(),
  18169. "ERR054 - Expected '(' at start of while-loop condition statement",
  18170. exprtk_error_location));
  18171. return error_node();
  18172. }
  18173. else if (0 == (condition = parse_expression()))
  18174. {
  18175. set_error(
  18176. make_error(parser_error::e_syntax,
  18177. current_token(),
  18178. "ERR055 - Failed to parse condition for while-loop",
  18179. exprtk_error_location));
  18180. return error_node();
  18181. }
  18182. else if (!token_is(token_t::e_rbracket))
  18183. {
  18184. set_error(
  18185. make_error(parser_error::e_syntax,
  18186. current_token(),
  18187. "ERR056 - Expected ')' at end of while-loop condition statement",
  18188. exprtk_error_location));
  18189. result = false;
  18190. }
  18191. brkcnt_list_.push_front(false);
  18192. if (result)
  18193. {
  18194. if (0 == (branch = parse_multi_sequence("while-loop")))
  18195. {
  18196. set_error(
  18197. make_error(parser_error::e_syntax,
  18198. current_token(),
  18199. "ERR057 - Failed to parse body of while-loop"));
  18200. result = false;
  18201. }
  18202. else if (0 == (result_node = expression_generator_.while_loop(condition,
  18203. branch,
  18204. brkcnt_list_.front())))
  18205. {
  18206. set_error(
  18207. make_error(parser_error::e_syntax,
  18208. current_token(),
  18209. "ERR058 - Failed to synthesize while-loop",
  18210. exprtk_error_location));
  18211. result = false;
  18212. }
  18213. }
  18214. if (!result)
  18215. {
  18216. free_node(node_allocator_, branch);
  18217. free_node(node_allocator_, condition);
  18218. free_node(node_allocator_, result_node);
  18219. brkcnt_list_.pop_front();
  18220. return error_node();
  18221. }
  18222. else
  18223. return result_node;
  18224. }
  18225. inline expression_node_ptr parse_repeat_until_loop()
  18226. {
  18227. // Parse: [repeat][{][expression][}][until][(][test expr][)]
  18228. expression_node_ptr condition = error_node();
  18229. expression_node_ptr branch = error_node();
  18230. next_token();
  18231. std::vector<expression_node_ptr> arg_list;
  18232. std::vector<bool> side_effect_list;
  18233. scoped_vec_delete<expression_node_t> sdd((*this),arg_list);
  18234. brkcnt_list_.push_front(false);
  18235. if (details::imatch(current_token().value,"until"))
  18236. {
  18237. next_token();
  18238. branch = node_allocator_.allocate<details::null_node<T> >();
  18239. }
  18240. else
  18241. {
  18242. const token_t::token_type seperator = token_t::e_eof;
  18243. scope_handler sh(*this);
  18244. scoped_bool_or_restorer sbr(state_.side_effect_present);
  18245. for ( ; ; )
  18246. {
  18247. state_.side_effect_present = false;
  18248. expression_node_ptr arg = parse_expression();
  18249. if (0 == arg)
  18250. return error_node();
  18251. else
  18252. {
  18253. arg_list.push_back(arg);
  18254. side_effect_list.push_back(state_.side_effect_present);
  18255. }
  18256. if (details::imatch(current_token().value,"until"))
  18257. {
  18258. next_token();
  18259. break;
  18260. }
  18261. const bool is_next_until = peek_token_is(token_t::e_symbol) &&
  18262. peek_token_is("until");
  18263. if (!token_is(seperator) && is_next_until)
  18264. {
  18265. set_error(
  18266. make_error(parser_error::e_syntax,
  18267. current_token(),
  18268. "ERR059 - Expected '" + token_t::to_str(seperator) + "' in body of repeat until loop",
  18269. exprtk_error_location));
  18270. return error_node();
  18271. }
  18272. if (details::imatch(current_token().value,"until"))
  18273. {
  18274. next_token();
  18275. break;
  18276. }
  18277. }
  18278. branch = simplify(arg_list,side_effect_list);
  18279. sdd.delete_ptr = (0 == branch);
  18280. if (sdd.delete_ptr)
  18281. {
  18282. brkcnt_list_.pop_front();
  18283. set_error(
  18284. make_error(parser_error::e_syntax,
  18285. current_token(),
  18286. "ERR060 - Failed to parse body of repeat until loop",
  18287. exprtk_error_location));
  18288. return error_node();
  18289. }
  18290. }
  18291. if (!token_is(token_t::e_lbracket))
  18292. {
  18293. brkcnt_list_.pop_front();
  18294. set_error(
  18295. make_error(parser_error::e_syntax,
  18296. current_token(),
  18297. "ERR061 - Expected '(' before condition statement of repeat until loop",
  18298. exprtk_error_location));
  18299. free_node(node_allocator_,branch);
  18300. return error_node();
  18301. }
  18302. else if (0 == (condition = parse_expression()))
  18303. {
  18304. brkcnt_list_.pop_front();
  18305. set_error(
  18306. make_error(parser_error::e_syntax,
  18307. current_token(),
  18308. "ERR062 - Failed to parse condition for repeat until loop",
  18309. exprtk_error_location));
  18310. free_node(node_allocator_,branch);
  18311. return error_node();
  18312. }
  18313. else if (!token_is(token_t::e_rbracket))
  18314. {
  18315. set_error(
  18316. make_error(parser_error::e_syntax,
  18317. current_token(),
  18318. "ERR063 - Expected ')' after condition of repeat until loop",
  18319. exprtk_error_location));
  18320. free_node(node_allocator_, branch);
  18321. free_node(node_allocator_, condition);
  18322. brkcnt_list_.pop_front();
  18323. return error_node();
  18324. }
  18325. expression_node_ptr result;
  18326. result = expression_generator_
  18327. .repeat_until_loop(condition, branch, brkcnt_list_.front());
  18328. if (0 == result)
  18329. {
  18330. set_error(
  18331. make_error(parser_error::e_syntax,
  18332. current_token(),
  18333. "ERR064 - Failed to synthesize repeat until loop",
  18334. exprtk_error_location));
  18335. free_node(node_allocator_,condition);
  18336. brkcnt_list_.pop_front();
  18337. return error_node();
  18338. }
  18339. else
  18340. {
  18341. brkcnt_list_.pop_front();
  18342. return result;
  18343. }
  18344. }
  18345. inline expression_node_ptr parse_for_loop()
  18346. {
  18347. expression_node_ptr initialiser = error_node();
  18348. expression_node_ptr condition = error_node();
  18349. expression_node_ptr incrementor = error_node();
  18350. expression_node_ptr loop_body = error_node();
  18351. scope_element* se = 0;
  18352. bool result = true;
  18353. next_token();
  18354. scope_handler sh(*this);
  18355. if (!token_is(token_t::e_lbracket))
  18356. {
  18357. set_error(
  18358. make_error(parser_error::e_syntax,
  18359. current_token(),
  18360. "ERR065 - Expected '(' at start of for-loop",
  18361. exprtk_error_location));
  18362. return error_node();
  18363. }
  18364. if (!token_is(token_t::e_eof))
  18365. {
  18366. if (
  18367. !token_is(token_t::e_symbol,prsrhlpr_t::e_hold) &&
  18368. details::imatch(current_token().value,"var")
  18369. )
  18370. {
  18371. next_token();
  18372. if (!token_is(token_t::e_symbol,prsrhlpr_t::e_hold))
  18373. {
  18374. set_error(
  18375. make_error(parser_error::e_syntax,
  18376. current_token(),
  18377. "ERR066 - Expected a variable at the start of initialiser section of for-loop",
  18378. exprtk_error_location));
  18379. return error_node();
  18380. }
  18381. else if (!peek_token_is(token_t::e_assign))
  18382. {
  18383. set_error(
  18384. make_error(parser_error::e_syntax,
  18385. current_token(),
  18386. "ERR067 - Expected variable assignment of initialiser section of for-loop",
  18387. exprtk_error_location));
  18388. return error_node();
  18389. }
  18390. const std::string loop_counter_symbol = current_token().value;
  18391. se = &sem_.get_element(loop_counter_symbol);
  18392. if ((se->name == loop_counter_symbol) && se->active)
  18393. {
  18394. set_error(
  18395. make_error(parser_error::e_syntax,
  18396. current_token(),
  18397. "ERR068 - For-loop variable '" + loop_counter_symbol+ "' is being shadowed by a previous declaration",
  18398. exprtk_error_location));
  18399. return error_node();
  18400. }
  18401. else if (!symtab_store_.is_variable(loop_counter_symbol))
  18402. {
  18403. if (
  18404. !se->active &&
  18405. (se->name == loop_counter_symbol) &&
  18406. (se->type == scope_element::e_variable)
  18407. )
  18408. {
  18409. se->active = true;
  18410. se->ref_count++;
  18411. }
  18412. else
  18413. {
  18414. scope_element nse;
  18415. nse.name = loop_counter_symbol;
  18416. nse.active = true;
  18417. nse.ref_count = 1;
  18418. nse.type = scope_element::e_variable;
  18419. nse.depth = state_.scope_depth;
  18420. nse.data = new T(T(0));
  18421. nse.var_node = node_allocator_.allocate<variable_node_t>(*(T*)(nse.data));
  18422. if (!sem_.add_element(nse))
  18423. {
  18424. set_error(
  18425. make_error(parser_error::e_syntax,
  18426. current_token(),
  18427. "ERR069 - Failed to add new local variable '" + loop_counter_symbol + "' to SEM",
  18428. exprtk_error_location));
  18429. sem_.free_element(nse);
  18430. result = false;
  18431. }
  18432. else
  18433. {
  18434. exprtk_debug(("parse_for_loop() - INFO - Added new local variable: %s\n",nse.name.c_str()));
  18435. state_.activate_side_effect("parse_for_loop()");
  18436. }
  18437. }
  18438. }
  18439. }
  18440. if (0 == (initialiser = parse_expression()))
  18441. {
  18442. set_error(
  18443. make_error(parser_error::e_syntax,
  18444. current_token(),
  18445. "ERR070 - Failed to parse initialiser of for-loop",
  18446. exprtk_error_location));
  18447. result = false;
  18448. }
  18449. else if (!token_is(token_t::e_eof))
  18450. {
  18451. set_error(
  18452. make_error(parser_error::e_syntax,
  18453. current_token(),
  18454. "ERR071 - Expected ';' after initialiser of for-loop",
  18455. exprtk_error_location));
  18456. result = false;
  18457. }
  18458. }
  18459. if (!token_is(token_t::e_eof))
  18460. {
  18461. if (0 == (condition = parse_expression()))
  18462. {
  18463. set_error(
  18464. make_error(parser_error::e_syntax,
  18465. current_token(),
  18466. "ERR072 - Failed to parse condition of for-loop",
  18467. exprtk_error_location));
  18468. result = false;
  18469. }
  18470. else if (!token_is(token_t::e_eof))
  18471. {
  18472. set_error(
  18473. make_error(parser_error::e_syntax,
  18474. current_token(),
  18475. "ERR073 - Expected ';' after condition section of for-loop",
  18476. exprtk_error_location));
  18477. result = false;
  18478. }
  18479. }
  18480. if (!token_is(token_t::e_rbracket))
  18481. {
  18482. if (0 == (incrementor = parse_expression()))
  18483. {
  18484. set_error(
  18485. make_error(parser_error::e_syntax,
  18486. current_token(),
  18487. "ERR074 - Failed to parse incrementor of for-loop",
  18488. exprtk_error_location));
  18489. result = false;
  18490. }
  18491. else if (!token_is(token_t::e_rbracket))
  18492. {
  18493. set_error(
  18494. make_error(parser_error::e_syntax,
  18495. current_token(),
  18496. "ERR075 - Expected ')' after incrementor section of for-loop",
  18497. exprtk_error_location));
  18498. result = false;
  18499. }
  18500. }
  18501. if (result)
  18502. {
  18503. brkcnt_list_.push_front(false);
  18504. if (0 == (loop_body = parse_multi_sequence("for-loop")))
  18505. {
  18506. set_error(
  18507. make_error(parser_error::e_syntax,
  18508. current_token(),
  18509. "ERR076 - Failed to parse body of for-loop",
  18510. exprtk_error_location));
  18511. result = false;
  18512. }
  18513. }
  18514. if (!result)
  18515. {
  18516. if (se)
  18517. {
  18518. se->ref_count--;
  18519. }
  18520. free_node(node_allocator_, initialiser);
  18521. free_node(node_allocator_, condition);
  18522. free_node(node_allocator_, incrementor);
  18523. free_node(node_allocator_, loop_body);
  18524. if (!brkcnt_list_.empty())
  18525. {
  18526. brkcnt_list_.pop_front();
  18527. }
  18528. return error_node();
  18529. }
  18530. else
  18531. {
  18532. expression_node_ptr result_node =
  18533. expression_generator_.for_loop(initialiser,
  18534. condition,
  18535. incrementor,
  18536. loop_body,
  18537. brkcnt_list_.front());
  18538. brkcnt_list_.pop_front();
  18539. return result_node;
  18540. }
  18541. }
  18542. inline expression_node_ptr parse_switch_statement()
  18543. {
  18544. std::vector<expression_node_ptr> arg_list;
  18545. expression_node_ptr result = error_node();
  18546. if (!details::imatch(current_token().value,"switch"))
  18547. {
  18548. set_error(
  18549. make_error(parser_error::e_syntax,
  18550. current_token(),
  18551. "ERR077 - Expected keyword 'switch'",
  18552. exprtk_error_location));
  18553. return error_node();
  18554. }
  18555. scoped_vec_delete<expression_node_t> svd((*this),arg_list);
  18556. next_token();
  18557. if (!token_is(token_t::e_lcrlbracket))
  18558. {
  18559. set_error(
  18560. make_error(parser_error::e_syntax,
  18561. current_token(),
  18562. "ERR078 - Expected '{' for call to switch statement",
  18563. exprtk_error_location));
  18564. return error_node();
  18565. }
  18566. for ( ; ; )
  18567. {
  18568. if (!details::imatch("case",current_token().value))
  18569. {
  18570. set_error(
  18571. make_error(parser_error::e_syntax,
  18572. current_token(),
  18573. "ERR079 - Expected either a 'case' or 'default' statement",
  18574. exprtk_error_location));
  18575. return error_node();
  18576. }
  18577. next_token();
  18578. expression_node_ptr condition = parse_expression();
  18579. if (0 == condition)
  18580. return error_node();
  18581. else if (!token_is(token_t::e_colon))
  18582. {
  18583. set_error(
  18584. make_error(parser_error::e_syntax,
  18585. current_token(),
  18586. "ERR080 - Expected ':' for case of switch statement",
  18587. exprtk_error_location));
  18588. return error_node();
  18589. }
  18590. expression_node_ptr consequent = parse_expression();
  18591. if (0 == consequent)
  18592. return error_node();
  18593. else if (!token_is(token_t::e_eof))
  18594. {
  18595. set_error(
  18596. make_error(parser_error::e_syntax,
  18597. current_token(),
  18598. "ERR081 - Expected ';' at end of case for switch statement",
  18599. exprtk_error_location));
  18600. return error_node();
  18601. }
  18602. // Can we optimise away the case statement?
  18603. if (is_constant_node(condition) && is_false(condition))
  18604. {
  18605. free_node(node_allocator_, condition);
  18606. free_node(node_allocator_, consequent);
  18607. }
  18608. else
  18609. {
  18610. arg_list.push_back( condition);
  18611. arg_list.push_back(consequent);
  18612. }
  18613. if (details::imatch("default",current_token().value))
  18614. {
  18615. next_token();
  18616. if (!token_is(token_t::e_colon))
  18617. {
  18618. set_error(
  18619. make_error(parser_error::e_syntax,
  18620. current_token(),
  18621. "ERR082 - Expected ':' for default of switch statement",
  18622. exprtk_error_location));
  18623. return error_node();
  18624. }
  18625. expression_node_ptr default_statement = error_node();
  18626. if (token_is(token_t::e_lcrlbracket,prsrhlpr_t::e_hold))
  18627. default_statement = parse_multi_sequence("switch-default");
  18628. else
  18629. default_statement = parse_expression();
  18630. if (0 == default_statement)
  18631. return error_node();
  18632. else if (!token_is(token_t::e_eof))
  18633. {
  18634. free_node(node_allocator_,default_statement);
  18635. set_error(
  18636. make_error(parser_error::e_syntax,
  18637. current_token(),
  18638. "ERR083 - Expected ';' at end of default for switch statement",
  18639. exprtk_error_location));
  18640. return error_node();
  18641. }
  18642. arg_list.push_back(default_statement);
  18643. break;
  18644. }
  18645. }
  18646. if (!token_is(token_t::e_rcrlbracket))
  18647. {
  18648. set_error(
  18649. make_error(parser_error::e_syntax,
  18650. current_token(),
  18651. "ERR084 - Expected '}' at end of switch statement",
  18652. exprtk_error_location));
  18653. return error_node();
  18654. }
  18655. result = expression_generator_.switch_statement(arg_list);
  18656. svd.delete_ptr = (0 == result);
  18657. return result;
  18658. }
  18659. inline expression_node_ptr parse_multi_switch_statement()
  18660. {
  18661. std::vector<expression_node_ptr> arg_list;
  18662. if (!details::imatch(current_token().value,"[*]"))
  18663. {
  18664. set_error(
  18665. make_error(parser_error::e_syntax,
  18666. current_token(),
  18667. "ERR085 - Expected token '[*]'",
  18668. exprtk_error_location));
  18669. return error_node();
  18670. }
  18671. scoped_vec_delete<expression_node_t> svd((*this),arg_list);
  18672. next_token();
  18673. if (!token_is(token_t::e_lcrlbracket))
  18674. {
  18675. set_error(
  18676. make_error(parser_error::e_syntax,
  18677. current_token(),
  18678. "ERR086 - Expected '{' for call to [*] statement",
  18679. exprtk_error_location));
  18680. return error_node();
  18681. }
  18682. for ( ; ; )
  18683. {
  18684. if (!details::imatch("case",current_token().value))
  18685. {
  18686. set_error(
  18687. make_error(parser_error::e_syntax,
  18688. current_token(),
  18689. "ERR087 - Expected a 'case' statement for multi-switch",
  18690. exprtk_error_location));
  18691. return error_node();
  18692. }
  18693. next_token();
  18694. expression_node_ptr condition = parse_expression();
  18695. if (0 == condition)
  18696. return error_node();
  18697. if (!token_is(token_t::e_colon))
  18698. {
  18699. set_error(
  18700. make_error(parser_error::e_syntax,
  18701. current_token(),
  18702. "ERR088 - Expected ':' for case of [*] statement",
  18703. exprtk_error_location));
  18704. return error_node();
  18705. }
  18706. expression_node_ptr consequent = parse_expression();
  18707. if (0 == consequent)
  18708. return error_node();
  18709. if (!token_is(token_t::e_eof))
  18710. {
  18711. set_error(
  18712. make_error(parser_error::e_syntax,
  18713. current_token(),
  18714. "ERR089 - Expected ';' at end of case for [*] statement",
  18715. exprtk_error_location));
  18716. return error_node();
  18717. }
  18718. // Can we optimise away the case statement?
  18719. if (is_constant_node(condition) && is_false(condition))
  18720. {
  18721. free_node(node_allocator_, condition);
  18722. free_node(node_allocator_, consequent);
  18723. }
  18724. else
  18725. {
  18726. arg_list.push_back( condition);
  18727. arg_list.push_back(consequent);
  18728. }
  18729. if (token_is(token_t::e_rcrlbracket,prsrhlpr_t::e_hold))
  18730. {
  18731. break;
  18732. }
  18733. }
  18734. if (!token_is(token_t::e_rcrlbracket))
  18735. {
  18736. set_error(
  18737. make_error(parser_error::e_syntax,
  18738. current_token(),
  18739. "ERR090 - Expected '}' at end of [*] statement",
  18740. exprtk_error_location));
  18741. return error_node();
  18742. }
  18743. const expression_node_ptr result = expression_generator_.multi_switch_statement(arg_list);
  18744. svd.delete_ptr = (0 == result);
  18745. return result;
  18746. }
  18747. inline expression_node_ptr parse_vararg_function()
  18748. {
  18749. std::vector<expression_node_ptr> arg_list;
  18750. details::operator_type opt_type = details::e_default;
  18751. const std::string symbol = current_token().value;
  18752. if (details::imatch(symbol,"~"))
  18753. {
  18754. next_token();
  18755. return parse_multi_sequence();
  18756. }
  18757. else if (details::imatch(symbol,"[*]"))
  18758. {
  18759. return parse_multi_switch_statement();
  18760. }
  18761. else if (details::imatch(symbol, "avg" )) opt_type = details::e_avg ;
  18762. else if (details::imatch(symbol, "mand")) opt_type = details::e_mand;
  18763. else if (details::imatch(symbol, "max" )) opt_type = details::e_max ;
  18764. else if (details::imatch(symbol, "min" )) opt_type = details::e_min ;
  18765. else if (details::imatch(symbol, "mor" )) opt_type = details::e_mor ;
  18766. else if (details::imatch(symbol, "mul" )) opt_type = details::e_prod;
  18767. else if (details::imatch(symbol, "sum" )) opt_type = details::e_sum ;
  18768. else
  18769. {
  18770. set_error(
  18771. make_error(parser_error::e_syntax,
  18772. current_token(),
  18773. "ERR091 - Unsupported vararg function: " + symbol,
  18774. exprtk_error_location));
  18775. return error_node();
  18776. }
  18777. scoped_vec_delete<expression_node_t> sdd((*this),arg_list);
  18778. lodge_symbol(symbol, e_st_function);
  18779. next_token();
  18780. if (!token_is(token_t::e_lbracket))
  18781. {
  18782. set_error(
  18783. make_error(parser_error::e_syntax,
  18784. current_token(),
  18785. "ERR092 - Expected '(' for call to vararg function: " + symbol,
  18786. exprtk_error_location));
  18787. return error_node();
  18788. }
  18789. for ( ; ; )
  18790. {
  18791. expression_node_ptr arg = parse_expression();
  18792. if (0 == arg)
  18793. return error_node();
  18794. else
  18795. arg_list.push_back(arg);
  18796. if (token_is(token_t::e_rbracket))
  18797. break;
  18798. else if (!token_is(token_t::e_comma))
  18799. {
  18800. set_error(
  18801. make_error(parser_error::e_syntax,
  18802. current_token(),
  18803. "ERR093 - Expected ',' for call to vararg function: " + symbol,
  18804. exprtk_error_location));
  18805. return error_node();
  18806. }
  18807. }
  18808. const expression_node_ptr result = expression_generator_.vararg_function(opt_type,arg_list);
  18809. sdd.delete_ptr = (0 == result);
  18810. return result;
  18811. }
  18812. #ifndef exprtk_disable_string_capabilities
  18813. inline expression_node_ptr parse_string_range_statement(expression_node_ptr& expression)
  18814. {
  18815. if (!token_is(token_t::e_lsqrbracket))
  18816. {
  18817. set_error(
  18818. make_error(parser_error::e_syntax,
  18819. current_token(),
  18820. "ERR094 - Expected '[' as start of string range definition",
  18821. exprtk_error_location));
  18822. free_node(node_allocator_,expression);
  18823. return error_node();
  18824. }
  18825. else if (token_is(token_t::e_rsqrbracket))
  18826. {
  18827. return node_allocator_.allocate<details::string_size_node<T> >(expression);
  18828. }
  18829. range_t rp;
  18830. if (!parse_range(rp,true))
  18831. {
  18832. free_node(node_allocator_,expression);
  18833. return error_node();
  18834. }
  18835. expression_node_ptr result = expression_generator_(expression,rp);
  18836. if (0 == result)
  18837. {
  18838. set_error(
  18839. make_error(parser_error::e_syntax,
  18840. current_token(),
  18841. "ERR095 - Failed to generate string range node",
  18842. exprtk_error_location));
  18843. free_node(node_allocator_,expression);
  18844. }
  18845. rp.clear();
  18846. return result;
  18847. }
  18848. #else
  18849. inline expression_node_ptr parse_string_range_statement(expression_node_ptr&)
  18850. {
  18851. return error_node();
  18852. }
  18853. #endif
  18854. inline void parse_pending_string_rangesize(expression_node_ptr& expression)
  18855. {
  18856. // Allow no more than 100 range calls, eg: s[][][]...[][]
  18857. const std::size_t max_rangesize_parses = 100;
  18858. std::size_t i = 0;
  18859. while
  18860. (
  18861. (0 != expression) &&
  18862. (i++ < max_rangesize_parses) &&
  18863. error_list_.empty() &&
  18864. is_generally_string_node(expression) &&
  18865. token_is(token_t::e_lsqrbracket,prsrhlpr_t::e_hold)
  18866. )
  18867. {
  18868. expression = parse_string_range_statement(expression);
  18869. }
  18870. }
  18871. template <typename Allocator1,
  18872. typename Allocator2,
  18873. template <typename, typename> class Sequence>
  18874. inline expression_node_ptr simplify(Sequence<expression_node_ptr,Allocator1>& expression_list,
  18875. Sequence<bool,Allocator2>& side_effect_list,
  18876. const bool specialise_on_final_type = false)
  18877. {
  18878. if (expression_list.empty())
  18879. return error_node();
  18880. else if (1 == expression_list.size())
  18881. return expression_list[0];
  18882. Sequence<expression_node_ptr,Allocator1> tmp_expression_list;
  18883. bool return_node_present = false;
  18884. for (std::size_t i = 0; i < (expression_list.size() - 1); ++i)
  18885. {
  18886. if (is_variable_node(expression_list[i]))
  18887. continue;
  18888. else if (
  18889. is_return_node (expression_list[i]) ||
  18890. is_break_node (expression_list[i]) ||
  18891. is_continue_node(expression_list[i])
  18892. )
  18893. {
  18894. tmp_expression_list.push_back(expression_list[i]);
  18895. // Remove all subexpressions after first short-circuit
  18896. // node has been encountered.
  18897. for (std::size_t j = i + 1; j < expression_list.size(); ++j)
  18898. {
  18899. free_node(node_allocator_,expression_list[j]);
  18900. }
  18901. return_node_present = true;
  18902. break;
  18903. }
  18904. else if (
  18905. is_constant_node(expression_list[i]) ||
  18906. is_null_node (expression_list[i]) ||
  18907. !side_effect_list[i]
  18908. )
  18909. {
  18910. free_node(node_allocator_,expression_list[i]);
  18911. continue;
  18912. }
  18913. else
  18914. tmp_expression_list.push_back(expression_list[i]);
  18915. }
  18916. if (!return_node_present)
  18917. {
  18918. tmp_expression_list.push_back(expression_list.back());
  18919. }
  18920. expression_list.swap(tmp_expression_list);
  18921. if (tmp_expression_list.size() > expression_list.size())
  18922. {
  18923. exprtk_debug(("simplify() - Reduced subexpressions from %d to %d\n",
  18924. static_cast<int>(tmp_expression_list.size()),
  18925. static_cast<int>(expression_list .size())));
  18926. }
  18927. if (
  18928. return_node_present ||
  18929. side_effect_list.back() ||
  18930. (expression_list.size() > 1)
  18931. )
  18932. state_.activate_side_effect("simplify()");
  18933. if (1 == expression_list.size())
  18934. return expression_list[0];
  18935. else if (specialise_on_final_type && is_generally_string_node(expression_list.back()))
  18936. return expression_generator_.vararg_function(details::e_smulti,expression_list);
  18937. else
  18938. return expression_generator_.vararg_function(details::e_multi,expression_list);
  18939. }
  18940. inline expression_node_ptr parse_multi_sequence(const std::string& source = "")
  18941. {
  18942. token_t::token_type close_bracket = token_t::e_rcrlbracket;
  18943. token_t::token_type seperator = token_t::e_eof;
  18944. if (!token_is(token_t::e_lcrlbracket))
  18945. {
  18946. if (token_is(token_t::e_lbracket))
  18947. {
  18948. close_bracket = token_t::e_rbracket;
  18949. seperator = token_t::e_comma;
  18950. }
  18951. else
  18952. {
  18953. set_error(
  18954. make_error(parser_error::e_syntax,
  18955. current_token(),
  18956. "ERR096 - Expected '" + token_t::to_str(close_bracket) + "' for call to multi-sequence" +
  18957. ((!source.empty()) ? std::string(" section of " + source): ""),
  18958. exprtk_error_location));
  18959. return error_node();
  18960. }
  18961. }
  18962. else if (token_is(token_t::e_rcrlbracket))
  18963. {
  18964. return node_allocator_.allocate<details::null_node<T> >();
  18965. }
  18966. std::vector<expression_node_ptr> arg_list;
  18967. std::vector<bool> side_effect_list;
  18968. expression_node_ptr result = error_node();
  18969. scoped_vec_delete<expression_node_t> sdd((*this),arg_list);
  18970. scope_handler sh(*this);
  18971. scoped_bool_or_restorer sbr(state_.side_effect_present);
  18972. for ( ; ; )
  18973. {
  18974. state_.side_effect_present = false;
  18975. expression_node_ptr arg = parse_expression();
  18976. if (0 == arg)
  18977. return error_node();
  18978. else
  18979. {
  18980. arg_list.push_back(arg);
  18981. side_effect_list.push_back(state_.side_effect_present);
  18982. }
  18983. if (token_is(close_bracket))
  18984. break;
  18985. const bool is_next_close = peek_token_is(close_bracket);
  18986. if (!token_is(seperator) && is_next_close)
  18987. {
  18988. set_error(
  18989. make_error(parser_error::e_syntax,
  18990. current_token(),
  18991. "ERR097 - Expected '" + details::to_str(seperator) + "' for call to multi-sequence section of " + source,
  18992. exprtk_error_location));
  18993. return error_node();
  18994. }
  18995. if (token_is(close_bracket))
  18996. break;
  18997. }
  18998. result = simplify(arg_list,side_effect_list,source.empty());
  18999. sdd.delete_ptr = (0 == result);
  19000. return result;
  19001. }
  19002. inline bool parse_range(range_t& rp, const bool skip_lsqr = false)
  19003. {
  19004. // Examples of valid ranges:
  19005. // 1. [1:5] -> 1..5
  19006. // 2. [ :5] -> 0..5
  19007. // 3. [1: ] -> 1..end
  19008. // 4. [x:y] -> x..y where x <= y
  19009. // 5. [x+1:y/2] -> x+1..y/2 where x+1 <= y/2
  19010. // 6. [ :y] -> 0..y where 0 <= y
  19011. // 7. [x: ] -> x..end where x <= end
  19012. rp.clear();
  19013. if (!skip_lsqr && !token_is(token_t::e_lsqrbracket))
  19014. {
  19015. set_error(
  19016. make_error(parser_error::e_syntax,
  19017. current_token(),
  19018. "ERR098 - Expected '[' for start of range",
  19019. exprtk_error_location));
  19020. return false;
  19021. }
  19022. if (token_is(token_t::e_colon))
  19023. {
  19024. rp.n0_c.first = true;
  19025. rp.n0_c.second = 0;
  19026. rp.cache.first = 0;
  19027. }
  19028. else
  19029. {
  19030. expression_node_ptr r0 = parse_expression();
  19031. if (0 == r0)
  19032. {
  19033. set_error(
  19034. make_error(parser_error::e_syntax,
  19035. current_token(),
  19036. "ERR099 - Failed parse begin section of range",
  19037. exprtk_error_location));
  19038. return false;
  19039. }
  19040. else if (is_constant_node(r0))
  19041. {
  19042. const T r0_value = r0->value();
  19043. if (r0_value >= T(0))
  19044. {
  19045. rp.n0_c.first = true;
  19046. rp.n0_c.second = static_cast<std::size_t>(details::numeric::to_int64(r0_value));
  19047. rp.cache.first = rp.n0_c.second;
  19048. }
  19049. free_node(node_allocator_,r0);
  19050. if (r0_value < T(0))
  19051. {
  19052. set_error(
  19053. make_error(parser_error::e_syntax,
  19054. current_token(),
  19055. "ERR100 - Range lower bound less than zero! Constraint: r0 >= 0",
  19056. exprtk_error_location));
  19057. return false;
  19058. }
  19059. }
  19060. else
  19061. {
  19062. rp.n0_e.first = true;
  19063. rp.n0_e.second = r0;
  19064. }
  19065. if (!token_is(token_t::e_colon))
  19066. {
  19067. set_error(
  19068. make_error(parser_error::e_syntax,
  19069. current_token(),
  19070. "ERR101 - Expected ':' for break in range",
  19071. exprtk_error_location));
  19072. rp.free();
  19073. return false;
  19074. }
  19075. }
  19076. if (token_is(token_t::e_rsqrbracket))
  19077. {
  19078. rp.n1_c.first = true;
  19079. rp.n1_c.second = std::numeric_limits<std::size_t>::max();
  19080. }
  19081. else
  19082. {
  19083. expression_node_ptr r1 = parse_expression();
  19084. if (0 == r1)
  19085. {
  19086. set_error(
  19087. make_error(parser_error::e_syntax,
  19088. current_token(),
  19089. "ERR102 - Failed parse end section of range",
  19090. exprtk_error_location));
  19091. rp.free();
  19092. return false;
  19093. }
  19094. else if (is_constant_node(r1))
  19095. {
  19096. const T r1_value = r1->value();
  19097. if (r1_value >= T(0))
  19098. {
  19099. rp.n1_c.first = true;
  19100. rp.n1_c.second = static_cast<std::size_t>(details::numeric::to_int64(r1_value));
  19101. rp.cache.second = rp.n1_c.second;
  19102. }
  19103. free_node(node_allocator_,r1);
  19104. if (r1_value < T(0))
  19105. {
  19106. set_error(
  19107. make_error(parser_error::e_syntax,
  19108. current_token(),
  19109. "ERR103 - Range upper bound less than zero! Constraint: r1 >= 0",
  19110. exprtk_error_location));
  19111. return false;
  19112. }
  19113. }
  19114. else
  19115. {
  19116. rp.n1_e.first = true;
  19117. rp.n1_e.second = r1;
  19118. }
  19119. if (!token_is(token_t::e_rsqrbracket))
  19120. {
  19121. set_error(
  19122. make_error(parser_error::e_syntax,
  19123. current_token(),
  19124. "ERR104 - Expected ']' for start of range",
  19125. exprtk_error_location));
  19126. rp.free();
  19127. return false;
  19128. }
  19129. }
  19130. if (rp.const_range())
  19131. {
  19132. std::size_t r0 = 0;
  19133. std::size_t r1 = 0;
  19134. const bool rp_result = rp(r0,r1);
  19135. if (!rp_result || (r0 > r1))
  19136. {
  19137. set_error(
  19138. make_error(parser_error::e_syntax,
  19139. current_token(),
  19140. "ERR105 - Invalid range, Constraint: r0 <= r1",
  19141. exprtk_error_location));
  19142. return false;
  19143. }
  19144. }
  19145. return true;
  19146. }
  19147. inline void lodge_symbol(const std::string& symbol,
  19148. const symbol_type st)
  19149. {
  19150. dec_.add_symbol(symbol,st);
  19151. }
  19152. #ifndef exprtk_disable_string_capabilities
  19153. inline expression_node_ptr parse_string()
  19154. {
  19155. const std::string symbol = current_token().value;
  19156. typedef details::stringvar_node<T>* strvar_node_t;
  19157. expression_node_ptr result = error_node();
  19158. strvar_node_t const_str_node = static_cast<strvar_node_t>(0);
  19159. scope_element& se = sem_.get_active_element(symbol);
  19160. if (scope_element::e_string == se.type)
  19161. {
  19162. se.active = true;
  19163. result = se.str_node;
  19164. lodge_symbol(symbol, e_st_local_string);
  19165. }
  19166. else
  19167. {
  19168. if (!symtab_store_.is_conststr_stringvar(symbol))
  19169. {
  19170. set_error(
  19171. make_error(parser_error::e_syntax,
  19172. current_token(),
  19173. "ERR106 - Unknown string symbol",
  19174. exprtk_error_location));
  19175. return error_node();
  19176. }
  19177. result = symtab_store_.get_stringvar(symbol);
  19178. if (symtab_store_.is_constant_string(symbol))
  19179. {
  19180. const_str_node = static_cast<strvar_node_t>(result);
  19181. result = expression_generator_(const_str_node->str());
  19182. }
  19183. lodge_symbol(symbol, e_st_string);
  19184. }
  19185. if (peek_token_is(token_t::e_lsqrbracket))
  19186. {
  19187. next_token();
  19188. if (peek_token_is(token_t::e_rsqrbracket))
  19189. {
  19190. next_token();
  19191. next_token();
  19192. if (const_str_node)
  19193. {
  19194. free_node(node_allocator_,result);
  19195. return expression_generator_(T(const_str_node->size()));
  19196. }
  19197. else
  19198. return node_allocator_.allocate<details::stringvar_size_node<T> >
  19199. (static_cast<details::stringvar_node<T>*>(result)->ref());
  19200. }
  19201. range_t rp;
  19202. if (!parse_range(rp))
  19203. {
  19204. free_node(node_allocator_,result);
  19205. return error_node();
  19206. }
  19207. else if (const_str_node)
  19208. {
  19209. free_node(node_allocator_,result);
  19210. result = expression_generator_(const_str_node->ref(),rp);
  19211. }
  19212. else
  19213. result = expression_generator_(static_cast<details::stringvar_node<T>*>
  19214. (result)->ref(), rp);
  19215. if (result)
  19216. rp.clear();
  19217. }
  19218. else
  19219. next_token();
  19220. return result;
  19221. }
  19222. #else
  19223. inline expression_node_ptr parse_string()
  19224. {
  19225. return error_node();
  19226. }
  19227. #endif
  19228. #ifndef exprtk_disable_string_capabilities
  19229. inline expression_node_ptr parse_const_string()
  19230. {
  19231. const std::string const_str = current_token().value;
  19232. expression_node_ptr result = expression_generator_(const_str);
  19233. if (peek_token_is(token_t::e_lsqrbracket))
  19234. {
  19235. next_token();
  19236. if (peek_token_is(token_t::e_rsqrbracket))
  19237. {
  19238. next_token();
  19239. next_token();
  19240. free_node(node_allocator_,result);
  19241. return expression_generator_(T(const_str.size()));
  19242. }
  19243. range_t rp;
  19244. if (!parse_range(rp))
  19245. {
  19246. free_node(node_allocator_,result);
  19247. return error_node();
  19248. }
  19249. free_node(node_allocator_,result);
  19250. if (rp.n1_c.first && (rp.n1_c.second == std::numeric_limits<std::size_t>::max()))
  19251. {
  19252. rp.n1_c.second = const_str.size() - 1;
  19253. rp.cache.second = rp.n1_c.second;
  19254. }
  19255. if (
  19256. (rp.n0_c.first && (rp.n0_c.second >= const_str.size())) ||
  19257. (rp.n1_c.first && (rp.n1_c.second >= const_str.size()))
  19258. )
  19259. {
  19260. set_error(
  19261. make_error(parser_error::e_syntax,
  19262. current_token(),
  19263. "ERR107 - Overflow in range for string: '" + const_str + "'[" +
  19264. (rp.n0_c.first ? details::to_str(static_cast<int>(rp.n0_c.second)) : "?") + ":" +
  19265. (rp.n1_c.first ? details::to_str(static_cast<int>(rp.n1_c.second)) : "?") + "]",
  19266. exprtk_error_location));
  19267. return error_node();
  19268. }
  19269. result = expression_generator_(const_str,rp);
  19270. if (result)
  19271. rp.clear();
  19272. }
  19273. else
  19274. next_token();
  19275. return result;
  19276. }
  19277. #else
  19278. inline expression_node_ptr parse_const_string()
  19279. {
  19280. return error_node();
  19281. }
  19282. #endif
  19283. inline expression_node_ptr parse_vector()
  19284. {
  19285. const std::string symbol = current_token().value;
  19286. vector_holder_ptr vec = vector_holder_ptr(0);
  19287. const scope_element& se = sem_.get_active_element(symbol);
  19288. if (
  19289. !details::imatch(se.name, symbol) ||
  19290. (se.depth > state_.scope_depth) ||
  19291. (scope_element::e_vector != se.type)
  19292. )
  19293. {
  19294. if (0 == (vec = symtab_store_.get_vector(symbol)))
  19295. {
  19296. set_error(
  19297. make_error(parser_error::e_syntax,
  19298. current_token(),
  19299. "ERR108 - Symbol '" + symbol+ " not a vector",
  19300. exprtk_error_location));
  19301. return error_node();
  19302. }
  19303. }
  19304. else
  19305. vec = se.vec_node;
  19306. expression_node_ptr index_expr = error_node();
  19307. next_token();
  19308. if (!token_is(token_t::e_lsqrbracket))
  19309. {
  19310. return node_allocator_.allocate<vector_node_t>(vec);
  19311. }
  19312. else if (token_is(token_t::e_rsqrbracket))
  19313. {
  19314. return expression_generator_(T(vec->size()));
  19315. }
  19316. else if (0 == (index_expr = parse_expression()))
  19317. {
  19318. set_error(
  19319. make_error(parser_error::e_syntax,
  19320. current_token(),
  19321. "ERR109 - Failed to parse index for vector: '" + symbol + "'",
  19322. exprtk_error_location));
  19323. return error_node();
  19324. }
  19325. else if (!token_is(token_t::e_rsqrbracket))
  19326. {
  19327. set_error(
  19328. make_error(parser_error::e_syntax,
  19329. current_token(),
  19330. "ERR110 - Expected ']' for index of vector: '" + symbol + "'",
  19331. exprtk_error_location));
  19332. free_node(node_allocator_,index_expr);
  19333. return error_node();
  19334. }
  19335. // Perform compile-time range check
  19336. if (details::is_constant_node(index_expr))
  19337. {
  19338. const std::size_t index = static_cast<std::size_t>(details::numeric::to_int32(index_expr->value()));
  19339. const std::size_t vec_size = vec->size();
  19340. if (index >= vec_size)
  19341. {
  19342. set_error(
  19343. make_error(parser_error::e_syntax,
  19344. current_token(),
  19345. "ERR111 - Index of " + details::to_str(index) + " out of range for "
  19346. "vector '" + symbol + "' of size " + details::to_str(vec_size),
  19347. exprtk_error_location));
  19348. free_node(node_allocator_,index_expr);
  19349. return error_node();
  19350. }
  19351. }
  19352. return expression_generator_.vector_element(symbol, vec, index_expr);
  19353. }
  19354. inline expression_node_ptr parse_vararg_function_call(ivararg_function<T>* vararg_function, const std::string& vararg_function_name)
  19355. {
  19356. std::vector<expression_node_ptr> arg_list;
  19357. expression_node_ptr result = error_node();
  19358. scoped_vec_delete<expression_node_t> sdd((*this),arg_list);
  19359. next_token();
  19360. if (token_is(token_t::e_lbracket))
  19361. {
  19362. if (token_is(token_t::e_rbracket))
  19363. {
  19364. if (!vararg_function->allow_zero_parameters())
  19365. {
  19366. set_error(
  19367. make_error(parser_error::e_syntax,
  19368. current_token(),
  19369. "ERR112 - Zero parameter call to vararg function: "
  19370. + vararg_function_name + " not allowed",
  19371. exprtk_error_location));
  19372. return error_node();
  19373. }
  19374. }
  19375. else
  19376. {
  19377. for ( ; ; )
  19378. {
  19379. expression_node_ptr arg = parse_expression();
  19380. if (0 == arg)
  19381. return error_node();
  19382. else
  19383. arg_list.push_back(arg);
  19384. if (token_is(token_t::e_rbracket))
  19385. break;
  19386. else if (!token_is(token_t::e_comma))
  19387. {
  19388. set_error(
  19389. make_error(parser_error::e_syntax,
  19390. current_token(),
  19391. "ERR113 - Expected ',' for call to vararg function: "
  19392. + vararg_function_name,
  19393. exprtk_error_location));
  19394. return error_node();
  19395. }
  19396. }
  19397. }
  19398. }
  19399. else if (!vararg_function->allow_zero_parameters())
  19400. {
  19401. set_error(
  19402. make_error(parser_error::e_syntax,
  19403. current_token(),
  19404. "ERR114 - Zero parameter call to vararg function: "
  19405. + vararg_function_name + " not allowed",
  19406. exprtk_error_location));
  19407. return error_node();
  19408. }
  19409. if (arg_list.size() < vararg_function->min_num_args())
  19410. {
  19411. set_error(
  19412. make_error(parser_error::e_syntax,
  19413. current_token(),
  19414. "ERR115 - Invalid number of parameters to call to vararg function: "
  19415. + vararg_function_name + ", require at least "
  19416. + details::to_str(static_cast<int>(vararg_function->min_num_args())) + " parameters",
  19417. exprtk_error_location));
  19418. return error_node();
  19419. }
  19420. else if (arg_list.size() > vararg_function->max_num_args())
  19421. {
  19422. set_error(
  19423. make_error(parser_error::e_syntax,
  19424. current_token(),
  19425. "ERR116 - Invalid number of parameters to call to vararg function: "
  19426. + vararg_function_name + ", require no more than "
  19427. + details::to_str(static_cast<int>(vararg_function->max_num_args())) + " parameters",
  19428. exprtk_error_location));
  19429. return error_node();
  19430. }
  19431. result = expression_generator_.vararg_function_call(vararg_function,arg_list);
  19432. sdd.delete_ptr = (0 == result);
  19433. return result;
  19434. }
  19435. class type_checker
  19436. {
  19437. public:
  19438. enum return_type_t
  19439. {
  19440. e_overload = ' ',
  19441. e_numeric = 'T',
  19442. e_string = 'S'
  19443. };
  19444. struct function_prototype_t
  19445. {
  19446. return_type_t return_type;
  19447. std::string param_seq;
  19448. };
  19449. typedef parser<T> parser_t;
  19450. typedef std::vector<function_prototype_t> function_definition_list_t;
  19451. type_checker(parser_t& p,
  19452. const std::string& func_name,
  19453. const std::string& func_prototypes,
  19454. const return_type_t default_return_type)
  19455. : invalid_state_(true),
  19456. parser_(p),
  19457. function_name_(func_name),
  19458. default_return_type_(default_return_type)
  19459. {
  19460. parse_function_prototypes(func_prototypes);
  19461. }
  19462. void set_default_return_type(const std::string& return_type)
  19463. {
  19464. default_return_type_ = return_type;
  19465. }
  19466. bool verify(const std::string& param_seq, std::size_t& pseq_index)
  19467. {
  19468. if (function_definition_list_.empty())
  19469. return true;
  19470. std::vector<std::pair<std::size_t,char> > error_list;
  19471. for (std::size_t i = 0; i < function_definition_list_.size(); ++i)
  19472. {
  19473. details::char_t diff_value = 0;
  19474. std::size_t diff_index = 0;
  19475. const bool result = details::sequence_match(function_definition_list_[i].param_seq,
  19476. param_seq,
  19477. diff_index, diff_value);
  19478. if (result)
  19479. {
  19480. pseq_index = i;
  19481. return true;
  19482. }
  19483. else
  19484. error_list.push_back(std::make_pair(diff_index, diff_value));
  19485. }
  19486. if (1 == error_list.size())
  19487. {
  19488. parser_.
  19489. set_error(
  19490. make_error(parser_error::e_syntax,
  19491. parser_.current_token(),
  19492. "ERR117 - Failed parameter type check for function '" + function_name_ + "', "
  19493. "Expected '" + function_definition_list_[0].param_seq +
  19494. "' call set: '" + param_seq + "'",
  19495. exprtk_error_location));
  19496. }
  19497. else
  19498. {
  19499. // find first with largest diff_index;
  19500. std::size_t max_diff_index = 0;
  19501. for (std::size_t i = 1; i < error_list.size(); ++i)
  19502. {
  19503. if (error_list[i].first > error_list[max_diff_index].first)
  19504. {
  19505. max_diff_index = i;
  19506. }
  19507. }
  19508. parser_.
  19509. set_error(
  19510. make_error(parser_error::e_syntax,
  19511. parser_.current_token(),
  19512. "ERR118 - Failed parameter type check for function '" + function_name_ + "', "
  19513. "Best match: '" + function_definition_list_[max_diff_index].param_seq +
  19514. "' call set: '" + param_seq + "'",
  19515. exprtk_error_location));
  19516. }
  19517. return false;
  19518. }
  19519. std::size_t paramseq_count() const
  19520. {
  19521. return function_definition_list_.size();
  19522. }
  19523. std::string paramseq(const std::size_t& index) const
  19524. {
  19525. return function_definition_list_[index].param_seq;
  19526. }
  19527. return_type_t return_type(const std::size_t& index) const
  19528. {
  19529. return function_definition_list_[index].return_type;
  19530. }
  19531. bool invalid() const
  19532. {
  19533. return !invalid_state_;
  19534. }
  19535. bool allow_zero_parameters() const
  19536. {
  19537. for (std::size_t i = 0; i < function_definition_list_.size(); ++i)
  19538. {
  19539. if (std::string::npos != function_definition_list_[i].param_seq.find("Z"))
  19540. {
  19541. return true;
  19542. }
  19543. }
  19544. return false;
  19545. }
  19546. private:
  19547. std::vector<std::string> split_param_seq(const std::string& param_seq, const details::char_t delimiter = '|') const
  19548. {
  19549. std::string::const_iterator current_begin = param_seq.begin();
  19550. std::string::const_iterator iter = param_seq.begin();
  19551. std::vector<std::string> result;
  19552. while (iter != param_seq.end())
  19553. {
  19554. if (*iter == delimiter)
  19555. {
  19556. result.push_back(std::string(current_begin, iter));
  19557. current_begin = ++iter;
  19558. }
  19559. else
  19560. ++iter;
  19561. }
  19562. if (current_begin != iter)
  19563. {
  19564. result.push_back(std::string(current_begin, iter));
  19565. }
  19566. return result;
  19567. }
  19568. inline bool is_valid_token(std::string param_seq,
  19569. function_prototype_t& funcproto) const
  19570. {
  19571. // Determine return type
  19572. funcproto.return_type = default_return_type_;
  19573. if (param_seq.size() > 2)
  19574. {
  19575. if (':' == param_seq[1])
  19576. {
  19577. // Note: Only overloaded igeneric functions can have return
  19578. // type definitions.
  19579. if (type_checker::e_overload != default_return_type_)
  19580. return false;
  19581. switch (param_seq[0])
  19582. {
  19583. case 'T' : funcproto.return_type = type_checker::e_numeric;
  19584. break;
  19585. case 'S' : funcproto.return_type = type_checker::e_string;
  19586. break;
  19587. default : return false;
  19588. }
  19589. param_seq.erase(0,2);
  19590. }
  19591. }
  19592. if (
  19593. (std::string::npos != param_seq.find("?*")) ||
  19594. (std::string::npos != param_seq.find("**"))
  19595. )
  19596. {
  19597. return false;
  19598. }
  19599. else if (
  19600. (std::string::npos == param_seq.find_first_not_of("STV*?|")) ||
  19601. ("Z" == param_seq)
  19602. )
  19603. {
  19604. funcproto.param_seq = param_seq;
  19605. return true;
  19606. }
  19607. return false;
  19608. }
  19609. void parse_function_prototypes(const std::string& func_prototypes)
  19610. {
  19611. if (func_prototypes.empty())
  19612. return;
  19613. std::vector<std::string> param_seq_list = split_param_seq(func_prototypes);
  19614. typedef std::map<std::string,std::size_t> param_seq_map_t;
  19615. param_seq_map_t param_seq_map;
  19616. for (std::size_t i = 0; i < param_seq_list.size(); ++i)
  19617. {
  19618. function_prototype_t func_proto;
  19619. if (!is_valid_token(param_seq_list[i], func_proto))
  19620. {
  19621. invalid_state_ = false;
  19622. parser_.
  19623. set_error(
  19624. make_error(parser_error::e_syntax,
  19625. parser_.current_token(),
  19626. "ERR119 - Invalid parameter sequence of '" + param_seq_list[i] +
  19627. "' for function: " + function_name_,
  19628. exprtk_error_location));
  19629. return;
  19630. }
  19631. param_seq_map_t::const_iterator seq_itr = param_seq_map.find(param_seq_list[i]);
  19632. if (param_seq_map.end() != seq_itr)
  19633. {
  19634. invalid_state_ = false;
  19635. parser_.
  19636. set_error(
  19637. make_error(parser_error::e_syntax,
  19638. parser_.current_token(),
  19639. "ERR120 - Function '" + function_name_ + "' has a parameter sequence conflict between " +
  19640. "pseq_idx[" + details::to_str(seq_itr->second) + "] and" +
  19641. "pseq_idx[" + details::to_str(i) + "] " +
  19642. "param seq: " + param_seq_list[i],
  19643. exprtk_error_location));
  19644. return;
  19645. }
  19646. function_definition_list_.push_back(func_proto);
  19647. }
  19648. }
  19649. type_checker(const type_checker&);
  19650. type_checker& operator=(const type_checker&);
  19651. bool invalid_state_;
  19652. parser_t& parser_;
  19653. std::string function_name_;
  19654. const return_type_t default_return_type_;
  19655. function_definition_list_t function_definition_list_;
  19656. };
  19657. inline expression_node_ptr parse_generic_function_call(igeneric_function<T>* function, const std::string& function_name)
  19658. {
  19659. std::vector<expression_node_ptr> arg_list;
  19660. scoped_vec_delete<expression_node_t> sdd((*this),arg_list);
  19661. next_token();
  19662. std::string param_type_list;
  19663. type_checker tc((*this), function_name, function->parameter_sequence, type_checker::e_string);
  19664. if (tc.invalid())
  19665. {
  19666. set_error(
  19667. make_error(parser_error::e_syntax,
  19668. current_token(),
  19669. "ERR121 - Type checker instantiation failure for generic function: " + function_name,
  19670. exprtk_error_location));
  19671. return error_node();
  19672. }
  19673. if (token_is(token_t::e_lbracket))
  19674. {
  19675. if (token_is(token_t::e_rbracket))
  19676. {
  19677. if (
  19678. !function->allow_zero_parameters() &&
  19679. !tc .allow_zero_parameters()
  19680. )
  19681. {
  19682. set_error(
  19683. make_error(parser_error::e_syntax,
  19684. current_token(),
  19685. "ERR122 - Zero parameter call to generic function: "
  19686. + function_name + " not allowed",
  19687. exprtk_error_location));
  19688. return error_node();
  19689. }
  19690. }
  19691. else
  19692. {
  19693. for ( ; ; )
  19694. {
  19695. expression_node_ptr arg = parse_expression();
  19696. if (0 == arg)
  19697. return error_node();
  19698. if (is_ivector_node(arg))
  19699. param_type_list += 'V';
  19700. else if (is_generally_string_node(arg))
  19701. param_type_list += 'S';
  19702. else // Everything else is assumed to be a scalar returning expression
  19703. param_type_list += 'T';
  19704. arg_list.push_back(arg);
  19705. if (token_is(token_t::e_rbracket))
  19706. break;
  19707. else if (!token_is(token_t::e_comma))
  19708. {
  19709. set_error(
  19710. make_error(parser_error::e_syntax,
  19711. current_token(),
  19712. "ERR123 - Expected ',' for call to generic function: " + function_name,
  19713. exprtk_error_location));
  19714. return error_node();
  19715. }
  19716. }
  19717. }
  19718. }
  19719. else if (
  19720. !function->parameter_sequence.empty() &&
  19721. function->allow_zero_parameters () &&
  19722. !tc .allow_zero_parameters ()
  19723. )
  19724. {
  19725. set_error(
  19726. make_error(parser_error::e_syntax,
  19727. current_token(),
  19728. "ERR124 - Zero parameter call to generic function: "
  19729. + function_name + " not allowed",
  19730. exprtk_error_location));
  19731. return error_node();
  19732. }
  19733. std::size_t param_seq_index = 0;
  19734. if (
  19735. state_.type_check_enabled &&
  19736. !tc.verify(param_type_list, param_seq_index)
  19737. )
  19738. {
  19739. set_error(
  19740. make_error(parser_error::e_syntax,
  19741. current_token(),
  19742. "ERR125 - Invalid input parameter sequence for call to generic function: " + function_name,
  19743. exprtk_error_location));
  19744. return error_node();
  19745. }
  19746. expression_node_ptr result = error_node();
  19747. if (tc.paramseq_count() <= 1)
  19748. result = expression_generator_
  19749. .generic_function_call(function, arg_list);
  19750. else
  19751. result = expression_generator_
  19752. .generic_function_call(function, arg_list, param_seq_index);
  19753. sdd.delete_ptr = (0 == result);
  19754. return result;
  19755. }
  19756. inline bool parse_igeneric_function_params(std::string& param_type_list,
  19757. std::vector<expression_node_ptr>& arg_list,
  19758. const std::string function_name,
  19759. igeneric_function<T>* function,
  19760. const type_checker& tc)
  19761. {
  19762. if (token_is(token_t::e_lbracket))
  19763. {
  19764. if (token_is(token_t::e_rbracket))
  19765. {
  19766. if (
  19767. !function->allow_zero_parameters() &&
  19768. !tc .allow_zero_parameters()
  19769. )
  19770. {
  19771. set_error(
  19772. make_error(parser_error::e_syntax,
  19773. current_token(),
  19774. "ERR126 - Zero parameter call to generic function: "
  19775. + function_name + " not allowed",
  19776. exprtk_error_location));
  19777. return false;
  19778. }
  19779. }
  19780. else
  19781. {
  19782. for ( ; ; )
  19783. {
  19784. expression_node_ptr arg = parse_expression();
  19785. if (0 == arg)
  19786. return false;
  19787. if (is_ivector_node(arg))
  19788. param_type_list += 'V';
  19789. else if (is_generally_string_node(arg))
  19790. param_type_list += 'S';
  19791. else // Everything else is a scalar returning expression
  19792. param_type_list += 'T';
  19793. arg_list.push_back(arg);
  19794. if (token_is(token_t::e_rbracket))
  19795. break;
  19796. else if (!token_is(token_t::e_comma))
  19797. {
  19798. set_error(
  19799. make_error(parser_error::e_syntax,
  19800. current_token(),
  19801. "ERR127 - Expected ',' for call to string function: " + function_name,
  19802. exprtk_error_location));
  19803. return false;
  19804. }
  19805. }
  19806. }
  19807. return true;
  19808. }
  19809. else
  19810. return false;
  19811. }
  19812. #ifndef exprtk_disable_string_capabilities
  19813. inline expression_node_ptr parse_string_function_call(igeneric_function<T>* function, const std::string& function_name)
  19814. {
  19815. // Move pass the function name
  19816. next_token();
  19817. std::string param_type_list;
  19818. type_checker tc((*this), function_name, function->parameter_sequence, type_checker::e_string);
  19819. if (
  19820. (!function->parameter_sequence.empty()) &&
  19821. (0 == tc.paramseq_count())
  19822. )
  19823. {
  19824. return error_node();
  19825. }
  19826. std::vector<expression_node_ptr> arg_list;
  19827. scoped_vec_delete<expression_node_t> sdd((*this),arg_list);
  19828. if (!parse_igeneric_function_params(param_type_list, arg_list, function_name, function, tc))
  19829. {
  19830. return error_node();
  19831. }
  19832. std::size_t param_seq_index = 0;
  19833. if (!tc.verify(param_type_list, param_seq_index))
  19834. {
  19835. set_error(
  19836. make_error(parser_error::e_syntax,
  19837. current_token(),
  19838. "ERR128 - Invalid input parameter sequence for call to string function: " + function_name,
  19839. exprtk_error_location));
  19840. return error_node();
  19841. }
  19842. expression_node_ptr result = error_node();
  19843. if (tc.paramseq_count() <= 1)
  19844. result = expression_generator_
  19845. .string_function_call(function, arg_list);
  19846. else
  19847. result = expression_generator_
  19848. .string_function_call(function, arg_list, param_seq_index);
  19849. sdd.delete_ptr = (0 == result);
  19850. return result;
  19851. }
  19852. inline expression_node_ptr parse_overload_function_call(igeneric_function<T>* function, const std::string& function_name)
  19853. {
  19854. // Move pass the function name
  19855. next_token();
  19856. std::string param_type_list;
  19857. type_checker tc((*this), function_name, function->parameter_sequence, type_checker::e_overload);
  19858. if (
  19859. (!function->parameter_sequence.empty()) &&
  19860. (0 == tc.paramseq_count())
  19861. )
  19862. {
  19863. return error_node();
  19864. }
  19865. std::vector<expression_node_ptr> arg_list;
  19866. scoped_vec_delete<expression_node_t> sdd((*this),arg_list);
  19867. if (!parse_igeneric_function_params(param_type_list, arg_list, function_name, function, tc))
  19868. {
  19869. return error_node();
  19870. }
  19871. std::size_t param_seq_index = 0;
  19872. if (!tc.verify(param_type_list, param_seq_index))
  19873. {
  19874. set_error(
  19875. make_error(parser_error::e_syntax,
  19876. current_token(),
  19877. "ERR129 - Invalid input parameter sequence for call to overloaded function: " + function_name,
  19878. exprtk_error_location));
  19879. return error_node();
  19880. }
  19881. expression_node_ptr result = error_node();
  19882. if (type_checker::e_numeric == tc.return_type(param_seq_index))
  19883. {
  19884. if (tc.paramseq_count() <= 1)
  19885. result = expression_generator_
  19886. .generic_function_call(function, arg_list);
  19887. else
  19888. result = expression_generator_
  19889. .generic_function_call(function, arg_list, param_seq_index);
  19890. }
  19891. else if (type_checker::e_string == tc.return_type(param_seq_index))
  19892. {
  19893. if (tc.paramseq_count() <= 1)
  19894. result = expression_generator_
  19895. .string_function_call(function, arg_list);
  19896. else
  19897. result = expression_generator_
  19898. .string_function_call(function, arg_list, param_seq_index);
  19899. }
  19900. else
  19901. {
  19902. set_error(
  19903. make_error(parser_error::e_syntax,
  19904. current_token(),
  19905. "ERR130 - Invalid return type for call to overloaded function: " + function_name,
  19906. exprtk_error_location));
  19907. }
  19908. sdd.delete_ptr = (0 == result);
  19909. return result;
  19910. }
  19911. #endif
  19912. template <typename Type, std::size_t NumberOfParameters>
  19913. struct parse_special_function_impl
  19914. {
  19915. static inline expression_node_ptr process(parser<Type>& p, const details::operator_type opt_type, const std::string& sf_name)
  19916. {
  19917. expression_node_ptr branch[NumberOfParameters];
  19918. expression_node_ptr result = error_node();
  19919. std::fill_n(branch,NumberOfParameters,reinterpret_cast<expression_node_ptr>(0));
  19920. scoped_delete<expression_node_t,NumberOfParameters> sd(p,branch);
  19921. p.next_token();
  19922. if (!p.token_is(token_t::e_lbracket))
  19923. {
  19924. p.set_error(
  19925. make_error(parser_error::e_syntax,
  19926. p.current_token(),
  19927. "ERR131 - Expected '(' for special function '" + sf_name + "'",
  19928. exprtk_error_location));
  19929. return error_node();
  19930. }
  19931. for (std::size_t i = 0; i < NumberOfParameters; ++i)
  19932. {
  19933. branch[i] = p.parse_expression();
  19934. if (0 == branch[i])
  19935. {
  19936. return p.error_node();
  19937. }
  19938. else if (i < (NumberOfParameters - 1))
  19939. {
  19940. if (!p.token_is(token_t::e_comma))
  19941. {
  19942. p.set_error(
  19943. make_error(parser_error::e_syntax,
  19944. p.current_token(),
  19945. "ERR132 - Expected ',' before next parameter of special function '" + sf_name + "'",
  19946. exprtk_error_location));
  19947. return p.error_node();
  19948. }
  19949. }
  19950. }
  19951. if (!p.token_is(token_t::e_rbracket))
  19952. {
  19953. p.set_error(
  19954. make_error(parser_error::e_syntax,
  19955. p.current_token(),
  19956. "ERR133 - Invalid number of parameters for special function '" + sf_name + "'",
  19957. exprtk_error_location));
  19958. return p.error_node();
  19959. }
  19960. else
  19961. result = p.expression_generator_.special_function(opt_type,branch);
  19962. sd.delete_ptr = (0 == result);
  19963. return result;
  19964. }
  19965. };
  19966. inline expression_node_ptr parse_special_function()
  19967. {
  19968. const std::string sf_name = current_token().value;
  19969. // Expect: $fDD(expr0,expr1,expr2) or $fDD(expr0,expr1,expr2,expr3)
  19970. if (
  19971. !details::is_digit(sf_name[2]) ||
  19972. !details::is_digit(sf_name[3])
  19973. )
  19974. {
  19975. set_error(
  19976. make_error(parser_error::e_token,
  19977. current_token(),
  19978. "ERR134 - Invalid special function[1]: " + sf_name,
  19979. exprtk_error_location));
  19980. return error_node();
  19981. }
  19982. const int id = (sf_name[2] - '0') * 10 +
  19983. (sf_name[3] - '0');
  19984. if (id >= details::e_sffinal)
  19985. {
  19986. set_error(
  19987. make_error(parser_error::e_token,
  19988. current_token(),
  19989. "ERR135 - Invalid special function[2]: " + sf_name,
  19990. exprtk_error_location));
  19991. return error_node();
  19992. }
  19993. const int sf_3_to_4 = details::e_sf48;
  19994. const details::operator_type opt_type = details::operator_type(id + 1000);
  19995. const std::size_t NumberOfParameters = (id < (sf_3_to_4 - 1000)) ? 3U : 4U;
  19996. switch (NumberOfParameters)
  19997. {
  19998. case 3 : return parse_special_function_impl<T,3>::process((*this), opt_type, sf_name);
  19999. case 4 : return parse_special_function_impl<T,4>::process((*this), opt_type, sf_name);
  20000. default : return error_node();
  20001. }
  20002. }
  20003. inline expression_node_ptr parse_null_statement()
  20004. {
  20005. next_token();
  20006. return node_allocator_.allocate<details::null_node<T> >();
  20007. }
  20008. #ifndef exprtk_disable_break_continue
  20009. inline expression_node_ptr parse_break_statement()
  20010. {
  20011. if (state_.parsing_break_stmt)
  20012. {
  20013. set_error(
  20014. make_error(parser_error::e_syntax,
  20015. current_token(),
  20016. "ERR136 - Break call within a break call is not allowed",
  20017. exprtk_error_location));
  20018. return error_node();
  20019. }
  20020. scoped_bool_negator sbn(state_.parsing_break_stmt);
  20021. if (!brkcnt_list_.empty())
  20022. {
  20023. next_token();
  20024. brkcnt_list_.front() = true;
  20025. expression_node_ptr return_expr = error_node();
  20026. if (token_is(token_t::e_lsqrbracket))
  20027. {
  20028. if (0 == (return_expr = parse_expression()))
  20029. {
  20030. set_error(
  20031. make_error(parser_error::e_syntax,
  20032. current_token(),
  20033. "ERR137 - Failed to parse return expression for 'break' statement",
  20034. exprtk_error_location));
  20035. return error_node();
  20036. }
  20037. else if (!token_is(token_t::e_rsqrbracket))
  20038. {
  20039. set_error(
  20040. make_error(parser_error::e_syntax,
  20041. current_token(),
  20042. "ERR138 - Expected ']' at the completion of break's return expression",
  20043. exprtk_error_location));
  20044. free_node(node_allocator_,return_expr);
  20045. return error_node();
  20046. }
  20047. }
  20048. state_.activate_side_effect("parse_break_statement()");
  20049. return node_allocator_.allocate<details::break_node<T> >(return_expr);
  20050. }
  20051. else
  20052. {
  20053. set_error(
  20054. make_error(parser_error::e_syntax,
  20055. current_token(),
  20056. "ERR139 - Invalid use of 'break', allowed only in the scope of a loop",
  20057. exprtk_error_location));
  20058. }
  20059. return error_node();
  20060. }
  20061. inline expression_node_ptr parse_continue_statement()
  20062. {
  20063. if (!brkcnt_list_.empty())
  20064. {
  20065. next_token();
  20066. brkcnt_list_.front() = true;
  20067. state_.activate_side_effect("parse_continue_statement()");
  20068. return node_allocator_.allocate<details::continue_node<T> >();
  20069. }
  20070. else
  20071. {
  20072. set_error(
  20073. make_error(parser_error::e_syntax,
  20074. current_token(),
  20075. "ERR140 - Invalid use of 'continue', allowed only in the scope of a loop",
  20076. exprtk_error_location));
  20077. return error_node();
  20078. }
  20079. }
  20080. #endif
  20081. inline expression_node_ptr parse_define_vector_statement(const std::string& vec_name)
  20082. {
  20083. expression_node_ptr size_expr = error_node();
  20084. if (!token_is(token_t::e_lsqrbracket))
  20085. {
  20086. set_error(
  20087. make_error(parser_error::e_syntax,
  20088. current_token(),
  20089. "ERR141 - Expected '[' as part of vector size definition",
  20090. exprtk_error_location));
  20091. return error_node();
  20092. }
  20093. else if (0 == (size_expr = parse_expression()))
  20094. {
  20095. set_error(
  20096. make_error(parser_error::e_syntax,
  20097. current_token(),
  20098. "ERR142 - Failed to determine size of vector '" + vec_name + "'",
  20099. exprtk_error_location));
  20100. return error_node();
  20101. }
  20102. else if (!is_constant_node(size_expr))
  20103. {
  20104. free_node(node_allocator_,size_expr);
  20105. set_error(
  20106. make_error(parser_error::e_syntax,
  20107. current_token(),
  20108. "ERR143 - Expected a literal number as size of vector '" + vec_name + "'",
  20109. exprtk_error_location));
  20110. return error_node();
  20111. }
  20112. const T vector_size = size_expr->value();
  20113. free_node(node_allocator_,size_expr);
  20114. const T max_vector_size = T(2000000000.0);
  20115. if (
  20116. (vector_size <= T(0)) ||
  20117. std::not_equal_to<T>()
  20118. (T(0),vector_size - details::numeric::trunc(vector_size)) ||
  20119. (vector_size > max_vector_size)
  20120. )
  20121. {
  20122. set_error(
  20123. make_error(parser_error::e_syntax,
  20124. current_token(),
  20125. "ERR144 - Invalid vector size. Must be an integer in the range [0,2e9], size: " +
  20126. details::to_str(details::numeric::to_int32(vector_size)),
  20127. exprtk_error_location));
  20128. return error_node();
  20129. }
  20130. std::vector<expression_node_ptr> vec_initilizer_list;
  20131. scoped_vec_delete<expression_node_t> svd((*this),vec_initilizer_list);
  20132. bool single_value_initialiser = false;
  20133. bool vec_to_vec_initialiser = false;
  20134. bool null_initialisation = false;
  20135. if (!token_is(token_t::e_rsqrbracket))
  20136. {
  20137. set_error(
  20138. make_error(parser_error::e_syntax,
  20139. current_token(),
  20140. "ERR145 - Expected ']' as part of vector size definition",
  20141. exprtk_error_location));
  20142. return error_node();
  20143. }
  20144. else if (!token_is(token_t::e_eof))
  20145. {
  20146. if (!token_is(token_t::e_assign))
  20147. {
  20148. set_error(
  20149. make_error(parser_error::e_syntax,
  20150. current_token(),
  20151. "ERR146 - Expected ':=' as part of vector definition",
  20152. exprtk_error_location));
  20153. return error_node();
  20154. }
  20155. else if (token_is(token_t::e_lsqrbracket))
  20156. {
  20157. expression_node_ptr initialiser = parse_expression();
  20158. if (0 == initialiser)
  20159. {
  20160. set_error(
  20161. make_error(parser_error::e_syntax,
  20162. current_token(),
  20163. "ERR147 - Failed to parse single vector initialiser",
  20164. exprtk_error_location));
  20165. return error_node();
  20166. }
  20167. vec_initilizer_list.push_back(initialiser);
  20168. if (!token_is(token_t::e_rsqrbracket))
  20169. {
  20170. set_error(
  20171. make_error(parser_error::e_syntax,
  20172. current_token(),
  20173. "ERR148 - Expected ']' to close single value vector initialiser",
  20174. exprtk_error_location));
  20175. return error_node();
  20176. }
  20177. single_value_initialiser = true;
  20178. }
  20179. else if (!token_is(token_t::e_lcrlbracket))
  20180. {
  20181. expression_node_ptr initialiser = error_node();
  20182. // Is this a vector to vector assignment and initialisation?
  20183. if (token_t::e_symbol == current_token().type)
  20184. {
  20185. // Is it a locally defined vector?
  20186. scope_element& se = sem_.get_active_element(current_token().value);
  20187. if (scope_element::e_vector == se.type)
  20188. {
  20189. if (0 != (initialiser = parse_expression()))
  20190. vec_initilizer_list.push_back(initialiser);
  20191. else
  20192. return error_node();
  20193. }
  20194. // Are we dealing with a user defined vector?
  20195. else if (symtab_store_.is_vector(current_token().value))
  20196. {
  20197. lodge_symbol(current_token().value, e_st_vector);
  20198. if (0 != (initialiser = parse_expression()))
  20199. vec_initilizer_list.push_back(initialiser);
  20200. else
  20201. return error_node();
  20202. }
  20203. // Are we dealing with a null initialisation vector definition?
  20204. else if (token_is(token_t::e_symbol,"null"))
  20205. null_initialisation = true;
  20206. }
  20207. if (!null_initialisation)
  20208. {
  20209. if (0 == initialiser)
  20210. {
  20211. set_error(
  20212. make_error(parser_error::e_syntax,
  20213. current_token(),
  20214. "ERR149 - Expected '{' as part of vector initialiser list",
  20215. exprtk_error_location));
  20216. return error_node();
  20217. }
  20218. else
  20219. vec_to_vec_initialiser = true;
  20220. }
  20221. }
  20222. else if (!token_is(token_t::e_rcrlbracket))
  20223. {
  20224. for ( ; ; )
  20225. {
  20226. expression_node_ptr initialiser = parse_expression();
  20227. if (0 == initialiser)
  20228. {
  20229. set_error(
  20230. make_error(parser_error::e_syntax,
  20231. current_token(),
  20232. "ERR150 - Expected '{' as part of vector initialiser list",
  20233. exprtk_error_location));
  20234. return error_node();
  20235. }
  20236. else
  20237. vec_initilizer_list.push_back(initialiser);
  20238. if (token_is(token_t::e_rcrlbracket))
  20239. break;
  20240. const bool is_next_close = peek_token_is(token_t::e_rcrlbracket);
  20241. if (!token_is(token_t::e_comma) && is_next_close)
  20242. {
  20243. set_error(
  20244. make_error(parser_error::e_syntax,
  20245. current_token(),
  20246. "ERR151 - Expected ',' between vector initialisers",
  20247. exprtk_error_location));
  20248. return error_node();
  20249. }
  20250. if (token_is(token_t::e_rcrlbracket))
  20251. break;
  20252. }
  20253. }
  20254. if (
  20255. !token_is(token_t::e_rbracket , prsrhlpr_t::e_hold) &&
  20256. !token_is(token_t::e_rcrlbracket, prsrhlpr_t::e_hold) &&
  20257. !token_is(token_t::e_rsqrbracket, prsrhlpr_t::e_hold)
  20258. )
  20259. {
  20260. if (!token_is(token_t::e_eof))
  20261. {
  20262. set_error(
  20263. make_error(parser_error::e_syntax,
  20264. current_token(),
  20265. "ERR152 - Expected ';' at end of vector definition",
  20266. exprtk_error_location));
  20267. return error_node();
  20268. }
  20269. }
  20270. if (vec_initilizer_list.size() > vector_size)
  20271. {
  20272. set_error(
  20273. make_error(parser_error::e_syntax,
  20274. current_token(),
  20275. "ERR153 - Initialiser list larger than the number of elements in the vector: '" + vec_name + "'",
  20276. exprtk_error_location));
  20277. return error_node();
  20278. }
  20279. }
  20280. typename symbol_table_t::vector_holder_ptr vec_holder = typename symbol_table_t::vector_holder_ptr(0);
  20281. const std::size_t vec_size = static_cast<std::size_t>(details::numeric::to_int32(vector_size));
  20282. scope_element& se = sem_.get_element(vec_name);
  20283. if (se.name == vec_name)
  20284. {
  20285. if (se.active)
  20286. {
  20287. set_error(
  20288. make_error(parser_error::e_syntax,
  20289. current_token(),
  20290. "ERR154 - Illegal redefinition of local vector: '" + vec_name + "'",
  20291. exprtk_error_location));
  20292. return error_node();
  20293. }
  20294. else if (
  20295. (se.size == vec_size) &&
  20296. (scope_element::e_vector == se.type)
  20297. )
  20298. {
  20299. vec_holder = se.vec_node;
  20300. se.active = true;
  20301. se.depth = state_.scope_depth;
  20302. se.ref_count++;
  20303. }
  20304. }
  20305. if (0 == vec_holder)
  20306. {
  20307. scope_element nse;
  20308. nse.name = vec_name;
  20309. nse.active = true;
  20310. nse.ref_count = 1;
  20311. nse.type = scope_element::e_vector;
  20312. nse.depth = state_.scope_depth;
  20313. nse.size = vec_size;
  20314. nse.data = new T[vec_size];
  20315. nse.vec_node = new typename scope_element::vector_holder_t((T*)(nse.data),nse.size);
  20316. if (!sem_.add_element(nse))
  20317. {
  20318. set_error(
  20319. make_error(parser_error::e_syntax,
  20320. current_token(),
  20321. "ERR155 - Failed to add new local vector '" + vec_name + "' to SEM",
  20322. exprtk_error_location));
  20323. sem_.free_element(nse);
  20324. return error_node();
  20325. }
  20326. vec_holder = nse.vec_node;
  20327. exprtk_debug(("parse_define_vector_statement() - INFO - Added new local vector: %s[%d]\n",
  20328. nse.name.c_str(),
  20329. static_cast<int>(nse.size)));
  20330. }
  20331. state_.activate_side_effect("parse_define_vector_statement()");
  20332. lodge_symbol(vec_name, e_st_local_vector);
  20333. expression_node_ptr result = error_node();
  20334. if (null_initialisation)
  20335. result = expression_generator_(T(0.0));
  20336. else if (vec_to_vec_initialiser)
  20337. {
  20338. expression_node_ptr vec_node = node_allocator_.allocate<vector_node_t>(vec_holder);
  20339. result = expression_generator_(
  20340. details::e_assign,
  20341. vec_node,
  20342. vec_initilizer_list[0]);
  20343. }
  20344. else
  20345. result = node_allocator_
  20346. .allocate<details::vector_assignment_node<T> >(
  20347. (*vec_holder)[0],
  20348. vec_size,
  20349. vec_initilizer_list,
  20350. single_value_initialiser);
  20351. svd.delete_ptr = (0 == result);
  20352. return result;
  20353. }
  20354. #ifndef exprtk_disable_string_capabilities
  20355. inline expression_node_ptr parse_define_string_statement(const std::string& str_name, expression_node_ptr initialisation_expression)
  20356. {
  20357. stringvar_node_t* str_node = reinterpret_cast<stringvar_node_t*>(0);
  20358. scope_element& se = sem_.get_element(str_name);
  20359. if (se.name == str_name)
  20360. {
  20361. if (se.active)
  20362. {
  20363. set_error(
  20364. make_error(parser_error::e_syntax,
  20365. current_token(),
  20366. "ERR156 - Illegal redefinition of local variable: '" + str_name + "'",
  20367. exprtk_error_location));
  20368. free_node(node_allocator_,initialisation_expression);
  20369. return error_node();
  20370. }
  20371. else if (scope_element::e_string == se.type)
  20372. {
  20373. str_node = se.str_node;
  20374. se.active = true;
  20375. se.depth = state_.scope_depth;
  20376. se.ref_count++;
  20377. }
  20378. }
  20379. if (0 == str_node)
  20380. {
  20381. scope_element nse;
  20382. nse.name = str_name;
  20383. nse.active = true;
  20384. nse.ref_count = 1;
  20385. nse.type = scope_element::e_string;
  20386. nse.depth = state_.scope_depth;
  20387. nse.data = new std::string;
  20388. nse.str_node = new stringvar_node_t(*(std::string*)(nse.data));
  20389. if (!sem_.add_element(nse))
  20390. {
  20391. set_error(
  20392. make_error(parser_error::e_syntax,
  20393. current_token(),
  20394. "ERR157 - Failed to add new local string variable '" + str_name + "' to SEM",
  20395. exprtk_error_location));
  20396. free_node(node_allocator_,initialisation_expression);
  20397. sem_.free_element(nse);
  20398. return error_node();
  20399. }
  20400. str_node = nse.str_node;
  20401. exprtk_debug(("parse_define_string_statement() - INFO - Added new local string variable: %s\n",nse.name.c_str()));
  20402. }
  20403. lodge_symbol(str_name, e_st_local_string);
  20404. state_.activate_side_effect("parse_define_string_statement()");
  20405. expression_node_ptr branch[2] = {0};
  20406. branch[0] = str_node;
  20407. branch[1] = initialisation_expression;
  20408. return expression_generator_(details::e_assign,branch);
  20409. }
  20410. #else
  20411. inline expression_node_ptr parse_define_string_statement(const std::string&, expression_node_ptr)
  20412. {
  20413. return error_node();
  20414. }
  20415. #endif
  20416. inline bool local_variable_is_shadowed(const std::string& symbol)
  20417. {
  20418. const scope_element& se = sem_.get_element(symbol);
  20419. return (se.name == symbol) && se.active;
  20420. }
  20421. inline expression_node_ptr parse_define_var_statement()
  20422. {
  20423. if (settings_.vardef_disabled())
  20424. {
  20425. set_error(
  20426. make_error(parser_error::e_syntax,
  20427. current_token(),
  20428. "ERR158 - Illegal variable definition",
  20429. exprtk_error_location));
  20430. return error_node();
  20431. }
  20432. else if (!details::imatch(current_token().value,"var"))
  20433. {
  20434. return error_node();
  20435. }
  20436. else
  20437. next_token();
  20438. const std::string var_name = current_token().value;
  20439. expression_node_ptr initialisation_expression = error_node();
  20440. if (!token_is(token_t::e_symbol))
  20441. {
  20442. set_error(
  20443. make_error(parser_error::e_syntax,
  20444. current_token(),
  20445. "ERR159 - Expected a symbol for variable definition",
  20446. exprtk_error_location));
  20447. return error_node();
  20448. }
  20449. else if (details::is_reserved_symbol(var_name))
  20450. {
  20451. set_error(
  20452. make_error(parser_error::e_syntax,
  20453. current_token(),
  20454. "ERR160 - Illegal redefinition of reserved keyword: '" + var_name + "'",
  20455. exprtk_error_location));
  20456. return error_node();
  20457. }
  20458. else if (symtab_store_.symbol_exists(var_name))
  20459. {
  20460. set_error(
  20461. make_error(parser_error::e_syntax,
  20462. current_token(),
  20463. "ERR161 - Illegal redefinition of variable '" + var_name + "'",
  20464. exprtk_error_location));
  20465. return error_node();
  20466. }
  20467. else if (local_variable_is_shadowed(var_name))
  20468. {
  20469. set_error(
  20470. make_error(parser_error::e_syntax,
  20471. current_token(),
  20472. "ERR162 - Illegal redefinition of local variable: '" + var_name + "'",
  20473. exprtk_error_location));
  20474. return error_node();
  20475. }
  20476. else if (token_is(token_t::e_lsqrbracket,prsrhlpr_t::e_hold))
  20477. {
  20478. return parse_define_vector_statement(var_name);
  20479. }
  20480. else if (token_is(token_t::e_lcrlbracket,prsrhlpr_t::e_hold))
  20481. {
  20482. return parse_uninitialised_var_statement(var_name);
  20483. }
  20484. else if (token_is(token_t::e_assign))
  20485. {
  20486. if (0 == (initialisation_expression = parse_expression()))
  20487. {
  20488. set_error(
  20489. make_error(parser_error::e_syntax,
  20490. current_token(),
  20491. "ERR163 - Failed to parse initialisation expression",
  20492. exprtk_error_location));
  20493. return error_node();
  20494. }
  20495. }
  20496. if (
  20497. !token_is(token_t::e_rbracket , prsrhlpr_t::e_hold) &&
  20498. !token_is(token_t::e_rcrlbracket, prsrhlpr_t::e_hold) &&
  20499. !token_is(token_t::e_rsqrbracket, prsrhlpr_t::e_hold)
  20500. )
  20501. {
  20502. if (!token_is(token_t::e_eof,prsrhlpr_t::e_hold))
  20503. {
  20504. set_error(
  20505. make_error(parser_error::e_syntax,
  20506. current_token(),
  20507. "ERR164 - Expected ';' after variable definition",
  20508. exprtk_error_location));
  20509. free_node(node_allocator_,initialisation_expression);
  20510. return error_node();
  20511. }
  20512. }
  20513. if (
  20514. (0 != initialisation_expression) &&
  20515. details::is_generally_string_node(initialisation_expression)
  20516. )
  20517. {
  20518. return parse_define_string_statement(var_name,initialisation_expression);
  20519. }
  20520. expression_node_ptr var_node = reinterpret_cast<expression_node_ptr>(0);
  20521. scope_element& se = sem_.get_element(var_name);
  20522. if (se.name == var_name)
  20523. {
  20524. if (se.active)
  20525. {
  20526. set_error(
  20527. make_error(parser_error::e_syntax,
  20528. current_token(),
  20529. "ERR165 - Illegal redefinition of local variable: '" + var_name + "'",
  20530. exprtk_error_location));
  20531. free_node(node_allocator_, initialisation_expression);
  20532. return error_node();
  20533. }
  20534. else if (scope_element::e_variable == se.type)
  20535. {
  20536. var_node = se.var_node;
  20537. se.active = true;
  20538. se.depth = state_.scope_depth;
  20539. se.ref_count++;
  20540. }
  20541. }
  20542. if (0 == var_node)
  20543. {
  20544. scope_element nse;
  20545. nse.name = var_name;
  20546. nse.active = true;
  20547. nse.ref_count = 1;
  20548. nse.type = scope_element::e_variable;
  20549. nse.depth = state_.scope_depth;
  20550. nse.data = new T(T(0));
  20551. nse.var_node = node_allocator_.allocate<variable_node_t>(*(T*)(nse.data));
  20552. if (!sem_.add_element(nse))
  20553. {
  20554. set_error(
  20555. make_error(parser_error::e_syntax,
  20556. current_token(),
  20557. "ERR166 - Failed to add new local variable '" + var_name + "' to SEM",
  20558. exprtk_error_location));
  20559. free_node(node_allocator_, initialisation_expression);
  20560. sem_.free_element(nse);
  20561. return error_node();
  20562. }
  20563. var_node = nse.var_node;
  20564. exprtk_debug(("parse_define_var_statement() - INFO - Added new local variable: %s\n",nse.name.c_str()));
  20565. }
  20566. state_.activate_side_effect("parse_define_var_statement()");
  20567. lodge_symbol(var_name, e_st_local_variable);
  20568. expression_node_ptr branch[2] = {0};
  20569. branch[0] = var_node;
  20570. branch[1] = initialisation_expression ? initialisation_expression : expression_generator_(T(0));
  20571. return expression_generator_(details::e_assign,branch);
  20572. }
  20573. inline expression_node_ptr parse_uninitialised_var_statement(const std::string& var_name)
  20574. {
  20575. if (
  20576. !token_is(token_t::e_lcrlbracket) ||
  20577. !token_is(token_t::e_rcrlbracket)
  20578. )
  20579. {
  20580. set_error(
  20581. make_error(parser_error::e_syntax,
  20582. current_token(),
  20583. "ERR167 - Expected a '{}' for uninitialised var definition",
  20584. exprtk_error_location));
  20585. return error_node();
  20586. }
  20587. else if (!token_is(token_t::e_eof,prsrhlpr_t::e_hold))
  20588. {
  20589. set_error(
  20590. make_error(parser_error::e_syntax,
  20591. current_token(),
  20592. "ERR168 - Expected ';' after uninitialised variable definition",
  20593. exprtk_error_location));
  20594. return error_node();
  20595. }
  20596. expression_node_ptr var_node = reinterpret_cast<expression_node_ptr>(0);
  20597. scope_element& se = sem_.get_element(var_name);
  20598. if (se.name == var_name)
  20599. {
  20600. if (se.active)
  20601. {
  20602. set_error(
  20603. make_error(parser_error::e_syntax,
  20604. current_token(),
  20605. "ERR169 - Illegal redefinition of local variable: '" + var_name + "'",
  20606. exprtk_error_location));
  20607. return error_node();
  20608. }
  20609. else if (scope_element::e_variable == se.type)
  20610. {
  20611. var_node = se.var_node;
  20612. se.active = true;
  20613. se.ref_count++;
  20614. }
  20615. }
  20616. if (0 == var_node)
  20617. {
  20618. scope_element nse;
  20619. nse.name = var_name;
  20620. nse.active = true;
  20621. nse.ref_count = 1;
  20622. nse.type = scope_element::e_variable;
  20623. nse.depth = state_.scope_depth;
  20624. nse.ip_index = sem_.next_ip_index();
  20625. nse.data = new T(T(0));
  20626. nse.var_node = node_allocator_.allocate<variable_node_t>(*(T*)(nse.data));
  20627. if (!sem_.add_element(nse))
  20628. {
  20629. set_error(
  20630. make_error(parser_error::e_syntax,
  20631. current_token(),
  20632. "ERR170 - Failed to add new local variable '" + var_name + "' to SEM",
  20633. exprtk_error_location));
  20634. sem_.free_element(nse);
  20635. return error_node();
  20636. }
  20637. exprtk_debug(("parse_uninitialised_var_statement() - INFO - Added new local variable: %s\n",
  20638. nse.name.c_str()));
  20639. }
  20640. lodge_symbol(var_name, e_st_local_variable);
  20641. state_.activate_side_effect("parse_uninitialised_var_statement()");
  20642. return expression_generator_(T(0));
  20643. }
  20644. inline expression_node_ptr parse_swap_statement()
  20645. {
  20646. if (!details::imatch(current_token().value,"swap"))
  20647. {
  20648. return error_node();
  20649. }
  20650. else
  20651. next_token();
  20652. if (!token_is(token_t::e_lbracket))
  20653. {
  20654. set_error(
  20655. make_error(parser_error::e_syntax,
  20656. current_token(),
  20657. "ERR171 - Expected '(' at start of swap statement",
  20658. exprtk_error_location));
  20659. return error_node();
  20660. }
  20661. expression_node_ptr variable0 = error_node();
  20662. expression_node_ptr variable1 = error_node();
  20663. bool variable0_generated = false;
  20664. bool variable1_generated = false;
  20665. const std::string var0_name = current_token().value;
  20666. if (!token_is(token_t::e_symbol,prsrhlpr_t::e_hold))
  20667. {
  20668. set_error(
  20669. make_error(parser_error::e_syntax,
  20670. current_token(),
  20671. "ERR172 - Expected a symbol for variable or vector element definition",
  20672. exprtk_error_location));
  20673. return error_node();
  20674. }
  20675. else if (peek_token_is(token_t::e_lsqrbracket))
  20676. {
  20677. if (0 == (variable0 = parse_vector()))
  20678. {
  20679. set_error(
  20680. make_error(parser_error::e_syntax,
  20681. current_token(),
  20682. "ERR173 - First parameter to swap is an invalid vector element: '" + var0_name + "'",
  20683. exprtk_error_location));
  20684. return error_node();
  20685. }
  20686. variable0_generated = true;
  20687. }
  20688. else
  20689. {
  20690. if (symtab_store_.is_variable(var0_name))
  20691. {
  20692. variable0 = symtab_store_.get_variable(var0_name);
  20693. }
  20694. scope_element& se = sem_.get_element(var0_name);
  20695. if (
  20696. (se.active) &&
  20697. (se.name == var0_name) &&
  20698. (scope_element::e_variable == se.type)
  20699. )
  20700. {
  20701. variable0 = se.var_node;
  20702. }
  20703. lodge_symbol(var0_name, e_st_variable);
  20704. if (0 == variable0)
  20705. {
  20706. set_error(
  20707. make_error(parser_error::e_syntax,
  20708. current_token(),
  20709. "ERR174 - First parameter to swap is an invalid variable: '" + var0_name + "'",
  20710. exprtk_error_location));
  20711. return error_node();
  20712. }
  20713. else
  20714. next_token();
  20715. }
  20716. if (!token_is(token_t::e_comma))
  20717. {
  20718. set_error(
  20719. make_error(parser_error::e_syntax,
  20720. current_token(),
  20721. "ERR175 - Expected ',' between parameters to swap",
  20722. exprtk_error_location));
  20723. if (variable0_generated)
  20724. {
  20725. free_node(node_allocator_,variable0);
  20726. }
  20727. return error_node();
  20728. }
  20729. const std::string var1_name = current_token().value;
  20730. if (!token_is(token_t::e_symbol,prsrhlpr_t::e_hold))
  20731. {
  20732. set_error(
  20733. make_error(parser_error::e_syntax,
  20734. current_token(),
  20735. "ERR176 - Expected a symbol for variable or vector element definition",
  20736. exprtk_error_location));
  20737. if (variable0_generated)
  20738. {
  20739. free_node(node_allocator_,variable0);
  20740. }
  20741. return error_node();
  20742. }
  20743. else if (peek_token_is(token_t::e_lsqrbracket))
  20744. {
  20745. if (0 == (variable1 = parse_vector()))
  20746. {
  20747. set_error(
  20748. make_error(parser_error::e_syntax,
  20749. current_token(),
  20750. "ERR177 - Second parameter to swap is an invalid vector element: '" + var1_name + "'",
  20751. exprtk_error_location));
  20752. if (variable0_generated)
  20753. {
  20754. free_node(node_allocator_,variable0);
  20755. }
  20756. return error_node();
  20757. }
  20758. variable1_generated = true;
  20759. }
  20760. else
  20761. {
  20762. if (symtab_store_.is_variable(var1_name))
  20763. {
  20764. variable1 = symtab_store_.get_variable(var1_name);
  20765. }
  20766. scope_element& se = sem_.get_element(var1_name);
  20767. if (
  20768. (se.active) &&
  20769. (se.name == var1_name) &&
  20770. (scope_element::e_variable == se.type)
  20771. )
  20772. {
  20773. variable1 = se.var_node;
  20774. }
  20775. lodge_symbol(var1_name, e_st_variable);
  20776. if (0 == variable1)
  20777. {
  20778. set_error(
  20779. make_error(parser_error::e_syntax,
  20780. current_token(),
  20781. "ERR178 - Second parameter to swap is an invalid variable: '" + var1_name + "'",
  20782. exprtk_error_location));
  20783. if (variable0_generated)
  20784. {
  20785. free_node(node_allocator_,variable0);
  20786. }
  20787. return error_node();
  20788. }
  20789. else
  20790. next_token();
  20791. }
  20792. if (!token_is(token_t::e_rbracket))
  20793. {
  20794. set_error(
  20795. make_error(parser_error::e_syntax,
  20796. current_token(),
  20797. "ERR179 - Expected ')' at end of swap statement",
  20798. exprtk_error_location));
  20799. if (variable0_generated)
  20800. {
  20801. free_node(node_allocator_,variable0);
  20802. }
  20803. if (variable1_generated)
  20804. {
  20805. free_node(node_allocator_,variable1);
  20806. }
  20807. return error_node();
  20808. }
  20809. typedef details::variable_node<T>* variable_node_ptr;
  20810. variable_node_ptr v0 = variable_node_ptr(0);
  20811. variable_node_ptr v1 = variable_node_ptr(0);
  20812. expression_node_ptr result = error_node();
  20813. if (
  20814. (0 != (v0 = dynamic_cast<variable_node_ptr>(variable0))) &&
  20815. (0 != (v1 = dynamic_cast<variable_node_ptr>(variable1)))
  20816. )
  20817. {
  20818. result = node_allocator_.allocate<details::swap_node<T> >(v0, v1);
  20819. if (variable0_generated)
  20820. {
  20821. free_node(node_allocator_,variable0);
  20822. }
  20823. if (variable1_generated)
  20824. {
  20825. free_node(node_allocator_,variable1);
  20826. }
  20827. }
  20828. else
  20829. result = node_allocator_.allocate<details::swap_generic_node<T> >
  20830. (variable0, variable1);
  20831. state_.activate_side_effect("parse_swap_statement()");
  20832. return result;
  20833. }
  20834. #ifndef exprtk_disable_return_statement
  20835. inline expression_node_ptr parse_return_statement()
  20836. {
  20837. if (state_.parsing_return_stmt)
  20838. {
  20839. set_error(
  20840. make_error(parser_error::e_syntax,
  20841. current_token(),
  20842. "ERR180 - Return call within a return call is not allowed",
  20843. exprtk_error_location));
  20844. return error_node();
  20845. }
  20846. scoped_bool_negator sbn(state_.parsing_return_stmt);
  20847. std::vector<expression_node_ptr> arg_list;
  20848. scoped_vec_delete<expression_node_t> sdd((*this),arg_list);
  20849. if (!details::imatch(current_token().value,"return"))
  20850. {
  20851. return error_node();
  20852. }
  20853. else
  20854. next_token();
  20855. if (!token_is(token_t::e_lsqrbracket))
  20856. {
  20857. set_error(
  20858. make_error(parser_error::e_syntax,
  20859. current_token(),
  20860. "ERR181 - Expected '[' at start of return statement",
  20861. exprtk_error_location));
  20862. return error_node();
  20863. }
  20864. else if (!token_is(token_t::e_rsqrbracket))
  20865. {
  20866. for ( ; ; )
  20867. {
  20868. expression_node_ptr arg = parse_expression();
  20869. if (0 == arg)
  20870. return error_node();
  20871. arg_list.push_back(arg);
  20872. if (token_is(token_t::e_rsqrbracket))
  20873. break;
  20874. else if (!token_is(token_t::e_comma))
  20875. {
  20876. set_error(
  20877. make_error(parser_error::e_syntax,
  20878. current_token(),
  20879. "ERR182 - Expected ',' between values during call to return",
  20880. exprtk_error_location));
  20881. return error_node();
  20882. }
  20883. }
  20884. }
  20885. else if (settings_.zero_return_disabled())
  20886. {
  20887. set_error(
  20888. make_error(parser_error::e_syntax,
  20889. current_token(),
  20890. "ERR183 - Zero parameter return statement not allowed",
  20891. exprtk_error_location));
  20892. return error_node();
  20893. }
  20894. const lexer::token prev_token = current_token();
  20895. if (token_is(token_t::e_rsqrbracket))
  20896. {
  20897. if (!arg_list.empty())
  20898. {
  20899. set_error(
  20900. make_error(parser_error::e_syntax,
  20901. prev_token,
  20902. "ERR184 - Invalid ']' found during return call",
  20903. exprtk_error_location));
  20904. return error_node();
  20905. }
  20906. }
  20907. std::string ret_param_type_list;
  20908. for (std::size_t i = 0; i < arg_list.size(); ++i)
  20909. {
  20910. if (0 == arg_list[i])
  20911. return error_node();
  20912. else if (is_ivector_node(arg_list[i]))
  20913. ret_param_type_list += 'V';
  20914. else if (is_generally_string_node(arg_list[i]))
  20915. ret_param_type_list += 'S';
  20916. else
  20917. ret_param_type_list += 'T';
  20918. }
  20919. dec_.retparam_list_.push_back(ret_param_type_list);
  20920. expression_node_ptr result = expression_generator_.return_call(arg_list);
  20921. sdd.delete_ptr = (0 == result);
  20922. state_.return_stmt_present = true;
  20923. state_.activate_side_effect("parse_return_statement()");
  20924. return result;
  20925. }
  20926. #else
  20927. inline expression_node_ptr parse_return_statement()
  20928. {
  20929. return error_node();
  20930. }
  20931. #endif
  20932. inline bool post_variable_process(const std::string& symbol)
  20933. {
  20934. if (
  20935. peek_token_is(token_t::e_lbracket ) ||
  20936. peek_token_is(token_t::e_lcrlbracket) ||
  20937. peek_token_is(token_t::e_lsqrbracket)
  20938. )
  20939. {
  20940. if (!settings_.commutative_check_enabled())
  20941. {
  20942. set_error(
  20943. make_error(parser_error::e_syntax,
  20944. current_token(),
  20945. "ERR185 - Invalid sequence of variable '"+ symbol + "' and bracket",
  20946. exprtk_error_location));
  20947. return false;
  20948. }
  20949. lexer().insert_front(token_t::e_mul);
  20950. }
  20951. return true;
  20952. }
  20953. inline bool post_bracket_process(const typename token_t::token_type& token, expression_node_ptr& branch)
  20954. {
  20955. bool implied_mul = false;
  20956. if (is_generally_string_node(branch))
  20957. return true;
  20958. const lexer::parser_helper::token_advance_mode hold = prsrhlpr_t::e_hold;
  20959. switch (token)
  20960. {
  20961. case token_t::e_lcrlbracket : implied_mul = token_is(token_t::e_lbracket ,hold) ||
  20962. token_is(token_t::e_lcrlbracket,hold) ||
  20963. token_is(token_t::e_lsqrbracket,hold) ;
  20964. break;
  20965. case token_t::e_lbracket : implied_mul = token_is(token_t::e_lbracket ,hold) ||
  20966. token_is(token_t::e_lcrlbracket,hold) ||
  20967. token_is(token_t::e_lsqrbracket,hold) ;
  20968. break;
  20969. case token_t::e_lsqrbracket : implied_mul = token_is(token_t::e_lbracket ,hold) ||
  20970. token_is(token_t::e_lcrlbracket,hold) ||
  20971. token_is(token_t::e_lsqrbracket,hold) ;
  20972. break;
  20973. default : return true;
  20974. }
  20975. if (implied_mul)
  20976. {
  20977. if (!settings_.commutative_check_enabled())
  20978. {
  20979. set_error(
  20980. make_error(parser_error::e_syntax,
  20981. current_token(),
  20982. "ERR186 - Invalid sequence of brackets",
  20983. exprtk_error_location));
  20984. return false;
  20985. }
  20986. else if (token_t::e_eof != current_token().type)
  20987. {
  20988. lexer().insert_front(current_token().type);
  20989. lexer().insert_front(token_t::e_mul);
  20990. next_token();
  20991. }
  20992. }
  20993. return true;
  20994. }
  20995. inline expression_node_ptr parse_symtab_symbol()
  20996. {
  20997. const std::string symbol = current_token().value;
  20998. // Are we dealing with a variable or a special constant?
  20999. expression_node_ptr variable = symtab_store_.get_variable(symbol);
  21000. if (variable)
  21001. {
  21002. if (symtab_store_.is_constant_node(symbol))
  21003. {
  21004. variable = expression_generator_(variable->value());
  21005. }
  21006. if (!post_variable_process(symbol))
  21007. return error_node();
  21008. lodge_symbol(symbol, e_st_variable);
  21009. next_token();
  21010. return variable;
  21011. }
  21012. // Are we dealing with a locally defined variable, vector or string?
  21013. if (!sem_.empty())
  21014. {
  21015. scope_element& se = sem_.get_active_element(symbol);
  21016. if (se.active && details::imatch(se.name, symbol))
  21017. {
  21018. if (scope_element::e_variable == se.type)
  21019. {
  21020. se.active = true;
  21021. lodge_symbol(symbol, e_st_local_variable);
  21022. if (!post_variable_process(symbol))
  21023. return error_node();
  21024. next_token();
  21025. return se.var_node;
  21026. }
  21027. else if (scope_element::e_vector == se.type)
  21028. {
  21029. return parse_vector();
  21030. }
  21031. #ifndef exprtk_disable_string_capabilities
  21032. else if (scope_element::e_string == se.type)
  21033. {
  21034. return parse_string();
  21035. }
  21036. #endif
  21037. }
  21038. }
  21039. #ifndef exprtk_disable_string_capabilities
  21040. // Are we dealing with a string variable?
  21041. if (symtab_store_.is_stringvar(symbol))
  21042. {
  21043. return parse_string();
  21044. }
  21045. #endif
  21046. {
  21047. // Are we dealing with a function?
  21048. ifunction<T>* function = symtab_store_.get_function(symbol);
  21049. if (function)
  21050. {
  21051. lodge_symbol(symbol, e_st_function);
  21052. expression_node_ptr func_node =
  21053. parse_function_invocation(function,symbol);
  21054. if (func_node)
  21055. return func_node;
  21056. else
  21057. {
  21058. set_error(
  21059. make_error(parser_error::e_syntax,
  21060. current_token(),
  21061. "ERR187 - Failed to generate node for function: '" + symbol + "'",
  21062. exprtk_error_location));
  21063. return error_node();
  21064. }
  21065. }
  21066. }
  21067. {
  21068. // Are we dealing with a vararg function?
  21069. ivararg_function<T>* vararg_function = symtab_store_.get_vararg_function(symbol);
  21070. if (vararg_function)
  21071. {
  21072. lodge_symbol(symbol, e_st_function);
  21073. expression_node_ptr vararg_func_node =
  21074. parse_vararg_function_call(vararg_function, symbol);
  21075. if (vararg_func_node)
  21076. return vararg_func_node;
  21077. else
  21078. {
  21079. set_error(
  21080. make_error(parser_error::e_syntax,
  21081. current_token(),
  21082. "ERR188 - Failed to generate node for vararg function: '" + symbol + "'",
  21083. exprtk_error_location));
  21084. return error_node();
  21085. }
  21086. }
  21087. }
  21088. {
  21089. // Are we dealing with a vararg generic function?
  21090. igeneric_function<T>* generic_function = symtab_store_.get_generic_function(symbol);
  21091. if (generic_function)
  21092. {
  21093. lodge_symbol(symbol, e_st_function);
  21094. expression_node_ptr genericfunc_node =
  21095. parse_generic_function_call(generic_function, symbol);
  21096. if (genericfunc_node)
  21097. return genericfunc_node;
  21098. else
  21099. {
  21100. set_error(
  21101. make_error(parser_error::e_syntax,
  21102. current_token(),
  21103. "ERR189 - Failed to generate node for generic function: '" + symbol + "'",
  21104. exprtk_error_location));
  21105. return error_node();
  21106. }
  21107. }
  21108. }
  21109. #ifndef exprtk_disable_string_capabilities
  21110. {
  21111. // Are we dealing with a vararg string returning function?
  21112. igeneric_function<T>* string_function = symtab_store_.get_string_function(symbol);
  21113. if (string_function)
  21114. {
  21115. lodge_symbol(symbol, e_st_function);
  21116. expression_node_ptr stringfunc_node =
  21117. parse_string_function_call(string_function, symbol);
  21118. if (stringfunc_node)
  21119. return stringfunc_node;
  21120. else
  21121. {
  21122. set_error(
  21123. make_error(parser_error::e_syntax,
  21124. current_token(),
  21125. "ERR190 - Failed to generate node for string function: '" + symbol + "'",
  21126. exprtk_error_location));
  21127. return error_node();
  21128. }
  21129. }
  21130. }
  21131. {
  21132. // Are we dealing with a vararg overloaded scalar/string returning function?
  21133. igeneric_function<T>* overload_function = symtab_store_.get_overload_function(symbol);
  21134. if (overload_function)
  21135. {
  21136. lodge_symbol(symbol, e_st_function);
  21137. expression_node_ptr overloadfunc_node =
  21138. parse_overload_function_call(overload_function, symbol);
  21139. if (overloadfunc_node)
  21140. return overloadfunc_node;
  21141. else
  21142. {
  21143. set_error(
  21144. make_error(parser_error::e_syntax,
  21145. current_token(),
  21146. "ERR191 - Failed to generate node for overload function: '" + symbol + "'",
  21147. exprtk_error_location));
  21148. return error_node();
  21149. }
  21150. }
  21151. }
  21152. #endif
  21153. // Are we dealing with a vector?
  21154. if (symtab_store_.is_vector(symbol))
  21155. {
  21156. lodge_symbol(symbol, e_st_vector);
  21157. return parse_vector();
  21158. }
  21159. if (details::is_reserved_symbol(symbol))
  21160. {
  21161. if (
  21162. settings_.function_enabled(symbol) ||
  21163. !details::is_base_function(symbol)
  21164. )
  21165. {
  21166. set_error(
  21167. make_error(parser_error::e_syntax,
  21168. current_token(),
  21169. "ERR192 - Invalid use of reserved symbol '" + symbol + "'",
  21170. exprtk_error_location));
  21171. return error_node();
  21172. }
  21173. }
  21174. // Should we handle unknown symbols?
  21175. if (resolve_unknown_symbol_ && unknown_symbol_resolver_)
  21176. {
  21177. if (!(settings_.rsrvd_sym_usr_disabled() && details::is_reserved_symbol(symbol)))
  21178. {
  21179. symbol_table_t& symtab = symtab_store_.get_symbol_table();
  21180. std::string error_message;
  21181. if (unknown_symbol_resolver::e_usrmode_default == unknown_symbol_resolver_->mode)
  21182. {
  21183. T default_value = T(0);
  21184. typename unknown_symbol_resolver::usr_symbol_type usr_symbol_type = unknown_symbol_resolver::e_usr_unknown_type;
  21185. if (unknown_symbol_resolver_->process(symbol, usr_symbol_type, default_value, error_message))
  21186. {
  21187. bool create_result = false;
  21188. switch (usr_symbol_type)
  21189. {
  21190. case unknown_symbol_resolver::e_usr_variable_type : create_result = symtab.create_variable(symbol, default_value);
  21191. break;
  21192. case unknown_symbol_resolver::e_usr_constant_type : create_result = symtab.add_constant(symbol, default_value);
  21193. break;
  21194. default : create_result = false;
  21195. }
  21196. if (create_result)
  21197. {
  21198. expression_node_ptr var = symtab_store_.get_variable(symbol);
  21199. if (var)
  21200. {
  21201. if (symtab_store_.is_constant_node(symbol))
  21202. {
  21203. var = expression_generator_(var->value());
  21204. }
  21205. lodge_symbol(symbol, e_st_variable);
  21206. if (!post_variable_process(symbol))
  21207. return error_node();
  21208. next_token();
  21209. return var;
  21210. }
  21211. }
  21212. }
  21213. set_error(
  21214. make_error(parser_error::e_symtab,
  21215. current_token(),
  21216. "ERR193 - Failed to create variable: '" + symbol + "'" +
  21217. (error_message.empty() ? "" : " - " + error_message),
  21218. exprtk_error_location));
  21219. }
  21220. else if (unknown_symbol_resolver::e_usrmode_extended == unknown_symbol_resolver_->mode)
  21221. {
  21222. if (unknown_symbol_resolver_->process(symbol, symtab, error_message))
  21223. {
  21224. expression_node_ptr result = parse_symtab_symbol();
  21225. if (result)
  21226. {
  21227. return result;
  21228. }
  21229. }
  21230. set_error(
  21231. make_error(parser_error::e_symtab,
  21232. current_token(),
  21233. "ERR194 - Failed to resolve symbol: '" + symbol + "'" +
  21234. (error_message.empty() ? "" : " - " + error_message),
  21235. exprtk_error_location));
  21236. }
  21237. return error_node();
  21238. }
  21239. }
  21240. set_error(
  21241. make_error(parser_error::e_syntax,
  21242. current_token(),
  21243. "ERR195 - Undefined symbol: '" + symbol + "'",
  21244. exprtk_error_location));
  21245. return error_node();
  21246. }
  21247. inline expression_node_ptr parse_symbol()
  21248. {
  21249. static const std::string symbol_if = "if" ;
  21250. static const std::string symbol_while = "while" ;
  21251. static const std::string symbol_repeat = "repeat" ;
  21252. static const std::string symbol_for = "for" ;
  21253. static const std::string symbol_switch = "switch" ;
  21254. static const std::string symbol_null = "null" ;
  21255. static const std::string symbol_break = "break" ;
  21256. static const std::string symbol_continue = "continue";
  21257. static const std::string symbol_var = "var" ;
  21258. static const std::string symbol_swap = "swap" ;
  21259. static const std::string symbol_return = "return" ;
  21260. static const std::string symbol_not = "not" ;
  21261. if (valid_vararg_operation(current_token().value))
  21262. {
  21263. return parse_vararg_function();
  21264. }
  21265. else if (details::imatch(current_token().value, symbol_not))
  21266. {
  21267. return parse_not_statement();
  21268. }
  21269. else if (valid_base_operation(current_token().value))
  21270. {
  21271. return parse_base_operation();
  21272. }
  21273. else if (
  21274. details::imatch(current_token().value, symbol_if) &&
  21275. settings_.control_struct_enabled(current_token().value)
  21276. )
  21277. {
  21278. return parse_conditional_statement();
  21279. }
  21280. else if (
  21281. details::imatch(current_token().value, symbol_while) &&
  21282. settings_.control_struct_enabled(current_token().value)
  21283. )
  21284. {
  21285. return parse_while_loop();
  21286. }
  21287. else if (
  21288. details::imatch(current_token().value, symbol_repeat) &&
  21289. settings_.control_struct_enabled(current_token().value)
  21290. )
  21291. {
  21292. return parse_repeat_until_loop();
  21293. }
  21294. else if (
  21295. details::imatch(current_token().value, symbol_for) &&
  21296. settings_.control_struct_enabled(current_token().value)
  21297. )
  21298. {
  21299. return parse_for_loop();
  21300. }
  21301. else if (
  21302. details::imatch(current_token().value, symbol_switch) &&
  21303. settings_.control_struct_enabled(current_token().value)
  21304. )
  21305. {
  21306. return parse_switch_statement();
  21307. }
  21308. else if (details::is_valid_sf_symbol(current_token().value))
  21309. {
  21310. return parse_special_function();
  21311. }
  21312. else if (details::imatch(current_token().value, symbol_null))
  21313. {
  21314. return parse_null_statement();
  21315. }
  21316. #ifndef exprtk_disable_break_continue
  21317. else if (details::imatch(current_token().value, symbol_break))
  21318. {
  21319. return parse_break_statement();
  21320. }
  21321. else if (details::imatch(current_token().value, symbol_continue))
  21322. {
  21323. return parse_continue_statement();
  21324. }
  21325. #endif
  21326. else if (details::imatch(current_token().value, symbol_var))
  21327. {
  21328. return parse_define_var_statement();
  21329. }
  21330. else if (details::imatch(current_token().value, symbol_swap))
  21331. {
  21332. return parse_swap_statement();
  21333. }
  21334. #ifndef exprtk_disable_return_statement
  21335. else if (
  21336. details::imatch(current_token().value, symbol_return) &&
  21337. settings_.control_struct_enabled(current_token().value)
  21338. )
  21339. {
  21340. return parse_return_statement();
  21341. }
  21342. #endif
  21343. else if (symtab_store_.valid() || !sem_.empty())
  21344. {
  21345. return parse_symtab_symbol();
  21346. }
  21347. else
  21348. {
  21349. set_error(
  21350. make_error(parser_error::e_symtab,
  21351. current_token(),
  21352. "ERR196 - Variable or function detected, yet symbol-table is invalid, Symbol: " + current_token().value,
  21353. exprtk_error_location));
  21354. return error_node();
  21355. }
  21356. }
  21357. inline expression_node_ptr parse_branch(precedence_level precedence = e_level00)
  21358. {
  21359. expression_node_ptr branch = error_node();
  21360. if (token_t::e_number == current_token().type)
  21361. {
  21362. T numeric_value = T(0);
  21363. if (details::string_to_real(current_token().value, numeric_value))
  21364. {
  21365. expression_node_ptr literal_exp = expression_generator_(numeric_value);
  21366. if (0 == literal_exp)
  21367. {
  21368. set_error(
  21369. make_error(parser_error::e_numeric,
  21370. current_token(),
  21371. "ERR197 - Failed generate node for scalar: '" + current_token().value + "'",
  21372. exprtk_error_location));
  21373. return error_node();
  21374. }
  21375. next_token();
  21376. branch = literal_exp;
  21377. }
  21378. else
  21379. {
  21380. set_error(
  21381. make_error(parser_error::e_numeric,
  21382. current_token(),
  21383. "ERR198 - Failed to convert '" + current_token().value + "' to a number",
  21384. exprtk_error_location));
  21385. return error_node();
  21386. }
  21387. }
  21388. else if (token_t::e_symbol == current_token().type)
  21389. {
  21390. branch = parse_symbol();
  21391. }
  21392. #ifndef exprtk_disable_string_capabilities
  21393. else if (token_t::e_string == current_token().type)
  21394. {
  21395. branch = parse_const_string();
  21396. }
  21397. #endif
  21398. else if (token_t::e_lbracket == current_token().type)
  21399. {
  21400. next_token();
  21401. if (0 == (branch = parse_expression()))
  21402. return error_node();
  21403. else if (!token_is(token_t::e_rbracket))
  21404. {
  21405. set_error(
  21406. make_error(parser_error::e_syntax,
  21407. current_token(),
  21408. "ERR199 - Expected ')' instead of: '" + current_token().value + "'",
  21409. exprtk_error_location));
  21410. free_node(node_allocator_,branch);
  21411. return error_node();
  21412. }
  21413. else if (!post_bracket_process(token_t::e_lbracket,branch))
  21414. {
  21415. free_node(node_allocator_,branch);
  21416. return error_node();
  21417. }
  21418. }
  21419. else if (token_t::e_lsqrbracket == current_token().type)
  21420. {
  21421. next_token();
  21422. if (0 == (branch = parse_expression()))
  21423. return error_node();
  21424. else if (!token_is(token_t::e_rsqrbracket))
  21425. {
  21426. set_error(
  21427. make_error(parser_error::e_syntax,
  21428. current_token(),
  21429. "ERR200 - Expected ']' instead of: '" + current_token().value + "'",
  21430. exprtk_error_location));
  21431. free_node(node_allocator_,branch);
  21432. return error_node();
  21433. }
  21434. else if (!post_bracket_process(token_t::e_lsqrbracket,branch))
  21435. {
  21436. free_node(node_allocator_,branch);
  21437. return error_node();
  21438. }
  21439. }
  21440. else if (token_t::e_lcrlbracket == current_token().type)
  21441. {
  21442. next_token();
  21443. if (0 == (branch = parse_expression()))
  21444. return error_node();
  21445. else if (!token_is(token_t::e_rcrlbracket))
  21446. {
  21447. set_error(
  21448. make_error(parser_error::e_syntax,
  21449. current_token(),
  21450. "ERR201 - Expected '}' instead of: '" + current_token().value + "'",
  21451. exprtk_error_location));
  21452. free_node(node_allocator_,branch);
  21453. return error_node();
  21454. }
  21455. else if (!post_bracket_process(token_t::e_lcrlbracket,branch))
  21456. {
  21457. free_node(node_allocator_,branch);
  21458. return error_node();
  21459. }
  21460. }
  21461. else if (token_t::e_sub == current_token().type)
  21462. {
  21463. next_token();
  21464. branch = parse_expression(e_level11);
  21465. if (
  21466. branch &&
  21467. !(
  21468. details::is_neg_unary_node (branch) &&
  21469. simplify_unary_negation_branch(branch)
  21470. )
  21471. )
  21472. {
  21473. branch = expression_generator_(details::e_neg,branch);
  21474. }
  21475. }
  21476. else if (token_t::e_add == current_token().type)
  21477. {
  21478. next_token();
  21479. branch = parse_expression(e_level13);
  21480. }
  21481. else if (token_t::e_eof == current_token().type)
  21482. {
  21483. set_error(
  21484. make_error(parser_error::e_syntax,
  21485. current_token(),
  21486. "ERR202 - Premature end of expression[1]",
  21487. exprtk_error_location));
  21488. return error_node();
  21489. }
  21490. else
  21491. {
  21492. set_error(
  21493. make_error(parser_error::e_syntax,
  21494. current_token(),
  21495. "ERR203 - Premature end of expression[2]",
  21496. exprtk_error_location));
  21497. return error_node();
  21498. }
  21499. if (
  21500. branch &&
  21501. (e_level00 == precedence) &&
  21502. token_is(token_t::e_ternary,prsrhlpr_t::e_hold)
  21503. )
  21504. {
  21505. branch = parse_ternary_conditional_statement(branch);
  21506. }
  21507. parse_pending_string_rangesize(branch);
  21508. return branch;
  21509. }
  21510. template <typename Type>
  21511. class expression_generator
  21512. {
  21513. public:
  21514. typedef details::expression_node<Type>* expression_node_ptr;
  21515. typedef expression_node_ptr (*synthesize_functor_t)(expression_generator<T>&, const details::operator_type& operation, expression_node_ptr (&branch)[2]);
  21516. typedef std::map<std::string,synthesize_functor_t> synthesize_map_t;
  21517. typedef typename exprtk::parser<Type> parser_t;
  21518. typedef const Type& vtype;
  21519. typedef const Type ctype;
  21520. inline void init_synthesize_map()
  21521. {
  21522. #ifndef exprtk_disable_enhanced_features
  21523. synthesize_map_["(v)o(v)"] = synthesize_vov_expression::process;
  21524. synthesize_map_["(c)o(v)"] = synthesize_cov_expression::process;
  21525. synthesize_map_["(v)o(c)"] = synthesize_voc_expression::process;
  21526. #define register_synthezier(S) \
  21527. synthesize_map_[S ::node_type::id()] = S ::process; \
  21528. register_synthezier(synthesize_vovov_expression0)
  21529. register_synthezier(synthesize_vovov_expression1)
  21530. register_synthezier(synthesize_vovoc_expression0)
  21531. register_synthezier(synthesize_vovoc_expression1)
  21532. register_synthezier(synthesize_vocov_expression0)
  21533. register_synthezier(synthesize_vocov_expression1)
  21534. register_synthezier(synthesize_covov_expression0)
  21535. register_synthezier(synthesize_covov_expression1)
  21536. register_synthezier(synthesize_covoc_expression0)
  21537. register_synthezier(synthesize_covoc_expression1)
  21538. register_synthezier(synthesize_cocov_expression1)
  21539. register_synthezier(synthesize_vococ_expression0)
  21540. register_synthezier(synthesize_vovovov_expression0)
  21541. register_synthezier(synthesize_vovovoc_expression0)
  21542. register_synthezier(synthesize_vovocov_expression0)
  21543. register_synthezier(synthesize_vocovov_expression0)
  21544. register_synthezier(synthesize_covovov_expression0)
  21545. register_synthezier(synthesize_covocov_expression0)
  21546. register_synthezier(synthesize_vocovoc_expression0)
  21547. register_synthezier(synthesize_covovoc_expression0)
  21548. register_synthezier(synthesize_vococov_expression0)
  21549. register_synthezier(synthesize_vovovov_expression1)
  21550. register_synthezier(synthesize_vovovoc_expression1)
  21551. register_synthezier(synthesize_vovocov_expression1)
  21552. register_synthezier(synthesize_vocovov_expression1)
  21553. register_synthezier(synthesize_covovov_expression1)
  21554. register_synthezier(synthesize_covocov_expression1)
  21555. register_synthezier(synthesize_vocovoc_expression1)
  21556. register_synthezier(synthesize_covovoc_expression1)
  21557. register_synthezier(synthesize_vococov_expression1)
  21558. register_synthezier(synthesize_vovovov_expression2)
  21559. register_synthezier(synthesize_vovovoc_expression2)
  21560. register_synthezier(synthesize_vovocov_expression2)
  21561. register_synthezier(synthesize_vocovov_expression2)
  21562. register_synthezier(synthesize_covovov_expression2)
  21563. register_synthezier(synthesize_covocov_expression2)
  21564. register_synthezier(synthesize_vocovoc_expression2)
  21565. register_synthezier(synthesize_covovoc_expression2)
  21566. register_synthezier(synthesize_vovovov_expression3)
  21567. register_synthezier(synthesize_vovovoc_expression3)
  21568. register_synthezier(synthesize_vovocov_expression3)
  21569. register_synthezier(synthesize_vocovov_expression3)
  21570. register_synthezier(synthesize_covovov_expression3)
  21571. register_synthezier(synthesize_covocov_expression3)
  21572. register_synthezier(synthesize_vocovoc_expression3)
  21573. register_synthezier(synthesize_covovoc_expression3)
  21574. register_synthezier(synthesize_vococov_expression3)
  21575. register_synthezier(synthesize_vovovov_expression4)
  21576. register_synthezier(synthesize_vovovoc_expression4)
  21577. register_synthezier(synthesize_vovocov_expression4)
  21578. register_synthezier(synthesize_vocovov_expression4)
  21579. register_synthezier(synthesize_covovov_expression4)
  21580. register_synthezier(synthesize_covocov_expression4)
  21581. register_synthezier(synthesize_vocovoc_expression4)
  21582. register_synthezier(synthesize_covovoc_expression4)
  21583. #endif
  21584. }
  21585. inline void set_parser(parser_t& p)
  21586. {
  21587. parser_ = &p;
  21588. }
  21589. inline void set_uom(unary_op_map_t& unary_op_map)
  21590. {
  21591. unary_op_map_ = &unary_op_map;
  21592. }
  21593. inline void set_bom(binary_op_map_t& binary_op_map)
  21594. {
  21595. binary_op_map_ = &binary_op_map;
  21596. }
  21597. inline void set_ibom(inv_binary_op_map_t& inv_binary_op_map)
  21598. {
  21599. inv_binary_op_map_ = &inv_binary_op_map;
  21600. }
  21601. inline void set_sf3m(sf3_map_t& sf3_map)
  21602. {
  21603. sf3_map_ = &sf3_map;
  21604. }
  21605. inline void set_sf4m(sf4_map_t& sf4_map)
  21606. {
  21607. sf4_map_ = &sf4_map;
  21608. }
  21609. inline void set_allocator(details::node_allocator& na)
  21610. {
  21611. node_allocator_ = &na;
  21612. }
  21613. inline void set_strength_reduction_state(const bool enabled)
  21614. {
  21615. strength_reduction_enabled_ = enabled;
  21616. }
  21617. inline bool strength_reduction_enabled() const
  21618. {
  21619. return strength_reduction_enabled_;
  21620. }
  21621. inline bool valid_operator(const details::operator_type& operation, binary_functor_t& bop)
  21622. {
  21623. typename binary_op_map_t::iterator bop_itr = binary_op_map_->find(operation);
  21624. if ((*binary_op_map_).end() == bop_itr)
  21625. return false;
  21626. bop = bop_itr->second;
  21627. return true;
  21628. }
  21629. inline bool valid_operator(const details::operator_type& operation, unary_functor_t& uop)
  21630. {
  21631. typename unary_op_map_t::iterator uop_itr = unary_op_map_->find(operation);
  21632. if ((*unary_op_map_).end() == uop_itr)
  21633. return false;
  21634. uop = uop_itr->second;
  21635. return true;
  21636. }
  21637. inline details::operator_type get_operator(const binary_functor_t& bop) const
  21638. {
  21639. return (*inv_binary_op_map_).find(bop)->second;
  21640. }
  21641. inline expression_node_ptr operator() (const Type& v) const
  21642. {
  21643. return node_allocator_->allocate<literal_node_t>(v);
  21644. }
  21645. #ifndef exprtk_disable_string_capabilities
  21646. inline expression_node_ptr operator() (const std::string& s) const
  21647. {
  21648. return node_allocator_->allocate<string_literal_node_t>(s);
  21649. }
  21650. inline expression_node_ptr operator() (std::string& s, range_t& rp) const
  21651. {
  21652. return node_allocator_->allocate_rr<string_range_node_t>(s,rp);
  21653. }
  21654. inline expression_node_ptr operator() (const std::string& s, range_t& rp) const
  21655. {
  21656. return node_allocator_->allocate_tt<const_string_range_node_t>(s,rp);
  21657. }
  21658. inline expression_node_ptr operator() (expression_node_ptr branch, range_t& rp) const
  21659. {
  21660. if (is_generally_string_node(branch))
  21661. return node_allocator_->allocate_tt<generic_string_range_node_t>(branch,rp);
  21662. else
  21663. return error_node();
  21664. }
  21665. #endif
  21666. inline bool unary_optimisable(const details::operator_type& operation) const
  21667. {
  21668. return (details::e_abs == operation) || (details::e_acos == operation) ||
  21669. (details::e_acosh == operation) || (details::e_asin == operation) ||
  21670. (details::e_asinh == operation) || (details::e_atan == operation) ||
  21671. (details::e_atanh == operation) || (details::e_ceil == operation) ||
  21672. (details::e_cos == operation) || (details::e_cosh == operation) ||
  21673. (details::e_exp == operation) || (details::e_expm1 == operation) ||
  21674. (details::e_floor == operation) || (details::e_log == operation) ||
  21675. (details::e_log10 == operation) || (details::e_log2 == operation) ||
  21676. (details::e_log1p == operation) || (details::e_neg == operation) ||
  21677. (details::e_pos == operation) || (details::e_round == operation) ||
  21678. (details::e_sin == operation) || (details::e_sinc == operation) ||
  21679. (details::e_sinh == operation) || (details::e_sqrt == operation) ||
  21680. (details::e_tan == operation) || (details::e_tanh == operation) ||
  21681. (details::e_cot == operation) || (details::e_sec == operation) ||
  21682. (details::e_csc == operation) || (details::e_r2d == operation) ||
  21683. (details::e_d2r == operation) || (details::e_d2g == operation) ||
  21684. (details::e_g2d == operation) || (details::e_notl == operation) ||
  21685. (details::e_sgn == operation) || (details::e_erf == operation) ||
  21686. (details::e_erfc == operation) || (details::e_ncdf == operation) ||
  21687. (details::e_frac == operation) || (details::e_trunc == operation) ;
  21688. }
  21689. inline bool sf3_optimisable(const std::string& sf3id, trinary_functor_t& tfunc) const
  21690. {
  21691. typename sf3_map_t::const_iterator itr = sf3_map_->find(sf3id);
  21692. if (sf3_map_->end() == itr)
  21693. return false;
  21694. else
  21695. tfunc = itr->second.first;
  21696. return true;
  21697. }
  21698. inline bool sf4_optimisable(const std::string& sf4id, quaternary_functor_t& qfunc) const
  21699. {
  21700. typename sf4_map_t::const_iterator itr = sf4_map_->find(sf4id);
  21701. if (sf4_map_->end() == itr)
  21702. return false;
  21703. else
  21704. qfunc = itr->second.first;
  21705. return true;
  21706. }
  21707. inline bool sf3_optimisable(const std::string& sf3id, details::operator_type& operation) const
  21708. {
  21709. typename sf3_map_t::const_iterator itr = sf3_map_->find(sf3id);
  21710. if (sf3_map_->end() == itr)
  21711. return false;
  21712. else
  21713. operation = itr->second.second;
  21714. return true;
  21715. }
  21716. inline bool sf4_optimisable(const std::string& sf4id, details::operator_type& operation) const
  21717. {
  21718. typename sf4_map_t::const_iterator itr = sf4_map_->find(sf4id);
  21719. if (sf4_map_->end() == itr)
  21720. return false;
  21721. else
  21722. operation = itr->second.second;
  21723. return true;
  21724. }
  21725. inline expression_node_ptr operator() (const details::operator_type& operation, expression_node_ptr (&branch)[1])
  21726. {
  21727. if (0 == branch[0])
  21728. {
  21729. return error_node();
  21730. }
  21731. else if (details::is_null_node(branch[0]))
  21732. {
  21733. return branch[0];
  21734. }
  21735. else if (details::is_break_node(branch[0]))
  21736. {
  21737. return error_node();
  21738. }
  21739. else if (details::is_continue_node(branch[0]))
  21740. {
  21741. return error_node();
  21742. }
  21743. else if (details::is_constant_node(branch[0]))
  21744. {
  21745. return synthesize_expression<unary_node_t,1>(operation,branch);
  21746. }
  21747. else if (unary_optimisable(operation) && details::is_variable_node(branch[0]))
  21748. {
  21749. return synthesize_uv_expression(operation,branch);
  21750. }
  21751. else if (unary_optimisable(operation) && details::is_ivector_node(branch[0]))
  21752. {
  21753. return synthesize_uvec_expression(operation,branch);
  21754. }
  21755. else
  21756. return synthesize_unary_expression(operation,branch);
  21757. }
  21758. inline bool is_assignment_operation(const details::operator_type& operation) const
  21759. {
  21760. return (
  21761. (details::e_addass == operation) ||
  21762. (details::e_subass == operation) ||
  21763. (details::e_mulass == operation) ||
  21764. (details::e_divass == operation) ||
  21765. (details::e_modass == operation)
  21766. ) &&
  21767. parser_->settings_.assignment_enabled(operation);
  21768. }
  21769. #ifndef exprtk_disable_string_capabilities
  21770. inline bool valid_string_operation(const details::operator_type& operation) const
  21771. {
  21772. return (details::e_add == operation) ||
  21773. (details::e_lt == operation) ||
  21774. (details::e_lte == operation) ||
  21775. (details::e_gt == operation) ||
  21776. (details::e_gte == operation) ||
  21777. (details::e_eq == operation) ||
  21778. (details::e_ne == operation) ||
  21779. (details::e_in == operation) ||
  21780. (details::e_like == operation) ||
  21781. (details::e_ilike == operation) ||
  21782. (details::e_assign == operation) ||
  21783. (details::e_addass == operation) ||
  21784. (details::e_swap == operation) ;
  21785. }
  21786. #else
  21787. inline bool valid_string_operation(const details::operator_type&) const
  21788. {
  21789. return false;
  21790. }
  21791. #endif
  21792. inline std::string to_str(const details::operator_type& operation) const
  21793. {
  21794. switch (operation)
  21795. {
  21796. case details::e_add : return "+" ;
  21797. case details::e_sub : return "-" ;
  21798. case details::e_mul : return "*" ;
  21799. case details::e_div : return "/" ;
  21800. case details::e_mod : return "%" ;
  21801. case details::e_pow : return "^" ;
  21802. case details::e_lt : return "<" ;
  21803. case details::e_lte : return "<=" ;
  21804. case details::e_gt : return ">" ;
  21805. case details::e_gte : return ">=" ;
  21806. case details::e_eq : return "==" ;
  21807. case details::e_ne : return "!=" ;
  21808. case details::e_and : return "and" ;
  21809. case details::e_nand : return "nand" ;
  21810. case details::e_or : return "or" ;
  21811. case details::e_nor : return "nor" ;
  21812. case details::e_xor : return "xor" ;
  21813. case details::e_xnor : return "xnor" ;
  21814. default : return "UNKNOWN";
  21815. }
  21816. }
  21817. inline bool operation_optimisable(const details::operator_type& operation) const
  21818. {
  21819. return (details::e_add == operation) ||
  21820. (details::e_sub == operation) ||
  21821. (details::e_mul == operation) ||
  21822. (details::e_div == operation) ||
  21823. (details::e_mod == operation) ||
  21824. (details::e_pow == operation) ||
  21825. (details::e_lt == operation) ||
  21826. (details::e_lte == operation) ||
  21827. (details::e_gt == operation) ||
  21828. (details::e_gte == operation) ||
  21829. (details::e_eq == operation) ||
  21830. (details::e_ne == operation) ||
  21831. (details::e_and == operation) ||
  21832. (details::e_nand == operation) ||
  21833. (details::e_or == operation) ||
  21834. (details::e_nor == operation) ||
  21835. (details::e_xor == operation) ||
  21836. (details::e_xnor == operation) ;
  21837. }
  21838. inline std::string branch_to_id(expression_node_ptr branch) const
  21839. {
  21840. static const std::string null_str ("(null)" );
  21841. static const std::string const_str ("(c)" );
  21842. static const std::string var_str ("(v)" );
  21843. static const std::string vov_str ("(vov)" );
  21844. static const std::string cov_str ("(cov)" );
  21845. static const std::string voc_str ("(voc)" );
  21846. static const std::string str_str ("(s)" );
  21847. static const std::string strrng_str ("(rngs)" );
  21848. static const std::string cs_str ("(cs)" );
  21849. static const std::string cstrrng_str("(crngs)");
  21850. if (details::is_null_node(branch))
  21851. return null_str;
  21852. else if (details::is_constant_node(branch))
  21853. return const_str;
  21854. else if (details::is_variable_node(branch))
  21855. return var_str;
  21856. else if (details::is_vov_node(branch))
  21857. return vov_str;
  21858. else if (details::is_cov_node(branch))
  21859. return cov_str;
  21860. else if (details::is_voc_node(branch))
  21861. return voc_str;
  21862. else if (details::is_string_node(branch))
  21863. return str_str;
  21864. else if (details::is_const_string_node(branch))
  21865. return cs_str;
  21866. else if (details::is_string_range_node(branch))
  21867. return strrng_str;
  21868. else if (details::is_const_string_range_node(branch))
  21869. return cstrrng_str;
  21870. else if (details::is_t0ot1ot2_node(branch))
  21871. return "(" + dynamic_cast<details::T0oT1oT2_base_node<T>*>(branch)->type_id() + ")";
  21872. else if (details::is_t0ot1ot2ot3_node(branch))
  21873. return "(" + dynamic_cast<details::T0oT1oT2oT3_base_node<T>*>(branch)->type_id() + ")";
  21874. else
  21875. return "ERROR";
  21876. }
  21877. inline std::string branch_to_id(expression_node_ptr (&branch)[2]) const
  21878. {
  21879. return branch_to_id(branch[0]) + std::string("o") + branch_to_id(branch[1]);
  21880. }
  21881. inline bool cov_optimisable(const details::operator_type& operation, expression_node_ptr (&branch)[2]) const
  21882. {
  21883. if (!operation_optimisable(operation))
  21884. return false;
  21885. else
  21886. return details::is_constant_node(branch[0]) &&
  21887. details::is_variable_node(branch[1]) ;
  21888. }
  21889. inline bool voc_optimisable(const details::operator_type& operation, expression_node_ptr (&branch)[2]) const
  21890. {
  21891. if (!operation_optimisable(operation))
  21892. return false;
  21893. else
  21894. return details::is_variable_node(branch[0]) &&
  21895. details::is_constant_node(branch[1]) ;
  21896. }
  21897. inline bool vov_optimisable(const details::operator_type& operation, expression_node_ptr (&branch)[2]) const
  21898. {
  21899. if (!operation_optimisable(operation))
  21900. return false;
  21901. else
  21902. return details::is_variable_node(branch[0]) &&
  21903. details::is_variable_node(branch[1]) ;
  21904. }
  21905. inline bool cob_optimisable(const details::operator_type& operation, expression_node_ptr (&branch)[2]) const
  21906. {
  21907. if (!operation_optimisable(operation))
  21908. return false;
  21909. else
  21910. return details::is_constant_node(branch[0]) &&
  21911. !details::is_constant_node(branch[1]) ;
  21912. }
  21913. inline bool boc_optimisable(const details::operator_type& operation, expression_node_ptr (&branch)[2]) const
  21914. {
  21915. if (!operation_optimisable(operation))
  21916. return false;
  21917. else
  21918. return !details::is_constant_node(branch[0]) &&
  21919. details::is_constant_node(branch[1]) ;
  21920. }
  21921. inline bool cocob_optimisable(const details::operator_type& operation, expression_node_ptr (&branch)[2]) const
  21922. {
  21923. if (
  21924. (details::e_add == operation) ||
  21925. (details::e_sub == operation) ||
  21926. (details::e_mul == operation) ||
  21927. (details::e_div == operation)
  21928. )
  21929. {
  21930. return (details::is_constant_node(branch[0]) && details::is_cob_node(branch[1])) ||
  21931. (details::is_constant_node(branch[1]) && details::is_cob_node(branch[0])) ;
  21932. }
  21933. else
  21934. return false;
  21935. }
  21936. inline bool coboc_optimisable(const details::operator_type& operation, expression_node_ptr (&branch)[2]) const
  21937. {
  21938. if (
  21939. (details::e_add == operation) ||
  21940. (details::e_sub == operation) ||
  21941. (details::e_mul == operation) ||
  21942. (details::e_div == operation)
  21943. )
  21944. {
  21945. return (details::is_constant_node(branch[0]) && details::is_boc_node(branch[1])) ||
  21946. (details::is_constant_node(branch[1]) && details::is_boc_node(branch[0])) ;
  21947. }
  21948. else
  21949. return false;
  21950. }
  21951. inline bool uvouv_optimisable(const details::operator_type& operation, expression_node_ptr (&branch)[2]) const
  21952. {
  21953. if (!operation_optimisable(operation))
  21954. return false;
  21955. else
  21956. return details::is_uv_node(branch[0]) &&
  21957. details::is_uv_node(branch[1]) ;
  21958. }
  21959. inline bool vob_optimisable(const details::operator_type& operation, expression_node_ptr (&branch)[2]) const
  21960. {
  21961. if (!operation_optimisable(operation))
  21962. return false;
  21963. else
  21964. return details::is_variable_node(branch[0]) &&
  21965. !details::is_variable_node(branch[1]) ;
  21966. }
  21967. inline bool bov_optimisable(const details::operator_type& operation, expression_node_ptr (&branch)[2]) const
  21968. {
  21969. if (!operation_optimisable(operation))
  21970. return false;
  21971. else
  21972. return !details::is_variable_node(branch[0]) &&
  21973. details::is_variable_node(branch[1]) ;
  21974. }
  21975. inline bool binext_optimisable(const details::operator_type& operation, expression_node_ptr (&branch)[2]) const
  21976. {
  21977. if (!operation_optimisable(operation))
  21978. return false;
  21979. else
  21980. return !details::is_constant_node(branch[0]) ||
  21981. !details::is_constant_node(branch[1]) ;
  21982. }
  21983. inline bool is_invalid_assignment_op(const details::operator_type& operation, expression_node_ptr (&branch)[2]) const
  21984. {
  21985. if (is_assignment_operation(operation))
  21986. {
  21987. const bool b1_is_genstring = details::is_generally_string_node(branch[1]);
  21988. if (details::is_string_node(branch[0]))
  21989. return !b1_is_genstring;
  21990. else
  21991. return (
  21992. !details::is_variable_node (branch[0]) &&
  21993. !details::is_vector_elem_node (branch[0]) &&
  21994. !details::is_rebasevector_elem_node (branch[0]) &&
  21995. !details::is_rebasevector_celem_node(branch[0]) &&
  21996. !details::is_vector_node (branch[0])
  21997. )
  21998. || b1_is_genstring;
  21999. }
  22000. else
  22001. return false;
  22002. }
  22003. inline bool is_constpow_operation(const details::operator_type& operation, expression_node_ptr(&branch)[2]) const
  22004. {
  22005. if (
  22006. !details::is_constant_node(branch[1]) ||
  22007. details::is_constant_node(branch[0]) ||
  22008. details::is_variable_node(branch[0]) ||
  22009. details::is_vector_node (branch[0]) ||
  22010. details::is_generally_string_node(branch[0])
  22011. )
  22012. return false;
  22013. const Type c = static_cast<details::literal_node<Type>*>(branch[1])->value();
  22014. return cardinal_pow_optimisable(operation, c);
  22015. }
  22016. inline bool is_invalid_break_continue_op(expression_node_ptr (&branch)[2]) const
  22017. {
  22018. return (
  22019. details::is_break_node (branch[0]) ||
  22020. details::is_break_node (branch[1]) ||
  22021. details::is_continue_node(branch[0]) ||
  22022. details::is_continue_node(branch[1])
  22023. );
  22024. }
  22025. inline bool is_invalid_string_op(const details::operator_type& operation, expression_node_ptr (&branch)[2]) const
  22026. {
  22027. const bool b0_string = is_generally_string_node(branch[0]);
  22028. const bool b1_string = is_generally_string_node(branch[1]);
  22029. bool result = false;
  22030. if (b0_string != b1_string)
  22031. result = true;
  22032. else if (!valid_string_operation(operation) && b0_string && b1_string)
  22033. result = true;
  22034. if (result)
  22035. {
  22036. parser_->set_synthesis_error("Invalid string operation");
  22037. }
  22038. return result;
  22039. }
  22040. inline bool is_invalid_string_op(const details::operator_type& operation, expression_node_ptr (&branch)[3]) const
  22041. {
  22042. const bool b0_string = is_generally_string_node(branch[0]);
  22043. const bool b1_string = is_generally_string_node(branch[1]);
  22044. const bool b2_string = is_generally_string_node(branch[2]);
  22045. bool result = false;
  22046. if ((b0_string != b1_string) || (b1_string != b2_string))
  22047. result = true;
  22048. else if ((details::e_inrange != operation) && b0_string && b1_string && b2_string)
  22049. result = true;
  22050. if (result)
  22051. {
  22052. parser_->set_synthesis_error("Invalid string operation");
  22053. }
  22054. return result;
  22055. }
  22056. inline bool is_string_operation(const details::operator_type& operation, expression_node_ptr (&branch)[2]) const
  22057. {
  22058. const bool b0_string = is_generally_string_node(branch[0]);
  22059. const bool b1_string = is_generally_string_node(branch[1]);
  22060. return (b0_string && b1_string && valid_string_operation(operation));
  22061. }
  22062. inline bool is_string_operation(const details::operator_type& operation, expression_node_ptr (&branch)[3]) const
  22063. {
  22064. const bool b0_string = is_generally_string_node(branch[0]);
  22065. const bool b1_string = is_generally_string_node(branch[1]);
  22066. const bool b2_string = is_generally_string_node(branch[2]);
  22067. return (b0_string && b1_string && b2_string && (details::e_inrange == operation));
  22068. }
  22069. #ifndef exprtk_disable_sc_andor
  22070. inline bool is_shortcircuit_expression(const details::operator_type& operation) const
  22071. {
  22072. return (
  22073. (details::e_scand == operation) ||
  22074. (details::e_scor == operation)
  22075. );
  22076. }
  22077. #else
  22078. inline bool is_shortcircuit_expression(const details::operator_type&) const
  22079. {
  22080. return false;
  22081. }
  22082. #endif
  22083. inline bool is_null_present(expression_node_ptr (&branch)[2]) const
  22084. {
  22085. return (
  22086. details::is_null_node(branch[0]) ||
  22087. details::is_null_node(branch[1])
  22088. );
  22089. }
  22090. inline bool is_vector_eqineq_logic_operation(const details::operator_type& operation, expression_node_ptr (&branch)[2]) const
  22091. {
  22092. if (!is_ivector_node(branch[0]) && !is_ivector_node(branch[1]))
  22093. return false;
  22094. else
  22095. return (
  22096. (details::e_lt == operation) ||
  22097. (details::e_lte == operation) ||
  22098. (details::e_gt == operation) ||
  22099. (details::e_gte == operation) ||
  22100. (details::e_eq == operation) ||
  22101. (details::e_ne == operation) ||
  22102. (details::e_equal == operation) ||
  22103. (details::e_and == operation) ||
  22104. (details::e_nand == operation) ||
  22105. (details:: e_or == operation) ||
  22106. (details:: e_nor == operation) ||
  22107. (details:: e_xor == operation) ||
  22108. (details::e_xnor == operation)
  22109. );
  22110. }
  22111. inline bool is_vector_arithmetic_operation(const details::operator_type& operation, expression_node_ptr (&branch)[2]) const
  22112. {
  22113. if (!is_ivector_node(branch[0]) && !is_ivector_node(branch[1]))
  22114. return false;
  22115. else
  22116. return (
  22117. (details::e_add == operation) ||
  22118. (details::e_sub == operation) ||
  22119. (details::e_mul == operation) ||
  22120. (details::e_div == operation) ||
  22121. (details::e_pow == operation)
  22122. );
  22123. }
  22124. inline expression_node_ptr operator() (const details::operator_type& operation, expression_node_ptr (&branch)[2])
  22125. {
  22126. if ((0 == branch[0]) || (0 == branch[1]))
  22127. {
  22128. return error_node();
  22129. }
  22130. else if (is_invalid_string_op(operation,branch))
  22131. {
  22132. return error_node();
  22133. }
  22134. else if (is_invalid_assignment_op(operation,branch))
  22135. {
  22136. return error_node();
  22137. }
  22138. else if (is_invalid_break_continue_op(branch))
  22139. {
  22140. return error_node();
  22141. }
  22142. else if (details::e_assign == operation)
  22143. {
  22144. return synthesize_assignment_expression(operation, branch);
  22145. }
  22146. else if (details::e_swap == operation)
  22147. {
  22148. return synthesize_swap_expression(branch);
  22149. }
  22150. else if (is_assignment_operation(operation))
  22151. {
  22152. return synthesize_assignment_operation_expression(operation, branch);
  22153. }
  22154. else if (is_vector_eqineq_logic_operation(operation, branch))
  22155. {
  22156. return synthesize_veceqineqlogic_operation_expression(operation, branch);
  22157. }
  22158. else if (is_vector_arithmetic_operation(operation, branch))
  22159. {
  22160. return synthesize_vecarithmetic_operation_expression(operation, branch);
  22161. }
  22162. else if (is_shortcircuit_expression(operation))
  22163. {
  22164. return synthesize_shortcircuit_expression(operation, branch);
  22165. }
  22166. else if (is_string_operation(operation, branch))
  22167. {
  22168. return synthesize_string_expression(operation, branch);
  22169. }
  22170. else if (is_null_present(branch))
  22171. {
  22172. return synthesize_null_expression(operation, branch);
  22173. }
  22174. #ifndef exprtk_disable_cardinal_pow_optimisation
  22175. else if (is_constpow_operation(operation, branch))
  22176. {
  22177. return cardinal_pow_optimisation(branch);
  22178. }
  22179. #endif
  22180. expression_node_ptr result = error_node();
  22181. #ifndef exprtk_disable_enhanced_features
  22182. if (synthesize_expression(operation, branch, result))
  22183. {
  22184. return result;
  22185. }
  22186. else
  22187. #endif
  22188. {
  22189. /*
  22190. Possible reductions:
  22191. 1. c o cob -> cob
  22192. 2. cob o c -> cob
  22193. 3. c o boc -> boc
  22194. 4. boc o c -> boc
  22195. */
  22196. result = error_node();
  22197. if (cocob_optimisable(operation, branch))
  22198. {
  22199. result = synthesize_cocob_expression::process((*this), operation, branch);
  22200. }
  22201. else if (coboc_optimisable(operation, branch) && (0 == result))
  22202. {
  22203. result = synthesize_coboc_expression::process((*this), operation, branch);
  22204. }
  22205. if (result)
  22206. return result;
  22207. }
  22208. if (uvouv_optimisable(operation, branch))
  22209. {
  22210. return synthesize_uvouv_expression(operation, branch);
  22211. }
  22212. else if (vob_optimisable(operation, branch))
  22213. {
  22214. return synthesize_vob_expression::process((*this), operation, branch);
  22215. }
  22216. else if (bov_optimisable(operation, branch))
  22217. {
  22218. return synthesize_bov_expression::process((*this), operation, branch);
  22219. }
  22220. else if (cob_optimisable(operation, branch))
  22221. {
  22222. return synthesize_cob_expression::process((*this), operation, branch);
  22223. }
  22224. else if (boc_optimisable(operation, branch))
  22225. {
  22226. return synthesize_boc_expression::process((*this), operation, branch);
  22227. }
  22228. #ifndef exprtk_disable_enhanced_features
  22229. else if (cov_optimisable(operation, branch))
  22230. {
  22231. return synthesize_cov_expression::process((*this), operation, branch);
  22232. }
  22233. #endif
  22234. else if (binext_optimisable(operation, branch))
  22235. {
  22236. return synthesize_binary_ext_expression::process((*this), operation, branch);
  22237. }
  22238. else
  22239. return synthesize_expression<binary_node_t,2>(operation, branch);
  22240. }
  22241. inline expression_node_ptr operator() (const details::operator_type& operation, expression_node_ptr (&branch)[3])
  22242. {
  22243. if (
  22244. (0 == branch[0]) ||
  22245. (0 == branch[1]) ||
  22246. (0 == branch[2])
  22247. )
  22248. {
  22249. details::free_all_nodes(*node_allocator_,branch);
  22250. return error_node();
  22251. }
  22252. else if (is_invalid_string_op(operation, branch))
  22253. {
  22254. return error_node();
  22255. }
  22256. else if (is_string_operation(operation, branch))
  22257. {
  22258. return synthesize_string_expression(operation, branch);
  22259. }
  22260. else
  22261. return synthesize_expression<trinary_node_t,3>(operation, branch);
  22262. }
  22263. inline expression_node_ptr operator() (const details::operator_type& operation, expression_node_ptr (&branch)[4])
  22264. {
  22265. return synthesize_expression<quaternary_node_t,4>(operation,branch);
  22266. }
  22267. inline expression_node_ptr operator() (const details::operator_type& operation, expression_node_ptr b0)
  22268. {
  22269. expression_node_ptr branch[1] = { b0 };
  22270. return (*this)(operation,branch);
  22271. }
  22272. inline expression_node_ptr operator() (const details::operator_type& operation, expression_node_ptr& b0, expression_node_ptr& b1)
  22273. {
  22274. expression_node_ptr result = error_node();
  22275. if ((0 != b0) && (0 != b1))
  22276. {
  22277. expression_node_ptr branch[2] = { b0, b1 };
  22278. result = expression_generator<Type>::operator()(operation, branch);
  22279. b0 = branch[0];
  22280. b1 = branch[1];
  22281. }
  22282. return result;
  22283. }
  22284. inline expression_node_ptr conditional(expression_node_ptr condition,
  22285. expression_node_ptr consequent,
  22286. expression_node_ptr alternative) const
  22287. {
  22288. if ((0 == condition) || (0 == consequent))
  22289. {
  22290. free_node(*node_allocator_, condition);
  22291. free_node(*node_allocator_, consequent);
  22292. free_node(*node_allocator_, alternative);
  22293. return error_node();
  22294. }
  22295. // Can the condition be immediately evaluated? if so optimise.
  22296. else if (details::is_constant_node(condition))
  22297. {
  22298. // True branch
  22299. if (details::is_true(condition))
  22300. {
  22301. free_node(*node_allocator_, condition);
  22302. free_node(*node_allocator_, alternative);
  22303. return consequent;
  22304. }
  22305. // False branch
  22306. else
  22307. {
  22308. free_node(*node_allocator_, condition);
  22309. free_node(*node_allocator_, consequent);
  22310. if (alternative)
  22311. return alternative;
  22312. else
  22313. return node_allocator_->allocate<details::null_node<T> >();
  22314. }
  22315. }
  22316. else if ((0 != consequent) && (0 != alternative))
  22317. {
  22318. return node_allocator_->
  22319. allocate<conditional_node_t>(condition, consequent, alternative);
  22320. }
  22321. else
  22322. return node_allocator_->
  22323. allocate<cons_conditional_node_t>(condition, consequent);
  22324. }
  22325. #ifndef exprtk_disable_string_capabilities
  22326. inline expression_node_ptr conditional_string(expression_node_ptr condition,
  22327. expression_node_ptr consequent,
  22328. expression_node_ptr alternative) const
  22329. {
  22330. if ((0 == condition) || (0 == consequent))
  22331. {
  22332. free_node(*node_allocator_, condition);
  22333. free_node(*node_allocator_, consequent);
  22334. free_node(*node_allocator_, alternative);
  22335. return error_node();
  22336. }
  22337. // Can the condition be immediately evaluated? if so optimise.
  22338. else if (details::is_constant_node(condition))
  22339. {
  22340. // True branch
  22341. if (details::is_true(condition))
  22342. {
  22343. free_node(*node_allocator_, condition);
  22344. free_node(*node_allocator_, alternative);
  22345. return consequent;
  22346. }
  22347. // False branch
  22348. else
  22349. {
  22350. free_node(*node_allocator_, condition);
  22351. free_node(*node_allocator_, consequent);
  22352. if (alternative)
  22353. return alternative;
  22354. else
  22355. return node_allocator_->
  22356. allocate_c<details::string_literal_node<Type> >("");
  22357. }
  22358. }
  22359. else if ((0 != consequent) && (0 != alternative))
  22360. return node_allocator_->
  22361. allocate<conditional_string_node_t>(condition, consequent, alternative);
  22362. else
  22363. return error_node();
  22364. }
  22365. #else
  22366. inline expression_node_ptr conditional_string(expression_node_ptr,
  22367. expression_node_ptr,
  22368. expression_node_ptr) const
  22369. {
  22370. return error_node();
  22371. }
  22372. #endif
  22373. inline expression_node_ptr while_loop(expression_node_ptr& condition,
  22374. expression_node_ptr& branch,
  22375. const bool brkcont = false) const
  22376. {
  22377. if (!brkcont && details::is_constant_node(condition))
  22378. {
  22379. expression_node_ptr result = error_node();
  22380. if (details::is_true(condition))
  22381. // Infinite loops are not allowed.
  22382. result = error_node();
  22383. else
  22384. result = node_allocator_->allocate<details::null_node<Type> >();
  22385. free_node(*node_allocator_, condition);
  22386. free_node(*node_allocator_, branch);
  22387. return result;
  22388. }
  22389. else if (details::is_null_node(condition))
  22390. {
  22391. free_node(*node_allocator_,condition);
  22392. return branch;
  22393. }
  22394. else if (!brkcont)
  22395. return node_allocator_->allocate<while_loop_node_t>(condition,branch);
  22396. #ifndef exprtk_disable_break_continue
  22397. else
  22398. return node_allocator_->allocate<while_loop_bc_node_t>(condition,branch);
  22399. #else
  22400. return error_node();
  22401. #endif
  22402. }
  22403. inline expression_node_ptr repeat_until_loop(expression_node_ptr& condition,
  22404. expression_node_ptr& branch,
  22405. const bool brkcont = false) const
  22406. {
  22407. if (!brkcont && details::is_constant_node(condition))
  22408. {
  22409. if (
  22410. details::is_true(condition) &&
  22411. details::is_constant_node(branch)
  22412. )
  22413. {
  22414. free_node(*node_allocator_,condition);
  22415. return branch;
  22416. }
  22417. free_node(*node_allocator_, condition);
  22418. free_node(*node_allocator_, branch);
  22419. return error_node();
  22420. }
  22421. else if (details::is_null_node(condition))
  22422. {
  22423. free_node(*node_allocator_,condition);
  22424. return branch;
  22425. }
  22426. else if (!brkcont)
  22427. return node_allocator_->allocate<repeat_until_loop_node_t>(condition,branch);
  22428. #ifndef exprtk_disable_break_continue
  22429. else
  22430. return node_allocator_->allocate<repeat_until_loop_bc_node_t>(condition,branch);
  22431. #else
  22432. return error_node();
  22433. #endif
  22434. }
  22435. inline expression_node_ptr for_loop(expression_node_ptr& initialiser,
  22436. expression_node_ptr& condition,
  22437. expression_node_ptr& incrementor,
  22438. expression_node_ptr& loop_body,
  22439. bool brkcont = false) const
  22440. {
  22441. if (!brkcont && details::is_constant_node(condition))
  22442. {
  22443. expression_node_ptr result = error_node();
  22444. if (details::is_true(condition))
  22445. // Infinite loops are not allowed.
  22446. result = error_node();
  22447. else
  22448. result = node_allocator_->allocate<details::null_node<Type> >();
  22449. free_node(*node_allocator_, initialiser);
  22450. free_node(*node_allocator_, condition);
  22451. free_node(*node_allocator_, incrementor);
  22452. free_node(*node_allocator_, loop_body);
  22453. return result;
  22454. }
  22455. else if (details::is_null_node(condition) || (0 == condition))
  22456. {
  22457. free_node(*node_allocator_, initialiser);
  22458. free_node(*node_allocator_, condition);
  22459. free_node(*node_allocator_, incrementor);
  22460. return loop_body;
  22461. }
  22462. else if (!brkcont)
  22463. return node_allocator_->allocate<for_loop_node_t>
  22464. (
  22465. initialiser,
  22466. condition,
  22467. incrementor,
  22468. loop_body
  22469. );
  22470. #ifndef exprtk_disable_break_continue
  22471. else
  22472. return node_allocator_->allocate<for_loop_bc_node_t>
  22473. (
  22474. initialiser,
  22475. condition,
  22476. incrementor,
  22477. loop_body
  22478. );
  22479. #else
  22480. return error_node();
  22481. #endif
  22482. }
  22483. template <typename Allocator,
  22484. template <typename, typename> class Sequence>
  22485. inline expression_node_ptr const_optimise_switch(Sequence<expression_node_ptr,Allocator>& arg_list)
  22486. {
  22487. expression_node_ptr result = error_node();
  22488. for (std::size_t i = 0; i < (arg_list.size() / 2); ++i)
  22489. {
  22490. expression_node_ptr condition = arg_list[(2 * i) ];
  22491. expression_node_ptr consequent = arg_list[(2 * i) + 1];
  22492. if ((0 == result) && details::is_true(condition))
  22493. {
  22494. result = consequent;
  22495. break;
  22496. }
  22497. }
  22498. if (0 == result)
  22499. {
  22500. result = arg_list.back();
  22501. }
  22502. for (std::size_t i = 0; i < arg_list.size(); ++i)
  22503. {
  22504. expression_node_ptr current_expr = arg_list[i];
  22505. if (current_expr && (current_expr != result))
  22506. {
  22507. free_node(*node_allocator_,current_expr);
  22508. }
  22509. }
  22510. return result;
  22511. }
  22512. template <typename Allocator,
  22513. template <typename, typename> class Sequence>
  22514. inline expression_node_ptr const_optimise_mswitch(Sequence<expression_node_ptr,Allocator>& arg_list)
  22515. {
  22516. expression_node_ptr result = error_node();
  22517. for (std::size_t i = 0; i < (arg_list.size() / 2); ++i)
  22518. {
  22519. expression_node_ptr condition = arg_list[(2 * i) ];
  22520. expression_node_ptr consequent = arg_list[(2 * i) + 1];
  22521. if (details::is_true(condition))
  22522. {
  22523. result = consequent;
  22524. }
  22525. }
  22526. if (0 == result)
  22527. {
  22528. T zero = T(0);
  22529. result = node_allocator_->allocate<literal_node_t>(zero);
  22530. }
  22531. for (std::size_t i = 0; i < arg_list.size(); ++i)
  22532. {
  22533. expression_node_ptr& current_expr = arg_list[i];
  22534. if (current_expr && (current_expr != result))
  22535. {
  22536. free_node(*node_allocator_,current_expr);
  22537. }
  22538. }
  22539. return result;
  22540. }
  22541. struct switch_nodes
  22542. {
  22543. typedef std::vector<expression_node_ptr> arg_list_t;
  22544. #define case_stmt(N) \
  22545. if (is_true(arg[(2 * N)])) { return arg[(2 * N) + 1]->value(); } \
  22546. struct switch_1
  22547. {
  22548. static inline T process(const arg_list_t& arg)
  22549. {
  22550. case_stmt(0)
  22551. return arg.back()->value();
  22552. }
  22553. };
  22554. struct switch_2
  22555. {
  22556. static inline T process(const arg_list_t& arg)
  22557. {
  22558. case_stmt(0) case_stmt(1)
  22559. return arg.back()->value();
  22560. }
  22561. };
  22562. struct switch_3
  22563. {
  22564. static inline T process(const arg_list_t& arg)
  22565. {
  22566. case_stmt(0) case_stmt(1)
  22567. case_stmt(2)
  22568. return arg.back()->value();
  22569. }
  22570. };
  22571. struct switch_4
  22572. {
  22573. static inline T process(const arg_list_t& arg)
  22574. {
  22575. case_stmt(0) case_stmt(1)
  22576. case_stmt(2) case_stmt(3)
  22577. return arg.back()->value();
  22578. }
  22579. };
  22580. struct switch_5
  22581. {
  22582. static inline T process(const arg_list_t& arg)
  22583. {
  22584. case_stmt(0) case_stmt(1)
  22585. case_stmt(2) case_stmt(3)
  22586. case_stmt(4)
  22587. return arg.back()->value();
  22588. }
  22589. };
  22590. struct switch_6
  22591. {
  22592. static inline T process(const arg_list_t& arg)
  22593. {
  22594. case_stmt(0) case_stmt(1)
  22595. case_stmt(2) case_stmt(3)
  22596. case_stmt(4) case_stmt(5)
  22597. return arg.back()->value();
  22598. }
  22599. };
  22600. struct switch_7
  22601. {
  22602. static inline T process(const arg_list_t& arg)
  22603. {
  22604. case_stmt(0) case_stmt(1)
  22605. case_stmt(2) case_stmt(3)
  22606. case_stmt(4) case_stmt(5)
  22607. case_stmt(6)
  22608. return arg.back()->value();
  22609. }
  22610. };
  22611. #undef case_stmt
  22612. };
  22613. template <typename Allocator,
  22614. template <typename, typename> class Sequence>
  22615. inline expression_node_ptr switch_statement(Sequence<expression_node_ptr,Allocator>& arg_list)
  22616. {
  22617. if (arg_list.empty())
  22618. return error_node();
  22619. else if (
  22620. !all_nodes_valid(arg_list) ||
  22621. (arg_list.size() < 3) ||
  22622. ((arg_list.size() % 2) != 1)
  22623. )
  22624. {
  22625. details::free_all_nodes(*node_allocator_,arg_list);
  22626. return error_node();
  22627. }
  22628. else if (is_constant_foldable(arg_list))
  22629. return const_optimise_switch(arg_list);
  22630. switch ((arg_list.size() - 1) / 2)
  22631. {
  22632. #define case_stmt(N) \
  22633. case N : \
  22634. return node_allocator_-> \
  22635. allocate<details::switch_n_node \
  22636. <Type,typename switch_nodes::switch_##N> >(arg_list); \
  22637. case_stmt(1)
  22638. case_stmt(2)
  22639. case_stmt(3)
  22640. case_stmt(4)
  22641. case_stmt(5)
  22642. case_stmt(6)
  22643. case_stmt(7)
  22644. #undef case_stmt
  22645. default : return node_allocator_->allocate<details::switch_node<Type> >(arg_list);
  22646. }
  22647. }
  22648. template <typename Allocator,
  22649. template <typename, typename> class Sequence>
  22650. inline expression_node_ptr multi_switch_statement(Sequence<expression_node_ptr,Allocator>& arg_list)
  22651. {
  22652. if (!all_nodes_valid(arg_list))
  22653. {
  22654. details::free_all_nodes(*node_allocator_,arg_list);
  22655. return error_node();
  22656. }
  22657. else if (is_constant_foldable(arg_list))
  22658. return const_optimise_mswitch(arg_list);
  22659. else
  22660. return node_allocator_->allocate<details::multi_switch_node<Type> >(arg_list);
  22661. }
  22662. #define unary_opr_switch_statements \
  22663. case_stmt(details:: e_abs, details:: abs_op) \
  22664. case_stmt(details:: e_acos, details:: acos_op) \
  22665. case_stmt(details::e_acosh, details::acosh_op) \
  22666. case_stmt(details:: e_asin, details:: asin_op) \
  22667. case_stmt(details::e_asinh, details::asinh_op) \
  22668. case_stmt(details:: e_atan, details:: atan_op) \
  22669. case_stmt(details::e_atanh, details::atanh_op) \
  22670. case_stmt(details:: e_ceil, details:: ceil_op) \
  22671. case_stmt(details:: e_cos, details:: cos_op) \
  22672. case_stmt(details:: e_cosh, details:: cosh_op) \
  22673. case_stmt(details:: e_exp, details:: exp_op) \
  22674. case_stmt(details::e_expm1, details::expm1_op) \
  22675. case_stmt(details::e_floor, details::floor_op) \
  22676. case_stmt(details:: e_log, details:: log_op) \
  22677. case_stmt(details::e_log10, details::log10_op) \
  22678. case_stmt(details:: e_log2, details:: log2_op) \
  22679. case_stmt(details::e_log1p, details::log1p_op) \
  22680. case_stmt(details:: e_neg, details:: neg_op) \
  22681. case_stmt(details:: e_pos, details:: pos_op) \
  22682. case_stmt(details::e_round, details::round_op) \
  22683. case_stmt(details:: e_sin, details:: sin_op) \
  22684. case_stmt(details:: e_sinc, details:: sinc_op) \
  22685. case_stmt(details:: e_sinh, details:: sinh_op) \
  22686. case_stmt(details:: e_sqrt, details:: sqrt_op) \
  22687. case_stmt(details:: e_tan, details:: tan_op) \
  22688. case_stmt(details:: e_tanh, details:: tanh_op) \
  22689. case_stmt(details:: e_cot, details:: cot_op) \
  22690. case_stmt(details:: e_sec, details:: sec_op) \
  22691. case_stmt(details:: e_csc, details:: csc_op) \
  22692. case_stmt(details:: e_r2d, details:: r2d_op) \
  22693. case_stmt(details:: e_d2r, details:: d2r_op) \
  22694. case_stmt(details:: e_d2g, details:: d2g_op) \
  22695. case_stmt(details:: e_g2d, details:: g2d_op) \
  22696. case_stmt(details:: e_notl, details:: notl_op) \
  22697. case_stmt(details:: e_sgn, details:: sgn_op) \
  22698. case_stmt(details:: e_erf, details:: erf_op) \
  22699. case_stmt(details:: e_erfc, details:: erfc_op) \
  22700. case_stmt(details:: e_ncdf, details:: ncdf_op) \
  22701. case_stmt(details:: e_frac, details:: frac_op) \
  22702. case_stmt(details::e_trunc, details::trunc_op) \
  22703. inline expression_node_ptr synthesize_uv_expression(const details::operator_type& operation,
  22704. expression_node_ptr (&branch)[1])
  22705. {
  22706. T& v = static_cast<details::variable_node<T>*>(branch[0])->ref();
  22707. switch (operation)
  22708. {
  22709. #define case_stmt(op0,op1) \
  22710. case op0 : return node_allocator_-> \
  22711. allocate<typename details::unary_variable_node<Type,op1<Type> > >(v); \
  22712. unary_opr_switch_statements
  22713. #undef case_stmt
  22714. default : return error_node();
  22715. }
  22716. }
  22717. inline expression_node_ptr synthesize_uvec_expression(const details::operator_type& operation,
  22718. expression_node_ptr (&branch)[1])
  22719. {
  22720. switch (operation)
  22721. {
  22722. #define case_stmt(op0,op1) \
  22723. case op0 : return node_allocator_-> \
  22724. allocate<typename details::unary_vector_node<Type,op1<Type> > > \
  22725. (operation, branch[0]); \
  22726. unary_opr_switch_statements
  22727. #undef case_stmt
  22728. default : return error_node();
  22729. }
  22730. }
  22731. inline expression_node_ptr synthesize_unary_expression(const details::operator_type& operation,
  22732. expression_node_ptr (&branch)[1])
  22733. {
  22734. switch (operation)
  22735. {
  22736. #define case_stmt(op0,op1) \
  22737. case op0 : return node_allocator_-> \
  22738. allocate<typename details::unary_branch_node<Type,op1<Type> > >(branch[0]); \
  22739. unary_opr_switch_statements
  22740. #undef case_stmt
  22741. default : return error_node();
  22742. }
  22743. }
  22744. inline expression_node_ptr const_optimise_sf3(const details::operator_type& operation,
  22745. expression_node_ptr (&branch)[3])
  22746. {
  22747. expression_node_ptr temp_node = error_node();
  22748. switch (operation)
  22749. {
  22750. #define case_stmt(op) \
  22751. case details::e_sf##op : temp_node = node_allocator_-> \
  22752. allocate<details::sf3_node<Type,details::sf##op##_op<Type> > > \
  22753. (operation, branch); \
  22754. break; \
  22755. case_stmt(00) case_stmt(01) case_stmt(02) case_stmt(03)
  22756. case_stmt(04) case_stmt(05) case_stmt(06) case_stmt(07)
  22757. case_stmt(08) case_stmt(09) case_stmt(10) case_stmt(11)
  22758. case_stmt(12) case_stmt(13) case_stmt(14) case_stmt(15)
  22759. case_stmt(16) case_stmt(17) case_stmt(18) case_stmt(19)
  22760. case_stmt(20) case_stmt(21) case_stmt(22) case_stmt(23)
  22761. case_stmt(24) case_stmt(25) case_stmt(26) case_stmt(27)
  22762. case_stmt(28) case_stmt(29) case_stmt(30) case_stmt(31)
  22763. case_stmt(32) case_stmt(33) case_stmt(34) case_stmt(35)
  22764. case_stmt(36) case_stmt(37) case_stmt(38) case_stmt(39)
  22765. case_stmt(40) case_stmt(41) case_stmt(42) case_stmt(43)
  22766. case_stmt(44) case_stmt(45) case_stmt(46) case_stmt(47)
  22767. #undef case_stmt
  22768. default : return error_node();
  22769. }
  22770. const T v = temp_node->value();
  22771. details::free_node(*node_allocator_,temp_node);
  22772. return node_allocator_->allocate<literal_node_t>(v);
  22773. }
  22774. inline expression_node_ptr varnode_optimise_sf3(const details::operator_type& operation, expression_node_ptr (&branch)[3])
  22775. {
  22776. typedef details::variable_node<Type>* variable_ptr;
  22777. const Type& v0 = static_cast<variable_ptr>(branch[0])->ref();
  22778. const Type& v1 = static_cast<variable_ptr>(branch[1])->ref();
  22779. const Type& v2 = static_cast<variable_ptr>(branch[2])->ref();
  22780. switch (operation)
  22781. {
  22782. #define case_stmt(op) \
  22783. case details::e_sf##op : return node_allocator_-> \
  22784. allocate_rrr<details::sf3_var_node<Type,details::sf##op##_op<Type> > > \
  22785. (v0, v1, v2); \
  22786. case_stmt(00) case_stmt(01) case_stmt(02) case_stmt(03)
  22787. case_stmt(04) case_stmt(05) case_stmt(06) case_stmt(07)
  22788. case_stmt(08) case_stmt(09) case_stmt(10) case_stmt(11)
  22789. case_stmt(12) case_stmt(13) case_stmt(14) case_stmt(15)
  22790. case_stmt(16) case_stmt(17) case_stmt(18) case_stmt(19)
  22791. case_stmt(20) case_stmt(21) case_stmt(22) case_stmt(23)
  22792. case_stmt(24) case_stmt(25) case_stmt(26) case_stmt(27)
  22793. case_stmt(28) case_stmt(29) case_stmt(30) case_stmt(31)
  22794. case_stmt(32) case_stmt(33) case_stmt(34) case_stmt(35)
  22795. case_stmt(36) case_stmt(37) case_stmt(38) case_stmt(39)
  22796. case_stmt(40) case_stmt(41) case_stmt(42) case_stmt(43)
  22797. case_stmt(44) case_stmt(45) case_stmt(46) case_stmt(47)
  22798. #undef case_stmt
  22799. default : return error_node();
  22800. }
  22801. }
  22802. inline expression_node_ptr special_function(const details::operator_type& operation, expression_node_ptr (&branch)[3])
  22803. {
  22804. if (!all_nodes_valid(branch))
  22805. return error_node();
  22806. else if (is_constant_foldable(branch))
  22807. return const_optimise_sf3(operation,branch);
  22808. else if (all_nodes_variables(branch))
  22809. return varnode_optimise_sf3(operation,branch);
  22810. else
  22811. {
  22812. switch (operation)
  22813. {
  22814. #define case_stmt(op) \
  22815. case details::e_sf##op : return node_allocator_-> \
  22816. allocate<details::sf3_node<Type,details::sf##op##_op<Type> > > \
  22817. (operation, branch); \
  22818. case_stmt(00) case_stmt(01) case_stmt(02) case_stmt(03)
  22819. case_stmt(04) case_stmt(05) case_stmt(06) case_stmt(07)
  22820. case_stmt(08) case_stmt(09) case_stmt(10) case_stmt(11)
  22821. case_stmt(12) case_stmt(13) case_stmt(14) case_stmt(15)
  22822. case_stmt(16) case_stmt(17) case_stmt(18) case_stmt(19)
  22823. case_stmt(20) case_stmt(21) case_stmt(22) case_stmt(23)
  22824. case_stmt(24) case_stmt(25) case_stmt(26) case_stmt(27)
  22825. case_stmt(28) case_stmt(29) case_stmt(30) case_stmt(31)
  22826. case_stmt(32) case_stmt(33) case_stmt(34) case_stmt(35)
  22827. case_stmt(36) case_stmt(37) case_stmt(38) case_stmt(39)
  22828. case_stmt(40) case_stmt(41) case_stmt(42) case_stmt(43)
  22829. case_stmt(44) case_stmt(45) case_stmt(46) case_stmt(47)
  22830. #undef case_stmt
  22831. default : return error_node();
  22832. }
  22833. }
  22834. }
  22835. inline expression_node_ptr const_optimise_sf4(const details::operator_type& operation, expression_node_ptr (&branch)[4])
  22836. {
  22837. expression_node_ptr temp_node = error_node();
  22838. switch (operation)
  22839. {
  22840. #define case_stmt(op) \
  22841. case details::e_sf##op : temp_node = node_allocator_-> \
  22842. allocate<details::sf4_node<Type,details::sf##op##_op<Type> > > \
  22843. (operation, branch); \
  22844. break; \
  22845. case_stmt(48) case_stmt(49) case_stmt(50) case_stmt(51)
  22846. case_stmt(52) case_stmt(53) case_stmt(54) case_stmt(55)
  22847. case_stmt(56) case_stmt(57) case_stmt(58) case_stmt(59)
  22848. case_stmt(60) case_stmt(61) case_stmt(62) case_stmt(63)
  22849. case_stmt(64) case_stmt(65) case_stmt(66) case_stmt(67)
  22850. case_stmt(68) case_stmt(69) case_stmt(70) case_stmt(71)
  22851. case_stmt(72) case_stmt(73) case_stmt(74) case_stmt(75)
  22852. case_stmt(76) case_stmt(77) case_stmt(78) case_stmt(79)
  22853. case_stmt(80) case_stmt(81) case_stmt(82) case_stmt(83)
  22854. case_stmt(84) case_stmt(85) case_stmt(86) case_stmt(87)
  22855. case_stmt(88) case_stmt(89) case_stmt(90) case_stmt(91)
  22856. case_stmt(92) case_stmt(93) case_stmt(94) case_stmt(95)
  22857. case_stmt(96) case_stmt(97) case_stmt(98) case_stmt(99)
  22858. #undef case_stmt
  22859. default : return error_node();
  22860. }
  22861. const T v = temp_node->value();
  22862. details::free_node(*node_allocator_,temp_node);
  22863. return node_allocator_->allocate<literal_node_t>(v);
  22864. }
  22865. inline expression_node_ptr varnode_optimise_sf4(const details::operator_type& operation, expression_node_ptr (&branch)[4])
  22866. {
  22867. typedef details::variable_node<Type>* variable_ptr;
  22868. const Type& v0 = static_cast<variable_ptr>(branch[0])->ref();
  22869. const Type& v1 = static_cast<variable_ptr>(branch[1])->ref();
  22870. const Type& v2 = static_cast<variable_ptr>(branch[2])->ref();
  22871. const Type& v3 = static_cast<variable_ptr>(branch[3])->ref();
  22872. switch (operation)
  22873. {
  22874. #define case_stmt(op) \
  22875. case details::e_sf##op : return node_allocator_-> \
  22876. allocate_rrrr<details::sf4_var_node<Type,details::sf##op##_op<Type> > > \
  22877. (v0, v1, v2, v3); \
  22878. case_stmt(48) case_stmt(49) case_stmt(50) case_stmt(51)
  22879. case_stmt(52) case_stmt(53) case_stmt(54) case_stmt(55)
  22880. case_stmt(56) case_stmt(57) case_stmt(58) case_stmt(59)
  22881. case_stmt(60) case_stmt(61) case_stmt(62) case_stmt(63)
  22882. case_stmt(64) case_stmt(65) case_stmt(66) case_stmt(67)
  22883. case_stmt(68) case_stmt(69) case_stmt(70) case_stmt(71)
  22884. case_stmt(72) case_stmt(73) case_stmt(74) case_stmt(75)
  22885. case_stmt(76) case_stmt(77) case_stmt(78) case_stmt(79)
  22886. case_stmt(80) case_stmt(81) case_stmt(82) case_stmt(83)
  22887. case_stmt(84) case_stmt(85) case_stmt(86) case_stmt(87)
  22888. case_stmt(88) case_stmt(89) case_stmt(90) case_stmt(91)
  22889. case_stmt(92) case_stmt(93) case_stmt(94) case_stmt(95)
  22890. case_stmt(96) case_stmt(97) case_stmt(98) case_stmt(99)
  22891. #undef case_stmt
  22892. default : return error_node();
  22893. }
  22894. }
  22895. inline expression_node_ptr special_function(const details::operator_type& operation, expression_node_ptr (&branch)[4])
  22896. {
  22897. if (!all_nodes_valid(branch))
  22898. return error_node();
  22899. else if (is_constant_foldable(branch))
  22900. return const_optimise_sf4(operation,branch);
  22901. else if (all_nodes_variables(branch))
  22902. return varnode_optimise_sf4(operation,branch);
  22903. switch (operation)
  22904. {
  22905. #define case_stmt(op) \
  22906. case details::e_sf##op : return node_allocator_-> \
  22907. allocate<details::sf4_node<Type,details::sf##op##_op<Type> > > \
  22908. (operation, branch); \
  22909. case_stmt(48) case_stmt(49) case_stmt(50) case_stmt(51)
  22910. case_stmt(52) case_stmt(53) case_stmt(54) case_stmt(55)
  22911. case_stmt(56) case_stmt(57) case_stmt(58) case_stmt(59)
  22912. case_stmt(60) case_stmt(61) case_stmt(62) case_stmt(63)
  22913. case_stmt(64) case_stmt(65) case_stmt(66) case_stmt(67)
  22914. case_stmt(68) case_stmt(69) case_stmt(70) case_stmt(71)
  22915. case_stmt(72) case_stmt(73) case_stmt(74) case_stmt(75)
  22916. case_stmt(76) case_stmt(77) case_stmt(78) case_stmt(79)
  22917. case_stmt(80) case_stmt(81) case_stmt(82) case_stmt(83)
  22918. case_stmt(84) case_stmt(85) case_stmt(86) case_stmt(87)
  22919. case_stmt(88) case_stmt(89) case_stmt(90) case_stmt(91)
  22920. case_stmt(92) case_stmt(93) case_stmt(94) case_stmt(95)
  22921. case_stmt(96) case_stmt(97) case_stmt(98) case_stmt(99)
  22922. #undef case_stmt
  22923. default : return error_node();
  22924. }
  22925. }
  22926. template <typename Allocator,
  22927. template <typename, typename> class Sequence>
  22928. inline expression_node_ptr const_optimise_varargfunc(const details::operator_type& operation, Sequence<expression_node_ptr,Allocator>& arg_list)
  22929. {
  22930. expression_node_ptr temp_node = error_node();
  22931. switch (operation)
  22932. {
  22933. #define case_stmt(op0,op1) \
  22934. case op0 : temp_node = node_allocator_-> \
  22935. allocate<details::vararg_node<Type,op1<Type> > > \
  22936. (arg_list); \
  22937. break; \
  22938. case_stmt(details::e_sum , details::vararg_add_op )
  22939. case_stmt(details::e_prod , details::vararg_mul_op )
  22940. case_stmt(details::e_avg , details::vararg_avg_op )
  22941. case_stmt(details::e_min , details::vararg_min_op )
  22942. case_stmt(details::e_max , details::vararg_max_op )
  22943. case_stmt(details::e_mand , details::vararg_mand_op )
  22944. case_stmt(details::e_mor , details::vararg_mor_op )
  22945. case_stmt(details::e_multi , details::vararg_multi_op)
  22946. #undef case_stmt
  22947. default : return error_node();
  22948. }
  22949. const T v = temp_node->value();
  22950. details::free_node(*node_allocator_,temp_node);
  22951. return node_allocator_->allocate<literal_node_t>(v);
  22952. }
  22953. inline bool special_one_parameter_vararg(const details::operator_type& operation) const
  22954. {
  22955. return (
  22956. (details::e_sum == operation) ||
  22957. (details::e_prod == operation) ||
  22958. (details::e_avg == operation) ||
  22959. (details::e_min == operation) ||
  22960. (details::e_max == operation)
  22961. );
  22962. }
  22963. template <typename Allocator,
  22964. template <typename, typename> class Sequence>
  22965. inline expression_node_ptr varnode_optimise_varargfunc(const details::operator_type& operation, Sequence<expression_node_ptr,Allocator>& arg_list)
  22966. {
  22967. switch (operation)
  22968. {
  22969. #define case_stmt(op0,op1) \
  22970. case op0 : return node_allocator_-> \
  22971. allocate<details::vararg_varnode<Type,op1<Type> > >(arg_list); \
  22972. case_stmt(details::e_sum , details::vararg_add_op )
  22973. case_stmt(details::e_prod , details::vararg_mul_op )
  22974. case_stmt(details::e_avg , details::vararg_avg_op )
  22975. case_stmt(details::e_min , details::vararg_min_op )
  22976. case_stmt(details::e_max , details::vararg_max_op )
  22977. case_stmt(details::e_mand , details::vararg_mand_op )
  22978. case_stmt(details::e_mor , details::vararg_mor_op )
  22979. case_stmt(details::e_multi , details::vararg_multi_op)
  22980. #undef case_stmt
  22981. default : return error_node();
  22982. }
  22983. }
  22984. template <typename Allocator,
  22985. template <typename, typename> class Sequence>
  22986. inline expression_node_ptr vectorize_func(const details::operator_type& operation, Sequence<expression_node_ptr,Allocator>& arg_list)
  22987. {
  22988. if (1 == arg_list.size())
  22989. {
  22990. switch (operation)
  22991. {
  22992. #define case_stmt(op0,op1) \
  22993. case op0 : return node_allocator_-> \
  22994. allocate<details::vectorize_node<Type,op1<Type> > >(arg_list[0]); \
  22995. case_stmt(details::e_sum , details::vec_add_op)
  22996. case_stmt(details::e_prod , details::vec_mul_op)
  22997. case_stmt(details::e_avg , details::vec_avg_op)
  22998. case_stmt(details::e_min , details::vec_min_op)
  22999. case_stmt(details::e_max , details::vec_max_op)
  23000. #undef case_stmt
  23001. default : return error_node();
  23002. }
  23003. }
  23004. else
  23005. return error_node();
  23006. }
  23007. template <typename Allocator,
  23008. template <typename, typename> class Sequence>
  23009. inline expression_node_ptr vararg_function(const details::operator_type& operation, Sequence<expression_node_ptr,Allocator>& arg_list)
  23010. {
  23011. if (!all_nodes_valid(arg_list))
  23012. {
  23013. details::free_all_nodes(*node_allocator_,arg_list);
  23014. return error_node();
  23015. }
  23016. else if (is_constant_foldable(arg_list))
  23017. return const_optimise_varargfunc(operation,arg_list);
  23018. else if ((arg_list.size() == 1) && details::is_ivector_node(arg_list[0]))
  23019. return vectorize_func(operation,arg_list);
  23020. else if ((arg_list.size() == 1) && special_one_parameter_vararg(operation))
  23021. return arg_list[0];
  23022. else if (all_nodes_variables(arg_list))
  23023. return varnode_optimise_varargfunc(operation,arg_list);
  23024. #ifndef exprtk_disable_string_capabilities
  23025. if (details::e_smulti == operation)
  23026. {
  23027. return node_allocator_->
  23028. allocate<details::str_vararg_node<Type,details::vararg_multi_op<Type> > >(arg_list);
  23029. }
  23030. else
  23031. #endif
  23032. {
  23033. switch (operation)
  23034. {
  23035. #define case_stmt(op0,op1) \
  23036. case op0 : return node_allocator_-> \
  23037. allocate<details::vararg_node<Type,op1<Type> > >(arg_list); \
  23038. case_stmt(details::e_sum , details::vararg_add_op )
  23039. case_stmt(details::e_prod , details::vararg_mul_op )
  23040. case_stmt(details::e_avg , details::vararg_avg_op )
  23041. case_stmt(details::e_min , details::vararg_min_op )
  23042. case_stmt(details::e_max , details::vararg_max_op )
  23043. case_stmt(details::e_mand , details::vararg_mand_op )
  23044. case_stmt(details::e_mor , details::vararg_mor_op )
  23045. case_stmt(details::e_multi , details::vararg_multi_op)
  23046. #undef case_stmt
  23047. default : return error_node();
  23048. }
  23049. }
  23050. }
  23051. template <std::size_t N>
  23052. inline expression_node_ptr function(ifunction_t* f, expression_node_ptr (&b)[N])
  23053. {
  23054. typedef typename details::function_N_node<T,ifunction_t,N> function_N_node_t;
  23055. expression_node_ptr result = synthesize_expression<function_N_node_t,N>(f,b);
  23056. if (0 == result)
  23057. return error_node();
  23058. else
  23059. {
  23060. // Can the function call be completely optimised?
  23061. if (details::is_constant_node(result))
  23062. return result;
  23063. else if (!all_nodes_valid(b))
  23064. return error_node();
  23065. else if (N != f->param_count)
  23066. {
  23067. details::free_all_nodes(*node_allocator_,b);
  23068. return error_node();
  23069. }
  23070. function_N_node_t* func_node_ptr = static_cast<function_N_node_t*>(result);
  23071. if (func_node_ptr->init_branches(b))
  23072. return result;
  23073. else
  23074. {
  23075. details::free_all_nodes(*node_allocator_,b);
  23076. return error_node();
  23077. }
  23078. }
  23079. }
  23080. inline expression_node_ptr function(ifunction_t* f)
  23081. {
  23082. typedef typename details::function_N_node<Type,ifunction_t,0> function_N_node_t;
  23083. return node_allocator_->allocate<function_N_node_t>(f);
  23084. }
  23085. inline expression_node_ptr vararg_function_call(ivararg_function_t* vaf,
  23086. std::vector<expression_node_ptr>& arg_list)
  23087. {
  23088. if (!all_nodes_valid(arg_list))
  23089. {
  23090. details::free_all_nodes(*node_allocator_,arg_list);
  23091. return error_node();
  23092. }
  23093. typedef details::vararg_function_node<Type,ivararg_function_t> alloc_type;
  23094. expression_node_ptr result = node_allocator_->allocate<alloc_type>(vaf,arg_list);
  23095. if (
  23096. !arg_list.empty() &&
  23097. !vaf->has_side_effects() &&
  23098. is_constant_foldable(arg_list)
  23099. )
  23100. {
  23101. const Type v = result->value();
  23102. details::free_node(*node_allocator_,result);
  23103. result = node_allocator_->allocate<literal_node_t>(v);
  23104. }
  23105. parser_->state_.activate_side_effect("vararg_function_call()");
  23106. return result;
  23107. }
  23108. inline expression_node_ptr generic_function_call(igeneric_function_t* gf,
  23109. std::vector<expression_node_ptr>& arg_list,
  23110. const std::size_t& param_seq_index = std::numeric_limits<std::size_t>::max())
  23111. {
  23112. if (!all_nodes_valid(arg_list))
  23113. {
  23114. details::free_all_nodes(*node_allocator_,arg_list);
  23115. return error_node();
  23116. }
  23117. typedef details::generic_function_node <Type,igeneric_function_t> alloc_type1;
  23118. typedef details::multimode_genfunction_node<Type,igeneric_function_t> alloc_type2;
  23119. const std::size_t no_psi = std::numeric_limits<std::size_t>::max();
  23120. expression_node_ptr result = error_node();
  23121. if (no_psi == param_seq_index)
  23122. result = node_allocator_->allocate<alloc_type1>(arg_list,gf);
  23123. else
  23124. result = node_allocator_->allocate<alloc_type2>(gf, param_seq_index, arg_list);
  23125. alloc_type1* genfunc_node_ptr = static_cast<alloc_type1*>(result);
  23126. if (
  23127. !arg_list.empty() &&
  23128. !gf->has_side_effects() &&
  23129. parser_->state_.type_check_enabled &&
  23130. is_constant_foldable(arg_list)
  23131. )
  23132. {
  23133. genfunc_node_ptr->init_branches();
  23134. const Type v = result->value();
  23135. details::free_node(*node_allocator_,result);
  23136. return node_allocator_->allocate<literal_node_t>(v);
  23137. }
  23138. else if (genfunc_node_ptr->init_branches())
  23139. {
  23140. parser_->state_.activate_side_effect("generic_function_call()");
  23141. return result;
  23142. }
  23143. else
  23144. {
  23145. details::free_node(*node_allocator_, result);
  23146. details::free_all_nodes(*node_allocator_, arg_list);
  23147. return error_node();
  23148. }
  23149. }
  23150. #ifndef exprtk_disable_string_capabilities
  23151. inline expression_node_ptr string_function_call(igeneric_function_t* gf,
  23152. std::vector<expression_node_ptr>& arg_list,
  23153. const std::size_t& param_seq_index = std::numeric_limits<std::size_t>::max())
  23154. {
  23155. if (!all_nodes_valid(arg_list))
  23156. {
  23157. details::free_all_nodes(*node_allocator_,arg_list);
  23158. return error_node();
  23159. }
  23160. typedef details::string_function_node <Type,igeneric_function_t> alloc_type1;
  23161. typedef details::multimode_strfunction_node<Type,igeneric_function_t> alloc_type2;
  23162. const std::size_t no_psi = std::numeric_limits<std::size_t>::max();
  23163. expression_node_ptr result = error_node();
  23164. if (no_psi == param_seq_index)
  23165. result = node_allocator_->allocate<alloc_type1>(gf,arg_list);
  23166. else
  23167. result = node_allocator_->allocate<alloc_type2>(gf, param_seq_index, arg_list);
  23168. alloc_type1* strfunc_node_ptr = static_cast<alloc_type1*>(result);
  23169. if (
  23170. !arg_list.empty() &&
  23171. !gf->has_side_effects() &&
  23172. is_constant_foldable(arg_list)
  23173. )
  23174. {
  23175. strfunc_node_ptr->init_branches();
  23176. const Type v = result->value();
  23177. details::free_node(*node_allocator_,result);
  23178. return node_allocator_->allocate<literal_node_t>(v);
  23179. }
  23180. else if (strfunc_node_ptr->init_branches())
  23181. {
  23182. parser_->state_.activate_side_effect("string_function_call()");
  23183. return result;
  23184. }
  23185. else
  23186. {
  23187. details::free_node (*node_allocator_,result );
  23188. details::free_all_nodes(*node_allocator_,arg_list);
  23189. return error_node();
  23190. }
  23191. }
  23192. #endif
  23193. #ifndef exprtk_disable_return_statement
  23194. inline expression_node_ptr return_call(std::vector<expression_node_ptr>& arg_list)
  23195. {
  23196. if (!all_nodes_valid(arg_list))
  23197. {
  23198. details::free_all_nodes(*node_allocator_,arg_list);
  23199. return error_node();
  23200. }
  23201. typedef details::return_node<Type> alloc_type;
  23202. expression_node_ptr result = node_allocator_->
  23203. allocate_rr<alloc_type>(arg_list,parser_->results_ctx());
  23204. alloc_type* return_node_ptr = static_cast<alloc_type*>(result);
  23205. if (return_node_ptr->init_branches())
  23206. {
  23207. parser_->state_.activate_side_effect("return_call()");
  23208. return result;
  23209. }
  23210. else
  23211. {
  23212. details::free_node (*node_allocator_,result );
  23213. details::free_all_nodes(*node_allocator_,arg_list);
  23214. return error_node();
  23215. }
  23216. }
  23217. inline expression_node_ptr return_envelope(expression_node_ptr body,
  23218. results_context_t* rc,
  23219. bool*& return_invoked)
  23220. {
  23221. typedef details::return_envelope_node<Type> alloc_type;
  23222. expression_node_ptr result = node_allocator_->
  23223. allocate_cr<alloc_type>(body,(*rc));
  23224. return_invoked = static_cast<alloc_type*>(result)->retinvk_ptr();
  23225. return result;
  23226. }
  23227. #else
  23228. inline expression_node_ptr return_call(std::vector<expression_node_ptr>&)
  23229. {
  23230. return error_node();
  23231. }
  23232. inline expression_node_ptr return_envelope(expression_node_ptr,
  23233. results_context_t*,
  23234. bool*&)
  23235. {
  23236. return error_node();
  23237. }
  23238. #endif
  23239. inline expression_node_ptr vector_element(const std::string& symbol,
  23240. vector_holder_ptr vector_base,
  23241. expression_node_ptr index)
  23242. {
  23243. expression_node_ptr result = error_node();
  23244. if (details::is_constant_node(index))
  23245. {
  23246. std::size_t i = static_cast<std::size_t>(details::numeric::to_int64(index->value()));
  23247. details::free_node(*node_allocator_,index);
  23248. if (vector_base->rebaseable())
  23249. {
  23250. return node_allocator_->allocate<rebasevector_celem_node_t>(i,vector_base);
  23251. }
  23252. scope_element& se = parser_->sem_.get_element(symbol,i);
  23253. if (se.index == i)
  23254. {
  23255. result = se.var_node;
  23256. }
  23257. else
  23258. {
  23259. scope_element nse;
  23260. nse.name = symbol;
  23261. nse.active = true;
  23262. nse.ref_count = 1;
  23263. nse.type = scope_element::e_vecelem;
  23264. nse.index = i;
  23265. nse.depth = parser_->state_.scope_depth;
  23266. nse.data = 0;
  23267. nse.var_node = node_allocator_->allocate<variable_node_t>((*(*vector_base)[i]));
  23268. if (!parser_->sem_.add_element(nse))
  23269. {
  23270. parser_->set_synthesis_error("Failed to add new local vector element to SEM [1]");
  23271. parser_->sem_.free_element(nse);
  23272. result = error_node();
  23273. }
  23274. exprtk_debug(("vector_element() - INFO - Added new local vector element: %s\n",nse.name.c_str()));
  23275. parser_->state_.activate_side_effect("vector_element()");
  23276. result = nse.var_node;
  23277. }
  23278. }
  23279. else if (vector_base->rebaseable())
  23280. result = node_allocator_->allocate<rebasevector_elem_node_t>(index,vector_base);
  23281. else
  23282. result = node_allocator_->allocate<vector_elem_node_t>(index,vector_base);
  23283. return result;
  23284. }
  23285. private:
  23286. template <std::size_t N, typename NodePtr>
  23287. inline bool is_constant_foldable(NodePtr (&b)[N]) const
  23288. {
  23289. for (std::size_t i = 0; i < N; ++i)
  23290. {
  23291. if (0 == b[i])
  23292. return false;
  23293. else if (!details::is_constant_node(b[i]))
  23294. return false;
  23295. }
  23296. return true;
  23297. }
  23298. template <typename NodePtr,
  23299. typename Allocator,
  23300. template <typename, typename> class Sequence>
  23301. inline bool is_constant_foldable(const Sequence<NodePtr,Allocator>& b) const
  23302. {
  23303. for (std::size_t i = 0; i < b.size(); ++i)
  23304. {
  23305. if (0 == b[i])
  23306. return false;
  23307. else if (!details::is_constant_node(b[i]))
  23308. return false;
  23309. }
  23310. return true;
  23311. }
  23312. void lodge_assignment(symbol_type cst, expression_node_ptr node)
  23313. {
  23314. parser_->state_.activate_side_effect("lodge_assignment()");
  23315. if (!parser_->dec_.collect_assignments())
  23316. return;
  23317. std::string symbol_name;
  23318. switch (cst)
  23319. {
  23320. case e_st_variable : symbol_name = parser_->symtab_store_
  23321. .get_variable_name(node);
  23322. break;
  23323. #ifndef exprtk_disable_string_capabilities
  23324. case e_st_string : symbol_name = parser_->symtab_store_
  23325. .get_stringvar_name(node);
  23326. break;
  23327. #endif
  23328. case e_st_vector : {
  23329. typedef details::vector_holder<T> vector_holder_t;
  23330. vector_holder_t& vh = static_cast<vector_node_t*>(node)->vec_holder();
  23331. symbol_name = parser_->symtab_store_.get_vector_name(&vh);
  23332. }
  23333. break;
  23334. case e_st_vecelem : {
  23335. typedef details::vector_holder<T> vector_holder_t;
  23336. vector_holder_t& vh = static_cast<vector_elem_node_t*>(node)->vec_holder();
  23337. symbol_name = parser_->symtab_store_.get_vector_name(&vh);
  23338. cst = e_st_vector;
  23339. }
  23340. break;
  23341. default : return;
  23342. }
  23343. if (!symbol_name.empty())
  23344. {
  23345. parser_->dec_.add_assignment(symbol_name,cst);
  23346. }
  23347. }
  23348. inline expression_node_ptr synthesize_assignment_expression(const details::operator_type& operation, expression_node_ptr (&branch)[2])
  23349. {
  23350. if (details::is_variable_node(branch[0]))
  23351. {
  23352. lodge_assignment(e_st_variable,branch[0]);
  23353. return synthesize_expression<assignment_node_t,2>(operation,branch);
  23354. }
  23355. else if (details::is_vector_elem_node(branch[0]))
  23356. {
  23357. lodge_assignment(e_st_vecelem,branch[0]);
  23358. return synthesize_expression<assignment_vec_elem_node_t, 2>(operation, branch);
  23359. }
  23360. else if (details::is_rebasevector_elem_node(branch[0]))
  23361. {
  23362. lodge_assignment(e_st_vecelem,branch[0]);
  23363. return synthesize_expression<assignment_rebasevec_elem_node_t, 2>(operation, branch);
  23364. }
  23365. else if (details::is_rebasevector_celem_node(branch[0]))
  23366. {
  23367. lodge_assignment(e_st_vecelem,branch[0]);
  23368. return synthesize_expression<assignment_rebasevec_celem_node_t, 2>(operation, branch);
  23369. }
  23370. #ifndef exprtk_disable_string_capabilities
  23371. else if (details::is_string_node(branch[0]))
  23372. {
  23373. lodge_assignment(e_st_string,branch[0]);
  23374. return synthesize_expression<assignment_string_node_t,2>(operation, branch);
  23375. }
  23376. else if (details::is_string_range_node(branch[0]))
  23377. {
  23378. lodge_assignment(e_st_string,branch[0]);
  23379. return synthesize_expression<assignment_string_range_node_t,2>(operation, branch);
  23380. }
  23381. #endif
  23382. else if (details::is_vector_node(branch[0]))
  23383. {
  23384. lodge_assignment(e_st_vector,branch[0]);
  23385. if (details::is_ivector_node(branch[1]))
  23386. return synthesize_expression<assignment_vecvec_node_t,2>(operation, branch);
  23387. else
  23388. return synthesize_expression<assignment_vec_node_t,2>(operation, branch);
  23389. }
  23390. else
  23391. {
  23392. parser_->set_synthesis_error("Invalid assignment operation.[1]");
  23393. return error_node();
  23394. }
  23395. }
  23396. inline expression_node_ptr synthesize_assignment_operation_expression(const details::operator_type& operation,
  23397. expression_node_ptr (&branch)[2])
  23398. {
  23399. if (details::is_variable_node(branch[0]))
  23400. {
  23401. lodge_assignment(e_st_variable,branch[0]);
  23402. switch (operation)
  23403. {
  23404. #define case_stmt(op0,op1) \
  23405. case op0 : return node_allocator_-> \
  23406. template allocate_rrr<typename details::assignment_op_node<Type,op1<Type> > > \
  23407. (operation, branch[0], branch[1]); \
  23408. case_stmt(details::e_addass,details::add_op)
  23409. case_stmt(details::e_subass,details::sub_op)
  23410. case_stmt(details::e_mulass,details::mul_op)
  23411. case_stmt(details::e_divass,details::div_op)
  23412. case_stmt(details::e_modass,details::mod_op)
  23413. #undef case_stmt
  23414. default : return error_node();
  23415. }
  23416. }
  23417. else if (details::is_vector_elem_node(branch[0]))
  23418. {
  23419. lodge_assignment(e_st_vecelem,branch[0]);
  23420. switch (operation)
  23421. {
  23422. #define case_stmt(op0,op1) \
  23423. case op0 : return node_allocator_-> \
  23424. template allocate_rrr<typename details::assignment_vec_elem_op_node<Type,op1<Type> > > \
  23425. (operation, branch[0], branch[1]); \
  23426. case_stmt(details::e_addass,details::add_op)
  23427. case_stmt(details::e_subass,details::sub_op)
  23428. case_stmt(details::e_mulass,details::mul_op)
  23429. case_stmt(details::e_divass,details::div_op)
  23430. case_stmt(details::e_modass,details::mod_op)
  23431. #undef case_stmt
  23432. default : return error_node();
  23433. }
  23434. }
  23435. else if (details::is_rebasevector_elem_node(branch[0]))
  23436. {
  23437. lodge_assignment(e_st_vecelem,branch[0]);
  23438. switch (operation)
  23439. {
  23440. #define case_stmt(op0,op1) \
  23441. case op0 : return node_allocator_-> \
  23442. template allocate_rrr<typename details::assignment_rebasevec_elem_op_node<Type,op1<Type> > > \
  23443. (operation, branch[0], branch[1]); \
  23444. case_stmt(details::e_addass,details::add_op)
  23445. case_stmt(details::e_subass,details::sub_op)
  23446. case_stmt(details::e_mulass,details::mul_op)
  23447. case_stmt(details::e_divass,details::div_op)
  23448. case_stmt(details::e_modass,details::mod_op)
  23449. #undef case_stmt
  23450. default : return error_node();
  23451. }
  23452. }
  23453. else if (details::is_rebasevector_celem_node(branch[0]))
  23454. {
  23455. lodge_assignment(e_st_vecelem,branch[0]);
  23456. switch (operation)
  23457. {
  23458. #define case_stmt(op0,op1) \
  23459. case op0 : return node_allocator_-> \
  23460. template allocate_rrr<typename details::assignment_rebasevec_celem_op_node<Type,op1<Type> > > \
  23461. (operation, branch[0], branch[1]); \
  23462. case_stmt(details::e_addass,details::add_op)
  23463. case_stmt(details::e_subass,details::sub_op)
  23464. case_stmt(details::e_mulass,details::mul_op)
  23465. case_stmt(details::e_divass,details::div_op)
  23466. case_stmt(details::e_modass,details::mod_op)
  23467. #undef case_stmt
  23468. default : return error_node();
  23469. }
  23470. }
  23471. else if (details::is_vector_node(branch[0]))
  23472. {
  23473. lodge_assignment(e_st_vector,branch[0]);
  23474. if (details::is_ivector_node(branch[1]))
  23475. {
  23476. switch (operation)
  23477. {
  23478. #define case_stmt(op0,op1) \
  23479. case op0 : return node_allocator_-> \
  23480. template allocate_rrr<typename details::assignment_vecvec_op_node<Type,op1<Type> > > \
  23481. (operation, branch[0], branch[1]); \
  23482. case_stmt(details::e_addass,details::add_op)
  23483. case_stmt(details::e_subass,details::sub_op)
  23484. case_stmt(details::e_mulass,details::mul_op)
  23485. case_stmt(details::e_divass,details::div_op)
  23486. case_stmt(details::e_modass,details::mod_op)
  23487. #undef case_stmt
  23488. default : return error_node();
  23489. }
  23490. }
  23491. else
  23492. {
  23493. switch (operation)
  23494. {
  23495. #define case_stmt(op0,op1) \
  23496. case op0 : return node_allocator_-> \
  23497. template allocate_rrr<typename details::assignment_vec_op_node<Type,op1<Type> > > \
  23498. (operation, branch[0], branch[1]); \
  23499. case_stmt(details::e_addass,details::add_op)
  23500. case_stmt(details::e_subass,details::sub_op)
  23501. case_stmt(details::e_mulass,details::mul_op)
  23502. case_stmt(details::e_divass,details::div_op)
  23503. case_stmt(details::e_modass,details::mod_op)
  23504. #undef case_stmt
  23505. default : return error_node();
  23506. }
  23507. }
  23508. }
  23509. #ifndef exprtk_disable_string_capabilities
  23510. else if (
  23511. (details::e_addass == operation) &&
  23512. details::is_string_node(branch[0])
  23513. )
  23514. {
  23515. typedef details::assignment_string_node<T,details::asn_addassignment> addass_t;
  23516. lodge_assignment(e_st_string,branch[0]);
  23517. return synthesize_expression<addass_t,2>(operation,branch);
  23518. }
  23519. #endif
  23520. else
  23521. {
  23522. parser_->set_synthesis_error("Invalid assignment operation[2]");
  23523. return error_node();
  23524. }
  23525. }
  23526. inline expression_node_ptr synthesize_veceqineqlogic_operation_expression(const details::operator_type& operation,
  23527. expression_node_ptr (&branch)[2])
  23528. {
  23529. const bool is_b0_ivec = details::is_ivector_node(branch[0]);
  23530. const bool is_b1_ivec = details::is_ivector_node(branch[1]);
  23531. #define batch_eqineq_logic_case \
  23532. case_stmt(details:: e_lt, details:: lt_op) \
  23533. case_stmt(details:: e_lte, details:: lte_op) \
  23534. case_stmt(details:: e_gt, details:: gt_op) \
  23535. case_stmt(details:: e_gte, details:: gte_op) \
  23536. case_stmt(details:: e_eq, details:: eq_op) \
  23537. case_stmt(details:: e_ne, details:: ne_op) \
  23538. case_stmt(details::e_equal, details::equal_op) \
  23539. case_stmt(details:: e_and, details:: and_op) \
  23540. case_stmt(details:: e_nand, details:: nand_op) \
  23541. case_stmt(details:: e_or, details:: or_op) \
  23542. case_stmt(details:: e_nor, details:: nor_op) \
  23543. case_stmt(details:: e_xor, details:: xor_op) \
  23544. case_stmt(details:: e_xnor, details:: xnor_op) \
  23545. if (is_b0_ivec && is_b1_ivec)
  23546. {
  23547. switch (operation)
  23548. {
  23549. #define case_stmt(op0,op1) \
  23550. case op0 : return node_allocator_-> \
  23551. template allocate_rrr<typename details::vec_binop_vecvec_node<Type,op1<Type> > > \
  23552. (operation, branch[0], branch[1]); \
  23553. batch_eqineq_logic_case
  23554. #undef case_stmt
  23555. default : return error_node();
  23556. }
  23557. }
  23558. else if (is_b0_ivec && !is_b1_ivec)
  23559. {
  23560. switch (operation)
  23561. {
  23562. #define case_stmt(op0,op1) \
  23563. case op0 : return node_allocator_-> \
  23564. template allocate_rrr<typename details::vec_binop_vecval_node<Type,op1<Type> > > \
  23565. (operation, branch[0], branch[1]); \
  23566. batch_eqineq_logic_case
  23567. #undef case_stmt
  23568. default : return error_node();
  23569. }
  23570. }
  23571. else if (!is_b0_ivec && is_b1_ivec)
  23572. {
  23573. switch (operation)
  23574. {
  23575. #define case_stmt(op0,op1) \
  23576. case op0 : return node_allocator_-> \
  23577. template allocate_rrr<typename details::vec_binop_valvec_node<Type,op1<Type> > > \
  23578. (operation, branch[0], branch[1]); \
  23579. batch_eqineq_logic_case
  23580. #undef case_stmt
  23581. default : return error_node();
  23582. }
  23583. }
  23584. else
  23585. return error_node();
  23586. #undef batch_eqineq_logic_case
  23587. }
  23588. inline expression_node_ptr synthesize_vecarithmetic_operation_expression(const details::operator_type& operation,
  23589. expression_node_ptr (&branch)[2])
  23590. {
  23591. const bool is_b0_ivec = details::is_ivector_node(branch[0]);
  23592. const bool is_b1_ivec = details::is_ivector_node(branch[1]);
  23593. #define vector_ops \
  23594. case_stmt(details::e_add,details::add_op) \
  23595. case_stmt(details::e_sub,details::sub_op) \
  23596. case_stmt(details::e_mul,details::mul_op) \
  23597. case_stmt(details::e_div,details::div_op) \
  23598. case_stmt(details::e_mod,details::mod_op) \
  23599. if (is_b0_ivec && is_b1_ivec)
  23600. {
  23601. switch (operation)
  23602. {
  23603. #define case_stmt(op0,op1) \
  23604. case op0 : return node_allocator_-> \
  23605. template allocate_rrr<typename details::vec_binop_vecvec_node<Type,op1<Type> > > \
  23606. (operation, branch[0], branch[1]); \
  23607. vector_ops
  23608. case_stmt(details::e_pow,details:: pow_op)
  23609. #undef case_stmt
  23610. default : return error_node();
  23611. }
  23612. }
  23613. else if (is_b0_ivec && !is_b1_ivec)
  23614. {
  23615. switch (operation)
  23616. {
  23617. #define case_stmt(op0,op1) \
  23618. case op0 : return node_allocator_-> \
  23619. template allocate_rrr<typename details::vec_binop_vecval_node<Type,op1<Type> > > \
  23620. (operation, branch[0], branch[1]); \
  23621. vector_ops
  23622. case_stmt(details::e_pow,details:: pow_op)
  23623. #undef case_stmt
  23624. default : return error_node();
  23625. }
  23626. }
  23627. else if (!is_b0_ivec && is_b1_ivec)
  23628. {
  23629. switch (operation)
  23630. {
  23631. #define case_stmt(op0,op1) \
  23632. case op0 : return node_allocator_-> \
  23633. template allocate_rrr<typename details::vec_binop_valvec_node<Type,op1<Type> > > \
  23634. (operation, branch[0], branch[1]); \
  23635. vector_ops
  23636. #undef case_stmt
  23637. default : return error_node();
  23638. }
  23639. }
  23640. else
  23641. return error_node();
  23642. #undef vector_ops
  23643. }
  23644. inline expression_node_ptr synthesize_swap_expression(expression_node_ptr (&branch)[2])
  23645. {
  23646. const bool v0_is_ivar = details::is_ivariable_node(branch[0]);
  23647. const bool v1_is_ivar = details::is_ivariable_node(branch[1]);
  23648. const bool v0_is_ivec = details::is_ivector_node (branch[0]);
  23649. const bool v1_is_ivec = details::is_ivector_node (branch[1]);
  23650. #ifndef exprtk_disable_string_capabilities
  23651. const bool v0_is_str = details::is_generally_string_node(branch[0]);
  23652. const bool v1_is_str = details::is_generally_string_node(branch[1]);
  23653. #endif
  23654. expression_node_ptr result = error_node();
  23655. if (v0_is_ivar && v1_is_ivar)
  23656. {
  23657. typedef details::variable_node<T>* variable_node_ptr;
  23658. variable_node_ptr v0 = variable_node_ptr(0);
  23659. variable_node_ptr v1 = variable_node_ptr(0);
  23660. if (
  23661. (0 != (v0 = dynamic_cast<variable_node_ptr>(branch[0]))) &&
  23662. (0 != (v1 = dynamic_cast<variable_node_ptr>(branch[1])))
  23663. )
  23664. {
  23665. result = node_allocator_->allocate<details::swap_node<T> >(v0,v1);
  23666. }
  23667. else
  23668. result = node_allocator_->allocate<details::swap_generic_node<T> >(branch[0],branch[1]);
  23669. }
  23670. else if (v0_is_ivec && v1_is_ivec)
  23671. {
  23672. result = node_allocator_->allocate<details::swap_vecvec_node<T> >(branch[0],branch[1]);
  23673. }
  23674. #ifndef exprtk_disable_string_capabilities
  23675. else if (v0_is_str && v1_is_str)
  23676. {
  23677. if (is_string_node(branch[0]) && is_string_node(branch[1]))
  23678. result = node_allocator_->allocate<details::swap_string_node<T> >
  23679. (branch[0], branch[1]);
  23680. else
  23681. result = node_allocator_->allocate<details::swap_genstrings_node<T> >
  23682. (branch[0], branch[1]);
  23683. }
  23684. #endif
  23685. else
  23686. {
  23687. parser_->set_synthesis_error("Only variables, strings, vectors or vector elements can be swapped");
  23688. return error_node();
  23689. }
  23690. parser_->state_.activate_side_effect("synthesize_swap_expression()");
  23691. return result;
  23692. }
  23693. #ifndef exprtk_disable_sc_andor
  23694. inline expression_node_ptr synthesize_shortcircuit_expression(const details::operator_type& operation, expression_node_ptr (&branch)[2])
  23695. {
  23696. expression_node_ptr result = error_node();
  23697. if (details::is_constant_node(branch[0]))
  23698. {
  23699. if (
  23700. (details::e_scand == operation) &&
  23701. std::equal_to<T>()(T(0),branch[0]->value())
  23702. )
  23703. result = node_allocator_->allocate_c<literal_node_t>(T(0));
  23704. else if (
  23705. (details::e_scor == operation) &&
  23706. std::not_equal_to<T>()(T(0),branch[0]->value())
  23707. )
  23708. result = node_allocator_->allocate_c<literal_node_t>(T(1));
  23709. }
  23710. if (details::is_constant_node(branch[1]) && (0 == result))
  23711. {
  23712. if (
  23713. (details::e_scand == operation) &&
  23714. std::equal_to<T>()(T(0),branch[1]->value())
  23715. )
  23716. result = node_allocator_->allocate_c<literal_node_t>(T(0));
  23717. else if (
  23718. (details::e_scor == operation) &&
  23719. std::not_equal_to<T>()(T(0),branch[1]->value())
  23720. )
  23721. result = node_allocator_->allocate_c<literal_node_t>(T(1));
  23722. }
  23723. if (result)
  23724. {
  23725. free_node(*node_allocator_, branch[0]);
  23726. free_node(*node_allocator_, branch[1]);
  23727. return result;
  23728. }
  23729. else if (details::e_scand == operation)
  23730. {
  23731. return synthesize_expression<scand_node_t,2>(operation, branch);
  23732. }
  23733. else if (details::e_scor == operation)
  23734. {
  23735. return synthesize_expression<scor_node_t,2>(operation, branch);
  23736. }
  23737. else
  23738. return error_node();
  23739. }
  23740. #else
  23741. inline expression_node_ptr synthesize_shortcircuit_expression(const details::operator_type&, expression_node_ptr (&)[2])
  23742. {
  23743. return error_node();
  23744. }
  23745. #endif
  23746. #define basic_opr_switch_statements \
  23747. case_stmt(details::e_add, details::add_op) \
  23748. case_stmt(details::e_sub, details::sub_op) \
  23749. case_stmt(details::e_mul, details::mul_op) \
  23750. case_stmt(details::e_div, details::div_op) \
  23751. case_stmt(details::e_mod, details::mod_op) \
  23752. case_stmt(details::e_pow, details::pow_op) \
  23753. #define extended_opr_switch_statements \
  23754. case_stmt(details:: e_lt, details:: lt_op) \
  23755. case_stmt(details:: e_lte, details:: lte_op) \
  23756. case_stmt(details:: e_gt, details:: gt_op) \
  23757. case_stmt(details:: e_gte, details:: gte_op) \
  23758. case_stmt(details:: e_eq, details:: eq_op) \
  23759. case_stmt(details:: e_ne, details:: ne_op) \
  23760. case_stmt(details:: e_and, details:: and_op) \
  23761. case_stmt(details::e_nand, details::nand_op) \
  23762. case_stmt(details:: e_or, details:: or_op) \
  23763. case_stmt(details:: e_nor, details:: nor_op) \
  23764. case_stmt(details:: e_xor, details:: xor_op) \
  23765. case_stmt(details::e_xnor, details::xnor_op) \
  23766. #ifndef exprtk_disable_cardinal_pow_optimisation
  23767. template <typename TType, template <typename, typename> class IPowNode>
  23768. inline expression_node_ptr cardinal_pow_optimisation_impl(const TType& v, const unsigned int& p)
  23769. {
  23770. switch (p)
  23771. {
  23772. #define case_stmt(cp) \
  23773. case cp : return node_allocator_-> \
  23774. allocate<IPowNode<T,details::numeric::fast_exp<T,cp> > >(v); \
  23775. case_stmt( 1) case_stmt( 2) case_stmt( 3) case_stmt( 4)
  23776. case_stmt( 5) case_stmt( 6) case_stmt( 7) case_stmt( 8)
  23777. case_stmt( 9) case_stmt(10) case_stmt(11) case_stmt(12)
  23778. case_stmt(13) case_stmt(14) case_stmt(15) case_stmt(16)
  23779. case_stmt(17) case_stmt(18) case_stmt(19) case_stmt(20)
  23780. case_stmt(21) case_stmt(22) case_stmt(23) case_stmt(24)
  23781. case_stmt(25) case_stmt(26) case_stmt(27) case_stmt(28)
  23782. case_stmt(29) case_stmt(30) case_stmt(31) case_stmt(32)
  23783. case_stmt(33) case_stmt(34) case_stmt(35) case_stmt(36)
  23784. case_stmt(37) case_stmt(38) case_stmt(39) case_stmt(40)
  23785. case_stmt(41) case_stmt(42) case_stmt(43) case_stmt(44)
  23786. case_stmt(45) case_stmt(46) case_stmt(47) case_stmt(48)
  23787. case_stmt(49) case_stmt(50) case_stmt(51) case_stmt(52)
  23788. case_stmt(53) case_stmt(54) case_stmt(55) case_stmt(56)
  23789. case_stmt(57) case_stmt(58) case_stmt(59) case_stmt(60)
  23790. #undef case_stmt
  23791. default : return error_node();
  23792. }
  23793. }
  23794. inline expression_node_ptr cardinal_pow_optimisation(const T& v, const T& c)
  23795. {
  23796. const bool not_recipricol = (c >= T(0));
  23797. const unsigned int p = static_cast<unsigned int>(details::numeric::to_int32(details::numeric::abs(c)));
  23798. if (0 == p)
  23799. return node_allocator_->allocate_c<literal_node_t>(T(1));
  23800. else if (std::equal_to<T>()(T(2),c))
  23801. {
  23802. return node_allocator_->
  23803. template allocate_rr<typename details::vov_node<Type,details::mul_op<Type> > >(v,v);
  23804. }
  23805. else
  23806. {
  23807. if (not_recipricol)
  23808. return cardinal_pow_optimisation_impl<T,details::ipow_node>(v,p);
  23809. else
  23810. return cardinal_pow_optimisation_impl<T,details::ipowinv_node>(v,p);
  23811. }
  23812. }
  23813. inline bool cardinal_pow_optimisable(const details::operator_type& operation, const T& c) const
  23814. {
  23815. return (details::e_pow == operation) && (details::numeric::abs(c) <= T(60)) && details::numeric::is_integer(c);
  23816. }
  23817. inline expression_node_ptr cardinal_pow_optimisation(expression_node_ptr (&branch)[2])
  23818. {
  23819. const Type c = static_cast<details::literal_node<Type>*>(branch[1])->value();
  23820. const bool not_recipricol = (c >= T(0));
  23821. const unsigned int p = static_cast<unsigned int>(details::numeric::to_int32(details::numeric::abs(c)));
  23822. node_allocator_->free(branch[1]);
  23823. if (0 == p)
  23824. {
  23825. details::free_all_nodes(*node_allocator_, branch);
  23826. return node_allocator_->allocate_c<literal_node_t>(T(1));
  23827. }
  23828. else if (not_recipricol)
  23829. return cardinal_pow_optimisation_impl<expression_node_ptr,details::bipow_node>(branch[0],p);
  23830. else
  23831. return cardinal_pow_optimisation_impl<expression_node_ptr,details::bipowninv_node>(branch[0],p);
  23832. }
  23833. #else
  23834. inline expression_node_ptr cardinal_pow_optimisation(T&, const T&)
  23835. {
  23836. return error_node();
  23837. }
  23838. inline bool cardinal_pow_optimisable(const details::operator_type&, const T&)
  23839. {
  23840. return false;
  23841. }
  23842. inline expression_node_ptr cardinal_pow_optimisation(expression_node_ptr(&)[2])
  23843. {
  23844. return error_node();
  23845. }
  23846. #endif
  23847. struct synthesize_binary_ext_expression
  23848. {
  23849. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  23850. const details::operator_type& operation,
  23851. expression_node_ptr (&branch)[2])
  23852. {
  23853. const bool left_neg = is_neg_unary_node(branch[0]);
  23854. const bool right_neg = is_neg_unary_node(branch[1]);
  23855. if (left_neg && right_neg)
  23856. {
  23857. if (
  23858. (details::e_add == operation) ||
  23859. (details::e_sub == operation) ||
  23860. (details::e_mul == operation) ||
  23861. (details::e_div == operation)
  23862. )
  23863. {
  23864. if (
  23865. !expr_gen.parser_->simplify_unary_negation_branch(branch[0]) ||
  23866. !expr_gen.parser_->simplify_unary_negation_branch(branch[1])
  23867. )
  23868. {
  23869. details::free_all_nodes(*expr_gen.node_allocator_,branch);
  23870. return error_node();
  23871. }
  23872. }
  23873. switch (operation)
  23874. {
  23875. // -f(x + 1) + -g(y + 1) --> -(f(x + 1) + g(y + 1))
  23876. case details::e_add : return expr_gen(details::e_neg,
  23877. expr_gen.node_allocator_->
  23878. template allocate<typename details::binary_ext_node<Type,details::add_op<Type> > >
  23879. (branch[0],branch[1]));
  23880. // -f(x + 1) - -g(y + 1) --> g(y + 1) - f(x + 1)
  23881. case details::e_sub : return expr_gen.node_allocator_->
  23882. template allocate<typename details::binary_ext_node<Type,details::sub_op<Type> > >
  23883. (branch[1],branch[0]);
  23884. default : break;
  23885. }
  23886. }
  23887. else if (left_neg && !right_neg)
  23888. {
  23889. if (
  23890. (details::e_add == operation) ||
  23891. (details::e_sub == operation) ||
  23892. (details::e_mul == operation) ||
  23893. (details::e_div == operation)
  23894. )
  23895. {
  23896. if (!expr_gen.parser_->simplify_unary_negation_branch(branch[0]))
  23897. {
  23898. details::free_all_nodes(*expr_gen.node_allocator_,branch);
  23899. return error_node();
  23900. }
  23901. switch (operation)
  23902. {
  23903. // -f(x + 1) + g(y + 1) --> g(y + 1) - f(x + 1)
  23904. case details::e_add : return expr_gen.node_allocator_->
  23905. template allocate<typename details::binary_ext_node<Type,details::sub_op<Type> > >
  23906. (branch[1], branch[0]);
  23907. // -f(x + 1) - g(y + 1) --> -(f(x + 1) + g(y + 1))
  23908. case details::e_sub : return expr_gen(details::e_neg,
  23909. expr_gen.node_allocator_->
  23910. template allocate<typename details::binary_ext_node<Type,details::add_op<Type> > >
  23911. (branch[0], branch[1]));
  23912. // -f(x + 1) * g(y + 1) --> -(f(x + 1) * g(y + 1))
  23913. case details::e_mul : return expr_gen(details::e_neg,
  23914. expr_gen.node_allocator_->
  23915. template allocate<typename details::binary_ext_node<Type,details::mul_op<Type> > >
  23916. (branch[0], branch[1]));
  23917. // -f(x + 1) / g(y + 1) --> -(f(x + 1) / g(y + 1))
  23918. case details::e_div : return expr_gen(details::e_neg,
  23919. expr_gen.node_allocator_->
  23920. template allocate<typename details::binary_ext_node<Type,details::div_op<Type> > >
  23921. (branch[0], branch[1]));
  23922. default : return error_node();
  23923. }
  23924. }
  23925. }
  23926. else if (!left_neg && right_neg)
  23927. {
  23928. if (
  23929. (details::e_add == operation) ||
  23930. (details::e_sub == operation) ||
  23931. (details::e_mul == operation) ||
  23932. (details::e_div == operation)
  23933. )
  23934. {
  23935. if (!expr_gen.parser_->simplify_unary_negation_branch(branch[1]))
  23936. {
  23937. details::free_all_nodes(*expr_gen.node_allocator_,branch);
  23938. return error_node();
  23939. }
  23940. switch (operation)
  23941. {
  23942. // f(x + 1) + -g(y + 1) --> f(x + 1) - g(y + 1)
  23943. case details::e_add : return expr_gen.node_allocator_->
  23944. template allocate<typename details::binary_ext_node<Type,details::sub_op<Type> > >
  23945. (branch[0], branch[1]);
  23946. // f(x + 1) - - g(y + 1) --> f(x + 1) + g(y + 1)
  23947. case details::e_sub : return expr_gen.node_allocator_->
  23948. template allocate<typename details::binary_ext_node<Type,details::add_op<Type> > >
  23949. (branch[0], branch[1]);
  23950. // f(x + 1) * -g(y + 1) --> -(f(x + 1) * g(y + 1))
  23951. case details::e_mul : return expr_gen(details::e_neg,
  23952. expr_gen.node_allocator_->
  23953. template allocate<typename details::binary_ext_node<Type,details::mul_op<Type> > >
  23954. (branch[0], branch[1]));
  23955. // f(x + 1) / -g(y + 1) --> -(f(x + 1) / g(y + 1))
  23956. case details::e_div : return expr_gen(details::e_neg,
  23957. expr_gen.node_allocator_->
  23958. template allocate<typename details::binary_ext_node<Type,details::div_op<Type> > >
  23959. (branch[0], branch[1]));
  23960. default : return error_node();
  23961. }
  23962. }
  23963. }
  23964. switch (operation)
  23965. {
  23966. #define case_stmt(op0,op1) \
  23967. case op0 : return expr_gen.node_allocator_-> \
  23968. template allocate<typename details::binary_ext_node<Type,op1<Type> > > \
  23969. (branch[0], branch[1]); \
  23970. basic_opr_switch_statements
  23971. extended_opr_switch_statements
  23972. #undef case_stmt
  23973. default : return error_node();
  23974. }
  23975. }
  23976. };
  23977. struct synthesize_vob_expression
  23978. {
  23979. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  23980. const details::operator_type& operation,
  23981. expression_node_ptr (&branch)[2])
  23982. {
  23983. const Type& v = static_cast<details::variable_node<Type>*>(branch[0])->ref();
  23984. #ifndef exprtk_disable_enhanced_features
  23985. if (details::is_sf3ext_node(branch[1]))
  23986. {
  23987. expression_node_ptr result = error_node();
  23988. const bool synthesis_result =
  23989. synthesize_sf4ext_expression::template compile_right<vtype>
  23990. (expr_gen, v, operation, branch[1], result);
  23991. if (synthesis_result)
  23992. {
  23993. free_node(*expr_gen.node_allocator_,branch[1]);
  23994. return result;
  23995. }
  23996. }
  23997. #endif
  23998. if (
  23999. (details::e_mul == operation) ||
  24000. (details::e_div == operation)
  24001. )
  24002. {
  24003. if (details::is_uv_node(branch[1]))
  24004. {
  24005. typedef details::uv_base_node<Type>* uvbn_ptr_t;
  24006. details::operator_type o = static_cast<uvbn_ptr_t>(branch[1])->operation();
  24007. if (details::e_neg == o)
  24008. {
  24009. const Type& v1 = static_cast<uvbn_ptr_t>(branch[1])->v();
  24010. free_node(*expr_gen.node_allocator_,branch[1]);
  24011. switch (operation)
  24012. {
  24013. case details::e_mul : return expr_gen(details::e_neg,
  24014. expr_gen.node_allocator_->
  24015. template allocate_rr<typename details::
  24016. vov_node<Type,details::mul_op<Type> > >(v,v1));
  24017. case details::e_div : return expr_gen(details::e_neg,
  24018. expr_gen.node_allocator_->
  24019. template allocate_rr<typename details::
  24020. vov_node<Type,details::div_op<Type> > >(v,v1));
  24021. default : break;
  24022. }
  24023. }
  24024. }
  24025. }
  24026. switch (operation)
  24027. {
  24028. #define case_stmt(op0,op1) \
  24029. case op0 : return expr_gen.node_allocator_-> \
  24030. template allocate_rc<typename details::vob_node<Type,op1<Type> > > \
  24031. (v, branch[1]); \
  24032. basic_opr_switch_statements
  24033. extended_opr_switch_statements
  24034. #undef case_stmt
  24035. default : return error_node();
  24036. }
  24037. }
  24038. };
  24039. struct synthesize_bov_expression
  24040. {
  24041. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  24042. const details::operator_type& operation,
  24043. expression_node_ptr (&branch)[2])
  24044. {
  24045. const Type& v = static_cast<details::variable_node<Type>*>(branch[1])->ref();
  24046. #ifndef exprtk_disable_enhanced_features
  24047. if (details::is_sf3ext_node(branch[0]))
  24048. {
  24049. expression_node_ptr result = error_node();
  24050. const bool synthesis_result =
  24051. synthesize_sf4ext_expression::template compile_left<vtype>
  24052. (expr_gen, v, operation, branch[0], result);
  24053. if (synthesis_result)
  24054. {
  24055. free_node(*expr_gen.node_allocator_, branch[0]);
  24056. return result;
  24057. }
  24058. }
  24059. #endif
  24060. if (
  24061. (details::e_add == operation) ||
  24062. (details::e_sub == operation) ||
  24063. (details::e_mul == operation) ||
  24064. (details::e_div == operation)
  24065. )
  24066. {
  24067. if (details::is_uv_node(branch[0]))
  24068. {
  24069. typedef details::uv_base_node<Type>* uvbn_ptr_t;
  24070. details::operator_type o = static_cast<uvbn_ptr_t>(branch[0])->operation();
  24071. if (details::e_neg == o)
  24072. {
  24073. const Type& v0 = static_cast<uvbn_ptr_t>(branch[0])->v();
  24074. free_node(*expr_gen.node_allocator_,branch[0]);
  24075. switch (operation)
  24076. {
  24077. case details::e_add : return expr_gen.node_allocator_->
  24078. template allocate_rr<typename details::
  24079. vov_node<Type,details::sub_op<Type> > >(v,v0);
  24080. case details::e_sub : return expr_gen(details::e_neg,
  24081. expr_gen.node_allocator_->
  24082. template allocate_rr<typename details::
  24083. vov_node<Type,details::add_op<Type> > >(v0,v));
  24084. case details::e_mul : return expr_gen(details::e_neg,
  24085. expr_gen.node_allocator_->
  24086. template allocate_rr<typename details::
  24087. vov_node<Type,details::mul_op<Type> > >(v0,v));
  24088. case details::e_div : return expr_gen(details::e_neg,
  24089. expr_gen.node_allocator_->
  24090. template allocate_rr<typename details::
  24091. vov_node<Type,details::div_op<Type> > >(v0,v));
  24092. default : break;
  24093. }
  24094. }
  24095. }
  24096. }
  24097. switch (operation)
  24098. {
  24099. #define case_stmt(op0,op1) \
  24100. case op0 : return expr_gen.node_allocator_-> \
  24101. template allocate_cr<typename details::bov_node<Type,op1<Type> > > \
  24102. (branch[0], v); \
  24103. basic_opr_switch_statements
  24104. extended_opr_switch_statements
  24105. #undef case_stmt
  24106. default : return error_node();
  24107. }
  24108. }
  24109. };
  24110. struct synthesize_cob_expression
  24111. {
  24112. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  24113. const details::operator_type& operation,
  24114. expression_node_ptr (&branch)[2])
  24115. {
  24116. const Type c = static_cast<details::literal_node<Type>*>(branch[0])->value();
  24117. free_node(*expr_gen.node_allocator_,branch[0]);
  24118. if (std::equal_to<T>()(T(0),c) && (details::e_mul == operation))
  24119. {
  24120. free_node(*expr_gen.node_allocator_,branch[1]);
  24121. return expr_gen(T(0));
  24122. }
  24123. else if (std::equal_to<T>()(T(0),c) && (details::e_div == operation))
  24124. {
  24125. free_node(*expr_gen.node_allocator_, branch[1]);
  24126. return expr_gen(T(0));
  24127. }
  24128. else if (std::equal_to<T>()(T(0),c) && (details::e_add == operation))
  24129. return branch[1];
  24130. else if (std::equal_to<T>()(T(1),c) && (details::e_mul == operation))
  24131. return branch[1];
  24132. if (details::is_cob_node(branch[1]))
  24133. {
  24134. // Simplify expressions of the form:
  24135. // 1. (1 * (2 * (3 * (4 * (5 * (6 * (7 * (8 * (9 + x))))))))) --> 40320 * (9 + x)
  24136. // 2. (1 + (2 + (3 + (4 + (5 + (6 + (7 + (8 + (9 + x))))))))) --> 45 + x
  24137. if (
  24138. (operation == details::e_mul) ||
  24139. (operation == details::e_add)
  24140. )
  24141. {
  24142. details::cob_base_node<Type>* cobnode = static_cast<details::cob_base_node<Type>*>(branch[1]);
  24143. if (operation == cobnode->operation())
  24144. {
  24145. switch (operation)
  24146. {
  24147. case details::e_add : cobnode->set_c(c + cobnode->c()); break;
  24148. case details::e_mul : cobnode->set_c(c * cobnode->c()); break;
  24149. default : return error_node();
  24150. }
  24151. return cobnode;
  24152. }
  24153. }
  24154. if (operation == details::e_mul)
  24155. {
  24156. details::cob_base_node<Type>* cobnode = static_cast<details::cob_base_node<Type>*>(branch[1]);
  24157. details::operator_type cob_opr = cobnode->operation();
  24158. if (
  24159. (details::e_div == cob_opr) ||
  24160. (details::e_mul == cob_opr)
  24161. )
  24162. {
  24163. switch (cob_opr)
  24164. {
  24165. case details::e_div : cobnode->set_c(c * cobnode->c()); break;
  24166. case details::e_mul : cobnode->set_c(cobnode->c() / c); break;
  24167. default : return error_node();
  24168. }
  24169. return cobnode;
  24170. }
  24171. }
  24172. else if (operation == details::e_div)
  24173. {
  24174. details::cob_base_node<Type>* cobnode = static_cast<details::cob_base_node<Type>*>(branch[1]);
  24175. details::operator_type cob_opr = cobnode->operation();
  24176. if (
  24177. (details::e_div == cob_opr) ||
  24178. (details::e_mul == cob_opr)
  24179. )
  24180. {
  24181. details::expression_node<Type>* new_cobnode = error_node();
  24182. switch (cob_opr)
  24183. {
  24184. case details::e_div : new_cobnode = expr_gen.node_allocator_->
  24185. template allocate_tt<typename details::cob_node<Type,details::mul_op<Type> > >
  24186. (c / cobnode->c(), cobnode->move_branch(0));
  24187. break;
  24188. case details::e_mul : new_cobnode = expr_gen.node_allocator_->
  24189. template allocate_tt<typename details::cob_node<Type,details::div_op<Type> > >
  24190. (c / cobnode->c(), cobnode->move_branch(0));
  24191. break;
  24192. default : return error_node();
  24193. }
  24194. free_node(*expr_gen.node_allocator_,branch[1]);
  24195. return new_cobnode;
  24196. }
  24197. }
  24198. }
  24199. #ifndef exprtk_disable_enhanced_features
  24200. else if (details::is_sf3ext_node(branch[1]))
  24201. {
  24202. expression_node_ptr result = error_node();
  24203. const bool synthesis_result =
  24204. synthesize_sf4ext_expression::template compile_right<ctype>
  24205. (expr_gen, c, operation, branch[1], result);
  24206. if (synthesis_result)
  24207. {
  24208. free_node(*expr_gen.node_allocator_,branch[1]);
  24209. return result;
  24210. }
  24211. }
  24212. #endif
  24213. switch (operation)
  24214. {
  24215. #define case_stmt(op0,op1) \
  24216. case op0 : return expr_gen.node_allocator_-> \
  24217. template allocate_tt<typename details::cob_node<Type,op1<Type> > > \
  24218. (c, branch[1]); \
  24219. basic_opr_switch_statements
  24220. extended_opr_switch_statements
  24221. #undef case_stmt
  24222. default : return error_node();
  24223. }
  24224. }
  24225. };
  24226. struct synthesize_boc_expression
  24227. {
  24228. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  24229. const details::operator_type& operation,
  24230. expression_node_ptr (&branch)[2])
  24231. {
  24232. const Type c = static_cast<details::literal_node<Type>*>(branch[1])->value();
  24233. details::free_node(*(expr_gen.node_allocator_), branch[1]);
  24234. if (std::equal_to<T>()(T(0),c) && (details::e_mul == operation))
  24235. {
  24236. free_node(*expr_gen.node_allocator_, branch[0]);
  24237. return expr_gen(T(0));
  24238. }
  24239. else if (std::equal_to<T>()(T(0),c) && (details::e_div == operation))
  24240. {
  24241. free_node(*expr_gen.node_allocator_, branch[0]);
  24242. return expr_gen(std::numeric_limits<T>::quiet_NaN());
  24243. }
  24244. else if (std::equal_to<T>()(T(0),c) && (details::e_add == operation))
  24245. return branch[0];
  24246. else if (std::equal_to<T>()(T(1),c) && (details::e_mul == operation))
  24247. return branch[0];
  24248. if (details::is_boc_node(branch[0]))
  24249. {
  24250. // Simplify expressions of the form:
  24251. // 1. (((((((((x + 9) * 8) * 7) * 6) * 5) * 4) * 3) * 2) * 1) --> (x + 9) * 40320
  24252. // 2. (((((((((x + 9) + 8) + 7) + 6) + 5) + 4) + 3) + 2) + 1) --> x + 45
  24253. if (
  24254. (operation == details::e_mul) ||
  24255. (operation == details::e_add)
  24256. )
  24257. {
  24258. details::boc_base_node<Type>* bocnode = static_cast<details::boc_base_node<Type>*>(branch[0]);
  24259. if (operation == bocnode->operation())
  24260. {
  24261. switch (operation)
  24262. {
  24263. case details::e_add : bocnode->set_c(c + bocnode->c()); break;
  24264. case details::e_mul : bocnode->set_c(c * bocnode->c()); break;
  24265. default : return error_node();
  24266. }
  24267. return bocnode;
  24268. }
  24269. }
  24270. else if (operation == details::e_div)
  24271. {
  24272. details::boc_base_node<Type>* bocnode = static_cast<details::boc_base_node<Type>*>(branch[0]);
  24273. details::operator_type boc_opr = bocnode->operation();
  24274. if (
  24275. (details::e_div == boc_opr) ||
  24276. (details::e_mul == boc_opr)
  24277. )
  24278. {
  24279. switch (boc_opr)
  24280. {
  24281. case details::e_div : bocnode->set_c(c * bocnode->c()); break;
  24282. case details::e_mul : bocnode->set_c(bocnode->c() / c); break;
  24283. default : return error_node();
  24284. }
  24285. return bocnode;
  24286. }
  24287. }
  24288. else if (operation == details::e_pow)
  24289. {
  24290. // (v ^ c0) ^ c1 --> v ^(c0 * c1)
  24291. details::boc_base_node<Type>* bocnode = static_cast<details::boc_base_node<Type>*>(branch[0]);
  24292. details::operator_type boc_opr = bocnode->operation();
  24293. if (details::e_pow == boc_opr)
  24294. {
  24295. bocnode->set_c(bocnode->c() * c);
  24296. return bocnode;
  24297. }
  24298. }
  24299. }
  24300. #ifndef exprtk_disable_enhanced_features
  24301. if (details::is_sf3ext_node(branch[0]))
  24302. {
  24303. expression_node_ptr result = error_node();
  24304. const bool synthesis_result =
  24305. synthesize_sf4ext_expression::template compile_left<ctype>
  24306. (expr_gen, c, operation, branch[0], result);
  24307. if (synthesis_result)
  24308. {
  24309. free_node(*expr_gen.node_allocator_, branch[0]);
  24310. return result;
  24311. }
  24312. }
  24313. #endif
  24314. switch (operation)
  24315. {
  24316. #define case_stmt(op0,op1) \
  24317. case op0 : return expr_gen.node_allocator_-> \
  24318. template allocate_cr<typename details::boc_node<Type,op1<Type> > > \
  24319. (branch[0], c); \
  24320. basic_opr_switch_statements
  24321. extended_opr_switch_statements
  24322. #undef case_stmt
  24323. default : return error_node();
  24324. }
  24325. }
  24326. };
  24327. struct synthesize_cocob_expression
  24328. {
  24329. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  24330. const details::operator_type& operation,
  24331. expression_node_ptr (&branch)[2])
  24332. {
  24333. expression_node_ptr result = error_node();
  24334. // (cob) o c --> cob
  24335. if (details::is_cob_node(branch[0]))
  24336. {
  24337. details::cob_base_node<Type>* cobnode = static_cast<details::cob_base_node<Type>*>(branch[0]);
  24338. const Type c = static_cast<details::literal_node<Type>*>(branch[1])->value();
  24339. if (std::equal_to<T>()(T(0),c) && (details::e_mul == operation))
  24340. {
  24341. free_node(*expr_gen.node_allocator_, branch[0]);
  24342. free_node(*expr_gen.node_allocator_, branch[1]);
  24343. return expr_gen(T(0));
  24344. }
  24345. else if (std::equal_to<T>()(T(0),c) && (details::e_div == operation))
  24346. {
  24347. free_node(*expr_gen.node_allocator_, branch[0]);
  24348. free_node(*expr_gen.node_allocator_, branch[1]);
  24349. return expr_gen(T(std::numeric_limits<T>::quiet_NaN()));
  24350. }
  24351. else if (std::equal_to<T>()(T(0),c) && (details::e_add == operation))
  24352. {
  24353. free_node(*expr_gen.node_allocator_, branch[1]);
  24354. return branch[0];
  24355. }
  24356. else if (std::equal_to<T>()(T(1),c) && (details::e_mul == operation))
  24357. {
  24358. free_node(*expr_gen.node_allocator_, branch[1]);
  24359. return branch[0];
  24360. }
  24361. else if (std::equal_to<T>()(T(1),c) && (details::e_div == operation))
  24362. {
  24363. free_node(*expr_gen.node_allocator_, branch[1]);
  24364. return branch[0];
  24365. }
  24366. const bool op_addsub = (details::e_add == cobnode->operation()) ||
  24367. (details::e_sub == cobnode->operation()) ;
  24368. if (op_addsub)
  24369. {
  24370. switch (operation)
  24371. {
  24372. case details::e_add : cobnode->set_c(cobnode->c() + c); break;
  24373. case details::e_sub : cobnode->set_c(cobnode->c() - c); break;
  24374. default : return error_node();
  24375. }
  24376. result = cobnode;
  24377. }
  24378. else if (details::e_mul == cobnode->operation())
  24379. {
  24380. switch (operation)
  24381. {
  24382. case details::e_mul : cobnode->set_c(cobnode->c() * c); break;
  24383. case details::e_div : cobnode->set_c(cobnode->c() / c); break;
  24384. default : return error_node();
  24385. }
  24386. result = cobnode;
  24387. }
  24388. else if (details::e_div == cobnode->operation())
  24389. {
  24390. if (details::e_mul == operation)
  24391. {
  24392. cobnode->set_c(cobnode->c() * c);
  24393. result = cobnode;
  24394. }
  24395. else if (details::e_div == operation)
  24396. {
  24397. result = expr_gen.node_allocator_->
  24398. template allocate_tt<typename details::cob_node<Type,details::div_op<Type> > >
  24399. (cobnode->c() / c, cobnode->move_branch(0));
  24400. free_node(*expr_gen.node_allocator_, branch[0]);
  24401. }
  24402. }
  24403. if (result)
  24404. {
  24405. free_node(*expr_gen.node_allocator_,branch[1]);
  24406. }
  24407. }
  24408. // c o (cob) --> cob
  24409. else if (details::is_cob_node(branch[1]))
  24410. {
  24411. details::cob_base_node<Type>* cobnode = static_cast<details::cob_base_node<Type>*>(branch[1]);
  24412. const Type c = static_cast<details::literal_node<Type>*>(branch[0])->value();
  24413. if (std::equal_to<T>()(T(0),c) && (details::e_mul == operation))
  24414. {
  24415. free_node(*expr_gen.node_allocator_, branch[0]);
  24416. free_node(*expr_gen.node_allocator_, branch[1]);
  24417. return expr_gen(T(0));
  24418. }
  24419. else if (std::equal_to<T>()(T(0),c) && (details::e_div == operation))
  24420. {
  24421. free_node(*expr_gen.node_allocator_, branch[0]);
  24422. free_node(*expr_gen.node_allocator_, branch[1]);
  24423. return expr_gen(T(0));
  24424. }
  24425. else if (std::equal_to<T>()(T(0),c) && (details::e_add == operation))
  24426. {
  24427. free_node(*expr_gen.node_allocator_, branch[0]);
  24428. return branch[1];
  24429. }
  24430. else if (std::equal_to<T>()(T(1),c) && (details::e_mul == operation))
  24431. {
  24432. free_node(*expr_gen.node_allocator_, branch[0]);
  24433. return branch[1];
  24434. }
  24435. if (details::e_add == cobnode->operation())
  24436. {
  24437. if (details::e_add == operation)
  24438. {
  24439. cobnode->set_c(c + cobnode->c());
  24440. result = cobnode;
  24441. }
  24442. else if (details::e_sub == operation)
  24443. {
  24444. result = expr_gen.node_allocator_->
  24445. template allocate_tt<typename details::cob_node<Type,details::sub_op<Type> > >
  24446. (c - cobnode->c(), cobnode->move_branch(0));
  24447. free_node(*expr_gen.node_allocator_,branch[1]);
  24448. }
  24449. }
  24450. else if (details::e_sub == cobnode->operation())
  24451. {
  24452. if (details::e_add == operation)
  24453. {
  24454. cobnode->set_c(c + cobnode->c());
  24455. result = cobnode;
  24456. }
  24457. else if (details::e_sub == operation)
  24458. {
  24459. result = expr_gen.node_allocator_->
  24460. template allocate_tt<typename details::cob_node<Type,details::add_op<Type> > >
  24461. (c - cobnode->c(), cobnode->move_branch(0));
  24462. free_node(*expr_gen.node_allocator_,branch[1]);
  24463. }
  24464. }
  24465. else if (details::e_mul == cobnode->operation())
  24466. {
  24467. if (details::e_mul == operation)
  24468. {
  24469. cobnode->set_c(c * cobnode->c());
  24470. result = cobnode;
  24471. }
  24472. else if (details::e_div == operation)
  24473. {
  24474. result = expr_gen.node_allocator_->
  24475. template allocate_tt<typename details::cob_node<Type,details::div_op<Type> > >
  24476. (c / cobnode->c(), cobnode->move_branch(0));
  24477. free_node(*expr_gen.node_allocator_,branch[1]);
  24478. }
  24479. }
  24480. else if (details::e_div == cobnode->operation())
  24481. {
  24482. if (details::e_mul == operation)
  24483. {
  24484. cobnode->set_c(c * cobnode->c());
  24485. result = cobnode;
  24486. }
  24487. else if (details::e_div == operation)
  24488. {
  24489. result = expr_gen.node_allocator_->
  24490. template allocate_tt<typename details::cob_node<Type,details::mul_op<Type> > >
  24491. (c / cobnode->c(), cobnode->move_branch(0));
  24492. free_node(*expr_gen.node_allocator_,branch[1]);
  24493. }
  24494. }
  24495. if (result)
  24496. {
  24497. free_node(*expr_gen.node_allocator_,branch[0]);
  24498. }
  24499. }
  24500. return result;
  24501. }
  24502. };
  24503. struct synthesize_coboc_expression
  24504. {
  24505. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  24506. const details::operator_type& operation,
  24507. expression_node_ptr (&branch)[2])
  24508. {
  24509. expression_node_ptr result = error_node();
  24510. // (boc) o c --> boc
  24511. if (details::is_boc_node(branch[0]))
  24512. {
  24513. details::boc_base_node<Type>* bocnode = static_cast<details::boc_base_node<Type>*>(branch[0]);
  24514. const Type c = static_cast<details::literal_node<Type>*>(branch[1])->value();
  24515. if (details::e_add == bocnode->operation())
  24516. {
  24517. switch (operation)
  24518. {
  24519. case details::e_add : bocnode->set_c(bocnode->c() + c); break;
  24520. case details::e_sub : bocnode->set_c(bocnode->c() - c); break;
  24521. default : return error_node();
  24522. }
  24523. result = bocnode;
  24524. }
  24525. else if (details::e_mul == bocnode->operation())
  24526. {
  24527. switch (operation)
  24528. {
  24529. case details::e_mul : bocnode->set_c(bocnode->c() * c); break;
  24530. case details::e_div : bocnode->set_c(bocnode->c() / c); break;
  24531. default : return error_node();
  24532. }
  24533. result = bocnode;
  24534. }
  24535. else if (details::e_sub == bocnode->operation())
  24536. {
  24537. if (details::e_add == operation)
  24538. {
  24539. result = expr_gen.node_allocator_->
  24540. template allocate_tt<typename details::boc_node<Type,details::add_op<Type> > >
  24541. (bocnode->move_branch(0), c - bocnode->c());
  24542. free_node(*expr_gen.node_allocator_,branch[0]);
  24543. }
  24544. else if (details::e_sub == operation)
  24545. {
  24546. bocnode->set_c(bocnode->c() + c);
  24547. result = bocnode;
  24548. }
  24549. }
  24550. else if (details::e_div == bocnode->operation())
  24551. {
  24552. switch (operation)
  24553. {
  24554. case details::e_div : bocnode->set_c(bocnode->c() * c); break;
  24555. case details::e_mul : bocnode->set_c(bocnode->c() / c); break;
  24556. default : return error_node();
  24557. }
  24558. result = bocnode;
  24559. }
  24560. if (result)
  24561. {
  24562. free_node(*expr_gen.node_allocator_, branch[1]);
  24563. }
  24564. }
  24565. // c o (boc) --> boc
  24566. else if (details::is_boc_node(branch[1]))
  24567. {
  24568. details::boc_base_node<Type>* bocnode = static_cast<details::boc_base_node<Type>*>(branch[1]);
  24569. const Type c = static_cast<details::literal_node<Type>*>(branch[0])->value();
  24570. if (details::e_add == bocnode->operation())
  24571. {
  24572. if (details::e_add == operation)
  24573. {
  24574. bocnode->set_c(c + bocnode->c());
  24575. result = bocnode;
  24576. }
  24577. else if (details::e_sub == operation)
  24578. {
  24579. result = expr_gen.node_allocator_->
  24580. template allocate_tt<typename details::cob_node<Type,details::sub_op<Type> > >
  24581. (c - bocnode->c(), bocnode->move_branch(0));
  24582. free_node(*expr_gen.node_allocator_,branch[1]);
  24583. }
  24584. }
  24585. else if (details::e_sub == bocnode->operation())
  24586. {
  24587. if (details::e_add == operation)
  24588. {
  24589. result = expr_gen.node_allocator_->
  24590. template allocate_tt<typename details::boc_node<Type,details::add_op<Type> > >
  24591. (bocnode->move_branch(0), c - bocnode->c());
  24592. free_node(*expr_gen.node_allocator_,branch[1]);
  24593. }
  24594. else if (details::e_sub == operation)
  24595. {
  24596. result = expr_gen.node_allocator_->
  24597. template allocate_tt<typename details::cob_node<Type,details::sub_op<Type> > >
  24598. (c + bocnode->c(), bocnode->move_branch(0));
  24599. free_node(*expr_gen.node_allocator_,branch[1]);
  24600. }
  24601. }
  24602. else if (details::e_mul == bocnode->operation())
  24603. {
  24604. if (details::e_mul == operation)
  24605. {
  24606. bocnode->set_c(c * bocnode->c());
  24607. result = bocnode;
  24608. }
  24609. else if (details::e_div == operation)
  24610. {
  24611. result = expr_gen.node_allocator_->
  24612. template allocate_tt<typename details::cob_node<Type,details::div_op<Type> > >
  24613. (c / bocnode->c(), bocnode->move_branch(0));
  24614. free_node(*expr_gen.node_allocator_,branch[1]);
  24615. }
  24616. }
  24617. else if (details::e_div == bocnode->operation())
  24618. {
  24619. if (details::e_mul == operation)
  24620. {
  24621. bocnode->set_c(bocnode->c() / c);
  24622. result = bocnode;
  24623. }
  24624. else if (details::e_div == operation)
  24625. {
  24626. result = expr_gen.node_allocator_->
  24627. template allocate_tt<typename details::cob_node<Type,details::div_op<Type> > >
  24628. (c * bocnode->c(), bocnode->move_branch(0));
  24629. free_node(*expr_gen.node_allocator_,branch[1]);
  24630. }
  24631. }
  24632. if (result)
  24633. {
  24634. free_node(*expr_gen.node_allocator_,branch[0]);
  24635. }
  24636. }
  24637. return result;
  24638. }
  24639. };
  24640. #ifndef exprtk_disable_enhanced_features
  24641. inline bool synthesize_expression(const details::operator_type& operation,
  24642. expression_node_ptr (&branch)[2],
  24643. expression_node_ptr& result)
  24644. {
  24645. result = error_node();
  24646. if (!operation_optimisable(operation))
  24647. return false;
  24648. const std::string node_id = branch_to_id(branch);
  24649. const typename synthesize_map_t::iterator itr = synthesize_map_.find(node_id);
  24650. if (synthesize_map_.end() != itr)
  24651. {
  24652. result = itr->second((*this), operation, branch);
  24653. return true;
  24654. }
  24655. else
  24656. return false;
  24657. }
  24658. struct synthesize_vov_expression
  24659. {
  24660. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  24661. const details::operator_type& operation,
  24662. expression_node_ptr (&branch)[2])
  24663. {
  24664. const Type& v1 = static_cast<details::variable_node<Type>*>(branch[0])->ref();
  24665. const Type& v2 = static_cast<details::variable_node<Type>*>(branch[1])->ref();
  24666. switch (operation)
  24667. {
  24668. #define case_stmt(op0,op1) \
  24669. case op0 : return expr_gen.node_allocator_-> \
  24670. template allocate_rr<typename details::vov_node<Type,op1<Type> > > \
  24671. (v1, v2); \
  24672. basic_opr_switch_statements
  24673. extended_opr_switch_statements
  24674. #undef case_stmt
  24675. default : return error_node();
  24676. }
  24677. }
  24678. };
  24679. struct synthesize_cov_expression
  24680. {
  24681. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  24682. const details::operator_type& operation,
  24683. expression_node_ptr (&branch)[2])
  24684. {
  24685. const Type c = static_cast<details::literal_node<Type>*> (branch[0])->value();
  24686. const Type& v = static_cast<details::variable_node<Type>*>(branch[1])->ref ();
  24687. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  24688. if (std::equal_to<T>()(T(0),c) && (details::e_mul == operation))
  24689. return expr_gen(T(0));
  24690. else if (std::equal_to<T>()(T(0),c) && (details::e_div == operation))
  24691. return expr_gen(T(0));
  24692. else if (std::equal_to<T>()(T(0),c) && (details::e_add == operation))
  24693. return static_cast<details::variable_node<Type>*>(branch[1]);
  24694. else if (std::equal_to<T>()(T(1),c) && (details::e_mul == operation))
  24695. return static_cast<details::variable_node<Type>*>(branch[1]);
  24696. switch (operation)
  24697. {
  24698. #define case_stmt(op0,op1) \
  24699. case op0 : return expr_gen.node_allocator_-> \
  24700. template allocate_cr<typename details::cov_node<Type,op1<Type> > > \
  24701. (c, v); \
  24702. basic_opr_switch_statements
  24703. extended_opr_switch_statements
  24704. #undef case_stmt
  24705. default : return error_node();
  24706. }
  24707. }
  24708. };
  24709. struct synthesize_voc_expression
  24710. {
  24711. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  24712. const details::operator_type& operation,
  24713. expression_node_ptr (&branch)[2])
  24714. {
  24715. const Type& v = static_cast<details::variable_node<Type>*>(branch[0])->ref ();
  24716. const Type c = static_cast<details::literal_node<Type>*> (branch[1])->value();
  24717. details::free_node(*(expr_gen.node_allocator_), branch[1]);
  24718. if (expr_gen.cardinal_pow_optimisable(operation,c))
  24719. {
  24720. if (std::equal_to<T>()(T(1),c))
  24721. return branch[0];
  24722. else
  24723. return expr_gen.cardinal_pow_optimisation(v,c);
  24724. }
  24725. else if (std::equal_to<T>()(T(0),c) && (details::e_mul == operation))
  24726. return expr_gen(T(0));
  24727. else if (std::equal_to<T>()(T(0),c) && (details::e_div == operation))
  24728. return expr_gen(std::numeric_limits<T>::quiet_NaN());
  24729. else if (std::equal_to<T>()(T(0),c) && (details::e_add == operation))
  24730. return static_cast<details::variable_node<Type>*>(branch[0]);
  24731. else if (std::equal_to<T>()(T(1),c) && (details::e_mul == operation))
  24732. return static_cast<details::variable_node<Type>*>(branch[0]);
  24733. else if (std::equal_to<T>()(T(1),c) && (details::e_div == operation))
  24734. return static_cast<details::variable_node<Type>*>(branch[0]);
  24735. switch (operation)
  24736. {
  24737. #define case_stmt(op0,op1) \
  24738. case op0 : return expr_gen.node_allocator_-> \
  24739. template allocate_rc<typename details::voc_node<Type,op1<Type> > > \
  24740. (v, c); \
  24741. basic_opr_switch_statements
  24742. extended_opr_switch_statements
  24743. #undef case_stmt
  24744. default : return error_node();
  24745. }
  24746. }
  24747. };
  24748. struct synthesize_sf3ext_expression
  24749. {
  24750. template <typename T0, typename T1, typename T2>
  24751. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  24752. const details::operator_type& sf3opr,
  24753. T0 t0, T1 t1, T2 t2)
  24754. {
  24755. switch (sf3opr)
  24756. {
  24757. #define case_stmt(op) \
  24758. case details::e_sf##op : return details::T0oT1oT2_sf3ext<T,T0,T1,T2,details::sf##op##_op<Type> >:: \
  24759. allocate(*(expr_gen.node_allocator_), t0, t1, t2); \
  24760. case_stmt(00) case_stmt(01) case_stmt(02) case_stmt(03)
  24761. case_stmt(04) case_stmt(05) case_stmt(06) case_stmt(07)
  24762. case_stmt(08) case_stmt(09) case_stmt(10) case_stmt(11)
  24763. case_stmt(12) case_stmt(13) case_stmt(14) case_stmt(15)
  24764. case_stmt(16) case_stmt(17) case_stmt(18) case_stmt(19)
  24765. case_stmt(20) case_stmt(21) case_stmt(22) case_stmt(23)
  24766. case_stmt(24) case_stmt(25) case_stmt(26) case_stmt(27)
  24767. case_stmt(28) case_stmt(29) case_stmt(30)
  24768. #undef case_stmt
  24769. default : return error_node();
  24770. }
  24771. }
  24772. template <typename T0, typename T1, typename T2>
  24773. static inline bool compile(expression_generator<Type>& expr_gen, const std::string& id,
  24774. T0 t0, T1 t1, T2 t2,
  24775. expression_node_ptr& result)
  24776. {
  24777. details::operator_type sf3opr;
  24778. if (!expr_gen.sf3_optimisable(id,sf3opr))
  24779. return false;
  24780. else
  24781. result = synthesize_sf3ext_expression::template process<T0, T1, T2>
  24782. (expr_gen, sf3opr, t0, t1, t2);
  24783. return true;
  24784. }
  24785. };
  24786. struct synthesize_sf4ext_expression
  24787. {
  24788. template <typename T0, typename T1, typename T2, typename T3>
  24789. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  24790. const details::operator_type& sf4opr,
  24791. T0 t0, T1 t1, T2 t2, T3 t3)
  24792. {
  24793. switch (sf4opr)
  24794. {
  24795. #define case_stmt0(op) \
  24796. case details::e_sf##op : return details::T0oT1oT2oT3_sf4ext<Type,T0,T1,T2,T3,details::sf##op##_op<Type> >:: \
  24797. allocate(*(expr_gen.node_allocator_), t0, t1, t2, t3); \
  24798. #define case_stmt1(op) \
  24799. case details::e_sf4ext##op : return details::T0oT1oT2oT3_sf4ext<Type,T0,T1,T2,T3,details::sfext##op##_op<Type> >:: \
  24800. allocate(*(expr_gen.node_allocator_), t0, t1, t2, t3); \
  24801. case_stmt0(48) case_stmt0(49) case_stmt0(50) case_stmt0(51)
  24802. case_stmt0(52) case_stmt0(53) case_stmt0(54) case_stmt0(55)
  24803. case_stmt0(56) case_stmt0(57) case_stmt0(58) case_stmt0(59)
  24804. case_stmt0(60) case_stmt0(61) case_stmt0(62) case_stmt0(63)
  24805. case_stmt0(64) case_stmt0(65) case_stmt0(66) case_stmt0(67)
  24806. case_stmt0(68) case_stmt0(69) case_stmt0(70) case_stmt0(71)
  24807. case_stmt0(72) case_stmt0(73) case_stmt0(74) case_stmt0(75)
  24808. case_stmt0(76) case_stmt0(77) case_stmt0(78) case_stmt0(79)
  24809. case_stmt0(80) case_stmt0(81) case_stmt0(82) case_stmt0(83)
  24810. case_stmt1(00) case_stmt1(01) case_stmt1(02) case_stmt1(03)
  24811. case_stmt1(04) case_stmt1(05) case_stmt1(06) case_stmt1(07)
  24812. case_stmt1(08) case_stmt1(09) case_stmt1(10) case_stmt1(11)
  24813. case_stmt1(12) case_stmt1(13) case_stmt1(14) case_stmt1(15)
  24814. case_stmt1(16) case_stmt1(17) case_stmt1(18) case_stmt1(19)
  24815. case_stmt1(20) case_stmt1(21) case_stmt1(22) case_stmt1(23)
  24816. case_stmt1(24) case_stmt1(25) case_stmt1(26) case_stmt1(27)
  24817. case_stmt1(28) case_stmt1(29) case_stmt1(30) case_stmt1(31)
  24818. case_stmt1(32) case_stmt1(33) case_stmt1(34) case_stmt1(35)
  24819. case_stmt1(36) case_stmt1(37) case_stmt1(38) case_stmt1(39)
  24820. case_stmt1(40) case_stmt1(41) case_stmt1(42) case_stmt1(43)
  24821. case_stmt1(44) case_stmt1(45) case_stmt1(46) case_stmt1(47)
  24822. case_stmt1(48) case_stmt1(49) case_stmt1(50) case_stmt1(51)
  24823. case_stmt1(52) case_stmt1(53) case_stmt1(54) case_stmt1(55)
  24824. case_stmt1(56) case_stmt1(57) case_stmt1(58) case_stmt1(59)
  24825. case_stmt1(60) case_stmt1(61)
  24826. #undef case_stmt0
  24827. #undef case_stmt1
  24828. default : return error_node();
  24829. }
  24830. }
  24831. template <typename T0, typename T1, typename T2, typename T3>
  24832. static inline bool compile(expression_generator<Type>& expr_gen, const std::string& id,
  24833. T0 t0, T1 t1, T2 t2, T3 t3,
  24834. expression_node_ptr& result)
  24835. {
  24836. details::operator_type sf4opr;
  24837. if (!expr_gen.sf4_optimisable(id,sf4opr))
  24838. return false;
  24839. else
  24840. result = synthesize_sf4ext_expression::template process<T0, T1, T2, T3>
  24841. (expr_gen, sf4opr, t0, t1, t2, t3);
  24842. return true;
  24843. }
  24844. // T o (sf3ext)
  24845. template <typename ExternalType>
  24846. static inline bool compile_right(expression_generator<Type>& expr_gen,
  24847. ExternalType t,
  24848. const details::operator_type& operation,
  24849. expression_node_ptr& sf3node,
  24850. expression_node_ptr& result)
  24851. {
  24852. if (!details::is_sf3ext_node(sf3node))
  24853. return false;
  24854. typedef details::T0oT1oT2_base_node<Type>* sf3ext_base_ptr;
  24855. sf3ext_base_ptr n = static_cast<sf3ext_base_ptr>(sf3node);
  24856. const std::string id = "t" + expr_gen.to_str(operation) + "(" + n->type_id() + ")";
  24857. switch (n->type())
  24858. {
  24859. case details::expression_node<Type>::e_covoc : return compile_right_impl
  24860. <typename covoc_t::sf3_type_node,ExternalType, ctype, vtype, ctype>
  24861. (expr_gen, id, t, sf3node, result);
  24862. case details::expression_node<Type>::e_covov : return compile_right_impl
  24863. <typename covov_t::sf3_type_node,ExternalType, ctype, vtype, vtype>
  24864. (expr_gen, id, t, sf3node, result);
  24865. case details::expression_node<Type>::e_vocov : return compile_right_impl
  24866. <typename vocov_t::sf3_type_node,ExternalType, vtype, ctype, vtype>
  24867. (expr_gen, id, t, sf3node, result);
  24868. case details::expression_node<Type>::e_vovoc : return compile_right_impl
  24869. <typename vovoc_t::sf3_type_node,ExternalType, vtype, vtype, ctype>
  24870. (expr_gen, id, t, sf3node, result);
  24871. case details::expression_node<Type>::e_vovov : return compile_right_impl
  24872. <typename vovov_t::sf3_type_node,ExternalType, vtype, vtype, vtype>
  24873. (expr_gen, id, t, sf3node, result);
  24874. default : return false;
  24875. }
  24876. }
  24877. // (sf3ext) o T
  24878. template <typename ExternalType>
  24879. static inline bool compile_left(expression_generator<Type>& expr_gen,
  24880. ExternalType t,
  24881. const details::operator_type& operation,
  24882. expression_node_ptr& sf3node,
  24883. expression_node_ptr& result)
  24884. {
  24885. if (!details::is_sf3ext_node(sf3node))
  24886. return false;
  24887. typedef details::T0oT1oT2_base_node<Type>* sf3ext_base_ptr;
  24888. sf3ext_base_ptr n = static_cast<sf3ext_base_ptr>(sf3node);
  24889. const std::string id = "(" + n->type_id() + ")" + expr_gen.to_str(operation) + "t";
  24890. switch (n->type())
  24891. {
  24892. case details::expression_node<Type>::e_covoc : return compile_left_impl
  24893. <typename covoc_t::sf3_type_node,ExternalType, ctype, vtype, ctype>
  24894. (expr_gen, id, t, sf3node, result);
  24895. case details::expression_node<Type>::e_covov : return compile_left_impl
  24896. <typename covov_t::sf3_type_node,ExternalType, ctype, vtype, vtype>
  24897. (expr_gen, id, t, sf3node, result);
  24898. case details::expression_node<Type>::e_vocov : return compile_left_impl
  24899. <typename vocov_t::sf3_type_node,ExternalType, vtype, ctype, vtype>
  24900. (expr_gen, id, t, sf3node, result);
  24901. case details::expression_node<Type>::e_vovoc : return compile_left_impl
  24902. <typename vovoc_t::sf3_type_node,ExternalType, vtype, vtype, ctype>
  24903. (expr_gen, id, t, sf3node, result);
  24904. case details::expression_node<Type>::e_vovov : return compile_left_impl
  24905. <typename vovov_t::sf3_type_node,ExternalType, vtype, vtype, vtype>
  24906. (expr_gen, id, t, sf3node, result);
  24907. default : return false;
  24908. }
  24909. }
  24910. template <typename SF3TypeNode, typename ExternalType, typename T0, typename T1, typename T2>
  24911. static inline bool compile_right_impl(expression_generator<Type>& expr_gen,
  24912. const std::string& id,
  24913. ExternalType t,
  24914. expression_node_ptr& node,
  24915. expression_node_ptr& result)
  24916. {
  24917. SF3TypeNode* n = dynamic_cast<SF3TypeNode*>(node);
  24918. if (n)
  24919. {
  24920. T0 t0 = n->t0();
  24921. T1 t1 = n->t1();
  24922. T2 t2 = n->t2();
  24923. return synthesize_sf4ext_expression::template compile<ExternalType, T0, T1, T2>
  24924. (expr_gen, id, t, t0, t1, t2, result);
  24925. }
  24926. else
  24927. return false;
  24928. }
  24929. template <typename SF3TypeNode, typename ExternalType, typename T0, typename T1, typename T2>
  24930. static inline bool compile_left_impl(expression_generator<Type>& expr_gen,
  24931. const std::string& id,
  24932. ExternalType t,
  24933. expression_node_ptr& node,
  24934. expression_node_ptr& result)
  24935. {
  24936. SF3TypeNode* n = dynamic_cast<SF3TypeNode*>(node);
  24937. if (n)
  24938. {
  24939. T0 t0 = n->t0();
  24940. T1 t1 = n->t1();
  24941. T2 t2 = n->t2();
  24942. return synthesize_sf4ext_expression::template compile<T0, T1, T2, ExternalType>
  24943. (expr_gen, id, t0, t1, t2, t, result);
  24944. }
  24945. else
  24946. return false;
  24947. }
  24948. };
  24949. struct synthesize_vovov_expression0
  24950. {
  24951. typedef typename vovov_t::type0 node_type;
  24952. typedef typename vovov_t::sf3_type sf3_type;
  24953. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  24954. const details::operator_type& operation,
  24955. expression_node_ptr (&branch)[2])
  24956. {
  24957. // (v0 o0 v1) o1 (v2)
  24958. const details::vov_base_node<Type>* vov = static_cast<details::vov_base_node<Type>*>(branch[0]);
  24959. const Type& v0 = vov->v0();
  24960. const Type& v1 = vov->v1();
  24961. const Type& v2 = static_cast<details::variable_node<Type>*>(branch[1])->ref();
  24962. const details::operator_type o0 = vov->operation();
  24963. const details::operator_type o1 = operation;
  24964. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  24965. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  24966. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  24967. expression_node_ptr result = error_node();
  24968. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  24969. {
  24970. // (v0 / v1) / v2 --> (vovov) v0 / (v1 * v2)
  24971. if ((details::e_div == o0) && (details::e_div == o1))
  24972. {
  24973. const bool synthesis_result =
  24974. synthesize_sf3ext_expression::
  24975. template compile<vtype,vtype,vtype>(expr_gen, "t/(t*t)", v0, v1, v2, result);
  24976. exprtk_debug(("(v0 / v1) / v2 --> (vovov) v0 / (v1 * v2)\n"));
  24977. return (synthesis_result) ? result : error_node();
  24978. }
  24979. }
  24980. const bool synthesis_result =
  24981. synthesize_sf3ext_expression::template compile<vtype, vtype, vtype>
  24982. (expr_gen, id(expr_gen, o0, o1), v0, v1, v2, result);
  24983. if (synthesis_result)
  24984. return result;
  24985. else if (!expr_gen.valid_operator(o0,f0))
  24986. return error_node();
  24987. else if (!expr_gen.valid_operator(o1,f1))
  24988. return error_node();
  24989. else
  24990. return node_type::allocate(*(expr_gen.node_allocator_), v0, v1, v2, f0, f1);
  24991. }
  24992. static inline std::string id(expression_generator<Type>& expr_gen,
  24993. const details::operator_type o0, const details::operator_type o1)
  24994. {
  24995. return details::build_string()
  24996. << "(t" << expr_gen.to_str(o0)
  24997. << "t)" << expr_gen.to_str(o1)
  24998. << "t";
  24999. }
  25000. };
  25001. struct synthesize_vovov_expression1
  25002. {
  25003. typedef typename vovov_t::type1 node_type;
  25004. typedef typename vovov_t::sf3_type sf3_type;
  25005. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  25006. const details::operator_type& operation,
  25007. expression_node_ptr (&branch)[2])
  25008. {
  25009. // (v0) o0 (v1 o1 v2)
  25010. const details::vov_base_node<Type>* vov = static_cast<details::vov_base_node<Type>*>(branch[1]);
  25011. const Type& v0 = static_cast<details::variable_node<Type>*>(branch[0])->ref();
  25012. const Type& v1 = vov->v0();
  25013. const Type& v2 = vov->v1();
  25014. const details::operator_type o0 = operation;
  25015. const details::operator_type o1 = vov->operation();
  25016. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  25017. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  25018. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  25019. expression_node_ptr result = error_node();
  25020. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  25021. {
  25022. // v0 / (v1 / v2) --> (vovov) (v0 * v2) / v1
  25023. if ((details::e_div == o0) && (details::e_div == o1))
  25024. {
  25025. const bool synthesis_result =
  25026. synthesize_sf3ext_expression::
  25027. template compile<vtype,vtype,vtype>(expr_gen, "(t*t)/t", v0, v2, v1, result);
  25028. exprtk_debug(("v0 / (v1 / v2) --> (vovov) (v0 * v2) / v1\n"));
  25029. return (synthesis_result) ? result : error_node();
  25030. }
  25031. }
  25032. const bool synthesis_result =
  25033. synthesize_sf3ext_expression::template compile<vtype, vtype, vtype>
  25034. (expr_gen, id(expr_gen, o0, o1), v0, v1, v2, result);
  25035. if (synthesis_result)
  25036. return result;
  25037. else if (!expr_gen.valid_operator(o0,f0))
  25038. return error_node();
  25039. else if (!expr_gen.valid_operator(o1,f1))
  25040. return error_node();
  25041. else
  25042. return node_type::allocate(*(expr_gen.node_allocator_), v0, v1, v2, f0, f1);
  25043. }
  25044. static inline std::string id(expression_generator<Type>& expr_gen,
  25045. const details::operator_type o0, const details::operator_type o1)
  25046. {
  25047. return details::build_string()
  25048. << "t" << expr_gen.to_str(o0)
  25049. << "(t" << expr_gen.to_str(o1)
  25050. << "t)";
  25051. }
  25052. };
  25053. struct synthesize_vovoc_expression0
  25054. {
  25055. typedef typename vovoc_t::type0 node_type;
  25056. typedef typename vovoc_t::sf3_type sf3_type;
  25057. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  25058. const details::operator_type& operation,
  25059. expression_node_ptr (&branch)[2])
  25060. {
  25061. // (v0 o0 v1) o1 (c)
  25062. const details::vov_base_node<Type>* vov = static_cast<details::vov_base_node<Type>*>(branch[0]);
  25063. const Type& v0 = vov->v0();
  25064. const Type& v1 = vov->v1();
  25065. const Type c = static_cast<details::literal_node<Type>*>(branch[1])->value();
  25066. const details::operator_type o0 = vov->operation();
  25067. const details::operator_type o1 = operation;
  25068. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  25069. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  25070. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  25071. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  25072. expression_node_ptr result = error_node();
  25073. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  25074. {
  25075. // (v0 / v1) / c --> (vovoc) v0 / (v1 * c)
  25076. if ((details::e_div == o0) && (details::e_div == o1))
  25077. {
  25078. const bool synthesis_result =
  25079. synthesize_sf3ext_expression::
  25080. template compile<vtype,vtype,ctype>(expr_gen, "t/(t*t)", v0, v1, c, result);
  25081. exprtk_debug(("(v0 / v1) / c --> (vovoc) v0 / (v1 * c)\n"));
  25082. return (synthesis_result) ? result : error_node();
  25083. }
  25084. }
  25085. const bool synthesis_result =
  25086. synthesize_sf3ext_expression::template compile<vtype, vtype, ctype>
  25087. (expr_gen, id(expr_gen, o0, o1), v0, v1, c, result);
  25088. if (synthesis_result)
  25089. return result;
  25090. else if (!expr_gen.valid_operator(o0,f0))
  25091. return error_node();
  25092. else if (!expr_gen.valid_operator(o1,f1))
  25093. return error_node();
  25094. else
  25095. return node_type::allocate(*(expr_gen.node_allocator_), v0, v1, c, f0, f1);
  25096. }
  25097. static inline std::string id(expression_generator<Type>& expr_gen,
  25098. const details::operator_type o0, const details::operator_type o1)
  25099. {
  25100. return details::build_string()
  25101. << "(t" << expr_gen.to_str(o0)
  25102. << "t)" << expr_gen.to_str(o1)
  25103. << "t";
  25104. }
  25105. };
  25106. struct synthesize_vovoc_expression1
  25107. {
  25108. typedef typename vovoc_t::type1 node_type;
  25109. typedef typename vovoc_t::sf3_type sf3_type;
  25110. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  25111. const details::operator_type& operation,
  25112. expression_node_ptr (&branch)[2])
  25113. {
  25114. // (v0) o0 (v1 o1 c)
  25115. const details::voc_base_node<Type>* voc = static_cast<const details::voc_base_node<Type>*>(branch[1]);
  25116. const Type& v0 = static_cast<details::variable_node<Type>*>(branch[0])->ref();
  25117. const Type& v1 = voc->v();
  25118. const Type c = voc->c();
  25119. const details::operator_type o0 = operation;
  25120. const details::operator_type o1 = voc->operation();
  25121. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  25122. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  25123. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  25124. expression_node_ptr result = error_node();
  25125. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  25126. {
  25127. // v0 / (v1 / c) --> (vocov) (v0 * c) / v1
  25128. if ((details::e_div == o0) && (details::e_div == o1))
  25129. {
  25130. const bool synthesis_result =
  25131. synthesize_sf3ext_expression::
  25132. template compile<vtype,ctype,vtype>(expr_gen, "(t*t)/t", v0, c, v1, result);
  25133. exprtk_debug(("v0 / (v1 / c) --> (vocov) (v0 * c) / v1\n"));
  25134. return (synthesis_result) ? result : error_node();
  25135. }
  25136. }
  25137. const bool synthesis_result =
  25138. synthesize_sf3ext_expression::template compile<vtype, vtype, ctype>
  25139. (expr_gen, id(expr_gen, o0, o1), v0, v1, c, result);
  25140. if (synthesis_result)
  25141. return result;
  25142. else if (!expr_gen.valid_operator(o0,f0))
  25143. return error_node();
  25144. else if (!expr_gen.valid_operator(o1,f1))
  25145. return error_node();
  25146. else
  25147. return node_type::allocate(*(expr_gen.node_allocator_), v0, v1, c, f0, f1);
  25148. }
  25149. static inline std::string id(expression_generator<Type>& expr_gen,
  25150. const details::operator_type o0, const details::operator_type o1)
  25151. {
  25152. return details::build_string()
  25153. << "t" << expr_gen.to_str(o0)
  25154. << "(t" << expr_gen.to_str(o1)
  25155. << "t)";
  25156. }
  25157. };
  25158. struct synthesize_vocov_expression0
  25159. {
  25160. typedef typename vocov_t::type0 node_type;
  25161. typedef typename vocov_t::sf3_type sf3_type;
  25162. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  25163. const details::operator_type& operation,
  25164. expression_node_ptr (&branch)[2])
  25165. {
  25166. // (v0 o0 c) o1 (v1)
  25167. const details::voc_base_node<Type>* voc = static_cast<details::voc_base_node<Type>*>(branch[0]);
  25168. const Type& v0 = voc->v();
  25169. const Type c = voc->c();
  25170. const Type& v1 = static_cast<details::variable_node<Type>*>(branch[1])->ref();
  25171. const details::operator_type o0 = voc->operation();
  25172. const details::operator_type o1 = operation;
  25173. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  25174. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  25175. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  25176. expression_node_ptr result = error_node();
  25177. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  25178. {
  25179. // (v0 / c) / v1 --> (vovoc) v0 / (v1 * c)
  25180. if ((details::e_div == o0) && (details::e_div == o1))
  25181. {
  25182. const bool synthesis_result =
  25183. synthesize_sf3ext_expression::
  25184. template compile<vtype,vtype,ctype>(expr_gen, "t/(t*t)", v0, v1, c, result);
  25185. exprtk_debug(("(v0 / c) / v1 --> (vovoc) v0 / (v1 * c)\n"));
  25186. return (synthesis_result) ? result : error_node();
  25187. }
  25188. }
  25189. const bool synthesis_result =
  25190. synthesize_sf3ext_expression::template compile<vtype, ctype, vtype>
  25191. (expr_gen, id(expr_gen, o0, o1), v0, c, v1, result);
  25192. if (synthesis_result)
  25193. return result;
  25194. else if (!expr_gen.valid_operator(o0,f0))
  25195. return error_node();
  25196. else if (!expr_gen.valid_operator(o1,f1))
  25197. return error_node();
  25198. else
  25199. return node_type::allocate(*(expr_gen.node_allocator_), v0, c, v1, f0, f1);
  25200. }
  25201. static inline std::string id(expression_generator<Type>& expr_gen,
  25202. const details::operator_type o0, const details::operator_type o1)
  25203. {
  25204. return details::build_string()
  25205. << "(t" << expr_gen.to_str(o0)
  25206. << "t)" << expr_gen.to_str(o1)
  25207. << "t";
  25208. }
  25209. };
  25210. struct synthesize_vocov_expression1
  25211. {
  25212. typedef typename vocov_t::type1 node_type;
  25213. typedef typename vocov_t::sf3_type sf3_type;
  25214. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  25215. const details::operator_type& operation,
  25216. expression_node_ptr (&branch)[2])
  25217. {
  25218. // (v0) o0 (c o1 v1)
  25219. const details::cov_base_node<Type>* cov = static_cast<details::cov_base_node<Type>*>(branch[1]);
  25220. const Type& v0 = static_cast<details::variable_node<Type>*>(branch[0])->ref();
  25221. const Type c = cov->c();
  25222. const Type& v1 = cov->v();
  25223. const details::operator_type o0 = operation;
  25224. const details::operator_type o1 = cov->operation();
  25225. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  25226. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  25227. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  25228. expression_node_ptr result = error_node();
  25229. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  25230. {
  25231. // v0 / (c / v1) --> (vovoc) (v0 * v1) / c
  25232. if ((details::e_div == o0) && (details::e_div == o1))
  25233. {
  25234. const bool synthesis_result =
  25235. synthesize_sf3ext_expression::
  25236. template compile<vtype, vtype, ctype>(expr_gen, "(t*t)/t", v0, v1, c, result);
  25237. exprtk_debug(("v0 / (c / v1) --> (vovoc) (v0 * v1) / c\n"));
  25238. return (synthesis_result) ? result : error_node();
  25239. }
  25240. }
  25241. const bool synthesis_result =
  25242. synthesize_sf3ext_expression::template compile<vtype, ctype, vtype>
  25243. (expr_gen, id(expr_gen, o0, o1), v0, c, v1, result);
  25244. if (synthesis_result)
  25245. return result;
  25246. else if (!expr_gen.valid_operator(o0,f0))
  25247. return error_node();
  25248. else if (!expr_gen.valid_operator(o1,f1))
  25249. return error_node();
  25250. else
  25251. return node_type::allocate(*(expr_gen.node_allocator_), v0, c, v1, f0, f1);
  25252. }
  25253. static inline std::string id(expression_generator<Type>& expr_gen,
  25254. const details::operator_type o0, const details::operator_type o1)
  25255. {
  25256. return details::build_string()
  25257. << "t" << expr_gen.to_str(o0)
  25258. << "(t" << expr_gen.to_str(o1)
  25259. << "t)";
  25260. }
  25261. };
  25262. struct synthesize_covov_expression0
  25263. {
  25264. typedef typename covov_t::type0 node_type;
  25265. typedef typename covov_t::sf3_type sf3_type;
  25266. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  25267. const details::operator_type& operation,
  25268. expression_node_ptr (&branch)[2])
  25269. {
  25270. // (c o0 v0) o1 (v1)
  25271. const details::cov_base_node<Type>* cov = static_cast<details::cov_base_node<Type>*>(branch[0]);
  25272. const Type c = cov->c();
  25273. const Type& v0 = cov->v();
  25274. const Type& v1 = static_cast<details::variable_node<Type>*>(branch[1])->ref();
  25275. const details::operator_type o0 = cov->operation();
  25276. const details::operator_type o1 = operation;
  25277. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  25278. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  25279. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  25280. expression_node_ptr result = error_node();
  25281. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  25282. {
  25283. // (c / v0) / v1 --> (covov) c / (v0 * v1)
  25284. if ((details::e_div == o0) && (details::e_div == o1))
  25285. {
  25286. const bool synthesis_result =
  25287. synthesize_sf3ext_expression::
  25288. template compile<ctype, vtype, vtype>(expr_gen, "t/(t*t)", c, v0, v1, result);
  25289. exprtk_debug(("(c / v0) / v1 --> (covov) c / (v0 * v1)\n"));
  25290. return (synthesis_result) ? result : error_node();
  25291. }
  25292. }
  25293. const bool synthesis_result =
  25294. synthesize_sf3ext_expression::template compile<ctype, vtype, vtype>
  25295. (expr_gen, id(expr_gen, o0, o1), c, v0, v1, result);
  25296. if (synthesis_result)
  25297. return result;
  25298. else if (!expr_gen.valid_operator(o0,f0))
  25299. return error_node();
  25300. else if (!expr_gen.valid_operator(o1,f1))
  25301. return error_node();
  25302. else
  25303. return node_type::allocate(*(expr_gen.node_allocator_), c, v0, v1, f0, f1);
  25304. }
  25305. static inline std::string id(expression_generator<Type>& expr_gen,
  25306. const details::operator_type o0, const details::operator_type o1)
  25307. {
  25308. return details::build_string()
  25309. << "(t" << expr_gen.to_str(o0)
  25310. << "t)" << expr_gen.to_str(o1)
  25311. << "t";
  25312. }
  25313. };
  25314. struct synthesize_covov_expression1
  25315. {
  25316. typedef typename covov_t::type1 node_type;
  25317. typedef typename covov_t::sf3_type sf3_type;
  25318. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  25319. const details::operator_type& operation,
  25320. expression_node_ptr (&branch)[2])
  25321. {
  25322. // (c) o0 (v0 o1 v1)
  25323. const details::vov_base_node<Type>* vov = static_cast<details::vov_base_node<Type>*>(branch[1]);
  25324. const Type c = static_cast<details::literal_node<Type>*>(branch[0])->value();
  25325. const Type& v0 = vov->v0();
  25326. const Type& v1 = vov->v1();
  25327. const details::operator_type o0 = operation;
  25328. const details::operator_type o1 = vov->operation();
  25329. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  25330. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  25331. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  25332. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  25333. expression_node_ptr result = error_node();
  25334. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  25335. {
  25336. // c / (v0 / v1) --> (covov) (c * v1) / v0
  25337. if ((details::e_div == o0) && (details::e_div == o1))
  25338. {
  25339. const bool synthesis_result =
  25340. synthesize_sf3ext_expression::
  25341. template compile<ctype, vtype, vtype>(expr_gen, "(t*t)/t", c, v1, v0, result);
  25342. exprtk_debug(("c / (v0 / v1) --> (covov) (c * v1) / v0\n"));
  25343. return (synthesis_result) ? result : error_node();
  25344. }
  25345. }
  25346. const bool synthesis_result =
  25347. synthesize_sf3ext_expression::template compile<ctype, vtype, vtype>
  25348. (expr_gen, id(expr_gen, o0, o1), c, v0, v1, result);
  25349. if (synthesis_result)
  25350. return result;
  25351. else if (!expr_gen.valid_operator(o0,f0))
  25352. return error_node();
  25353. else if (!expr_gen.valid_operator(o1,f1))
  25354. return error_node();
  25355. else
  25356. return node_type::allocate(*(expr_gen.node_allocator_), c, v0, v1, f0, f1);
  25357. }
  25358. static inline std::string id(expression_generator<Type>& expr_gen, const details::operator_type o0, const details::operator_type o1)
  25359. {
  25360. return details::build_string()
  25361. << "t" << expr_gen.to_str(o0)
  25362. << "(t" << expr_gen.to_str(o1)
  25363. << "t)";
  25364. }
  25365. };
  25366. struct synthesize_covoc_expression0
  25367. {
  25368. typedef typename covoc_t::type0 node_type;
  25369. typedef typename covoc_t::sf3_type sf3_type;
  25370. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  25371. const details::operator_type& operation,
  25372. expression_node_ptr (&branch)[2])
  25373. {
  25374. // (c0 o0 v) o1 (c1)
  25375. const details::cov_base_node<Type>* cov = static_cast<details::cov_base_node<Type>*>(branch[0]);
  25376. const Type c0 = cov->c();
  25377. const Type& v = cov->v();
  25378. const Type c1 = static_cast<details::literal_node<Type>*>(branch[1])->value();
  25379. const details::operator_type o0 = cov->operation();
  25380. const details::operator_type o1 = operation;
  25381. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  25382. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  25383. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  25384. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  25385. expression_node_ptr result = error_node();
  25386. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  25387. {
  25388. // (c0 + v) + c1 --> (cov) (c0 + c1) + v
  25389. if ((details::e_add == o0) && (details::e_add == o1))
  25390. {
  25391. exprtk_debug(("(c0 + v) + c1 --> (cov) (c0 + c1) + v\n"));
  25392. return expr_gen.node_allocator_->
  25393. template allocate_cr<typename details::cov_node<Type,details::add_op<Type> > >(c0 + c1, v);
  25394. }
  25395. // (c0 + v) - c1 --> (cov) (c0 - c1) + v
  25396. else if ((details::e_add == o0) && (details::e_sub == o1))
  25397. {
  25398. exprtk_debug(("(c0 + v) - c1 --> (cov) (c0 - c1) + v\n"));
  25399. return expr_gen.node_allocator_->
  25400. template allocate_cr<typename details::cov_node<Type,details::add_op<Type> > >(c0 - c1, v);
  25401. }
  25402. // (c0 - v) + c1 --> (cov) (c0 + c1) - v
  25403. else if ((details::e_sub == o0) && (details::e_add == o1))
  25404. {
  25405. exprtk_debug(("(c0 - v) + c1 --> (cov) (c0 + c1) - v\n"));
  25406. return expr_gen.node_allocator_->
  25407. template allocate_cr<typename details::cov_node<Type,details::sub_op<Type> > >(c0 + c1, v);
  25408. }
  25409. // (c0 - v) - c1 --> (cov) (c0 - c1) - v
  25410. else if ((details::e_sub == o0) && (details::e_sub == o1))
  25411. {
  25412. exprtk_debug(("(c0 - v) - c1 --> (cov) (c0 - c1) - v\n"));
  25413. return expr_gen.node_allocator_->
  25414. template allocate_cr<typename details::cov_node<Type,details::sub_op<Type> > >(c0 - c1, v);
  25415. }
  25416. // (c0 * v) * c1 --> (cov) (c0 * c1) * v
  25417. else if ((details::e_mul == o0) && (details::e_mul == o1))
  25418. {
  25419. exprtk_debug(("(c0 * v) * c1 --> (cov) (c0 * c1) * v\n"));
  25420. return expr_gen.node_allocator_->
  25421. template allocate_cr<typename details::cov_node<Type,details::mul_op<Type> > >(c0 * c1, v);
  25422. }
  25423. // (c0 * v) / c1 --> (cov) (c0 / c1) * v
  25424. else if ((details::e_mul == o0) && (details::e_div == o1))
  25425. {
  25426. exprtk_debug(("(c0 * v) / c1 --> (cov) (c0 / c1) * v\n"));
  25427. return expr_gen.node_allocator_->
  25428. template allocate_cr<typename details::cov_node<Type,details::mul_op<Type> > >(c0 / c1, v);
  25429. }
  25430. // (c0 / v) * c1 --> (cov) (c0 * c1) / v
  25431. else if ((details::e_div == o0) && (details::e_mul == o1))
  25432. {
  25433. exprtk_debug(("(c0 / v) * c1 --> (cov) (c0 * c1) / v\n"));
  25434. return expr_gen.node_allocator_->
  25435. template allocate_cr<typename details::cov_node<Type,details::div_op<Type> > >(c0 * c1, v);
  25436. }
  25437. // (c0 / v) / c1 --> (cov) (c0 / c1) / v
  25438. else if ((details::e_div == o0) && (details::e_div == o1))
  25439. {
  25440. exprtk_debug(("(c0 / v) / c1 --> (cov) (c0 / c1) / v\n"));
  25441. return expr_gen.node_allocator_->
  25442. template allocate_cr<typename details::cov_node<Type,details::div_op<Type> > >(c0 / c1, v);
  25443. }
  25444. }
  25445. const bool synthesis_result =
  25446. synthesize_sf3ext_expression::template compile<ctype, vtype, ctype>
  25447. (expr_gen, id(expr_gen, o0, o1), c0, v, c1, result);
  25448. if (synthesis_result)
  25449. return result;
  25450. else if (!expr_gen.valid_operator(o0,f0))
  25451. return error_node();
  25452. else if (!expr_gen.valid_operator(o1,f1))
  25453. return error_node();
  25454. else
  25455. return node_type::allocate(*(expr_gen.node_allocator_), c0, v, c1, f0, f1);
  25456. }
  25457. static inline std::string id(expression_generator<Type>& expr_gen,
  25458. const details::operator_type o0, const details::operator_type o1)
  25459. {
  25460. return details::build_string()
  25461. << "(t" << expr_gen.to_str(o0)
  25462. << "t)" << expr_gen.to_str(o1)
  25463. << "t";
  25464. }
  25465. };
  25466. struct synthesize_covoc_expression1
  25467. {
  25468. typedef typename covoc_t::type1 node_type;
  25469. typedef typename covoc_t::sf3_type sf3_type;
  25470. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  25471. const details::operator_type& operation,
  25472. expression_node_ptr (&branch)[2])
  25473. {
  25474. // (c0) o0 (v o1 c1)
  25475. const details::voc_base_node<Type>* voc = static_cast<details::voc_base_node<Type>*>(branch[1]);
  25476. const Type c0 = static_cast<details::literal_node<Type>*>(branch[0])->value();
  25477. const Type& v = voc->v();
  25478. const Type c1 = voc->c();
  25479. const details::operator_type o0 = operation;
  25480. const details::operator_type o1 = voc->operation();
  25481. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  25482. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  25483. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  25484. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  25485. expression_node_ptr result = error_node();
  25486. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  25487. {
  25488. // (c0) + (v + c1) --> (cov) (c0 + c1) + v
  25489. if ((details::e_add == o0) && (details::e_add == o1))
  25490. {
  25491. exprtk_debug(("(c0) + (v + c1) --> (cov) (c0 + c1) + v\n"));
  25492. return expr_gen.node_allocator_->
  25493. template allocate_cr<typename details::cov_node<Type,details::add_op<Type> > >(c0 + c1, v);
  25494. }
  25495. // (c0) + (v - c1) --> (cov) (c0 - c1) + v
  25496. else if ((details::e_add == o0) && (details::e_sub == o1))
  25497. {
  25498. exprtk_debug(("(c0) + (v - c1) --> (cov) (c0 - c1) + v\n"));
  25499. return expr_gen.node_allocator_->
  25500. template allocate_cr<typename details::cov_node<Type,details::add_op<Type> > >(c0 - c1, v);
  25501. }
  25502. // (c0) - (v + c1) --> (cov) (c0 - c1) - v
  25503. else if ((details::e_sub == o0) && (details::e_add == o1))
  25504. {
  25505. exprtk_debug(("(c0) - (v + c1) --> (cov) (c0 - c1) - v\n"));
  25506. return expr_gen.node_allocator_->
  25507. template allocate_cr<typename details::cov_node<Type,details::sub_op<Type> > >(c0 - c1, v);
  25508. }
  25509. // (c0) - (v - c1) --> (cov) (c0 + c1) - v
  25510. else if ((details::e_sub == o0) && (details::e_sub == o1))
  25511. {
  25512. exprtk_debug(("(c0) - (v - c1) --> (cov) (c0 + c1) - v\n"));
  25513. return expr_gen.node_allocator_->
  25514. template allocate_cr<typename details::cov_node<Type,details::sub_op<Type> > >(c0 + c1, v);
  25515. }
  25516. // (c0) * (v * c1) --> (voc) v * (c0 * c1)
  25517. else if ((details::e_mul == o0) && (details::e_mul == o1))
  25518. {
  25519. exprtk_debug(("(c0) * (v * c1) --> (voc) v * (c0 * c1)\n"));
  25520. return expr_gen.node_allocator_->
  25521. template allocate_cr<typename details::cov_node<Type,details::mul_op<Type> > >(c0 * c1, v);
  25522. }
  25523. // (c0) * (v / c1) --> (cov) (c0 / c1) * v
  25524. else if ((details::e_mul == o0) && (details::e_div == o1))
  25525. {
  25526. exprtk_debug(("(c0) * (v / c1) --> (cov) (c0 / c1) * v\n"));
  25527. return expr_gen.node_allocator_->
  25528. template allocate_cr<typename details::cov_node<Type,details::mul_op<Type> > >(c0 / c1, v);
  25529. }
  25530. // (c0) / (v * c1) --> (cov) (c0 / c1) / v
  25531. else if ((details::e_div == o0) && (details::e_mul == o1))
  25532. {
  25533. exprtk_debug(("(c0) / (v * c1) --> (cov) (c0 / c1) / v\n"));
  25534. return expr_gen.node_allocator_->
  25535. template allocate_cr<typename details::cov_node<Type,details::div_op<Type> > >(c0 / c1, v);
  25536. }
  25537. // (c0) / (v / c1) --> (cov) (c0 * c1) / v
  25538. else if ((details::e_div == o0) && (details::e_div == o1))
  25539. {
  25540. exprtk_debug(("(c0) / (v / c1) --> (cov) (c0 * c1) / v\n"));
  25541. return expr_gen.node_allocator_->
  25542. template allocate_cr<typename details::cov_node<Type,details::div_op<Type> > >(c0 * c1, v);
  25543. }
  25544. }
  25545. const bool synthesis_result =
  25546. synthesize_sf3ext_expression::template compile<ctype, vtype, ctype>
  25547. (expr_gen, id(expr_gen, o0, o1), c0, v, c1, result);
  25548. if (synthesis_result)
  25549. return result;
  25550. else if (!expr_gen.valid_operator(o0,f0))
  25551. return error_node();
  25552. else if (!expr_gen.valid_operator(o1,f1))
  25553. return error_node();
  25554. else
  25555. return node_type::allocate(*(expr_gen.node_allocator_), c0, v, c1, f0, f1);
  25556. }
  25557. static inline std::string id(expression_generator<Type>& expr_gen,
  25558. const details::operator_type o0, const details::operator_type o1)
  25559. {
  25560. return details::build_string()
  25561. << "t" << expr_gen.to_str(o0)
  25562. << "(t" << expr_gen.to_str(o1)
  25563. << "t)";
  25564. }
  25565. };
  25566. struct synthesize_cocov_expression0
  25567. {
  25568. typedef typename cocov_t::type0 node_type;
  25569. static inline expression_node_ptr process(expression_generator<Type>&, const details::operator_type&, expression_node_ptr (&)[2])
  25570. {
  25571. // (c0 o0 c1) o1 (v) - Not possible.
  25572. return error_node();
  25573. }
  25574. };
  25575. struct synthesize_cocov_expression1
  25576. {
  25577. typedef typename cocov_t::type1 node_type;
  25578. typedef typename cocov_t::sf3_type sf3_type;
  25579. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  25580. const details::operator_type& operation,
  25581. expression_node_ptr (&branch)[2])
  25582. {
  25583. // (c0) o0 (c1 o1 v)
  25584. const details::cov_base_node<Type>* cov = static_cast<details::cov_base_node<Type>*>(branch[1]);
  25585. const Type c0 = static_cast<details::literal_node<Type>*>(branch[0])->value();
  25586. const Type c1 = cov->c();
  25587. const Type& v = cov->v();
  25588. const details::operator_type o0 = operation;
  25589. const details::operator_type o1 = cov->operation();
  25590. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  25591. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  25592. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  25593. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  25594. expression_node_ptr result = error_node();
  25595. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  25596. {
  25597. // (c0) + (c1 + v) --> (cov) (c0 + c1) + v
  25598. if ((details::e_add == o0) && (details::e_add == o1))
  25599. {
  25600. exprtk_debug(("(c0) + (c1 + v) --> (cov) (c0 + c1) + v\n"));
  25601. return expr_gen.node_allocator_->
  25602. template allocate_cr<typename details::cov_node<Type,details::add_op<Type> > >(c0 + c1, v);
  25603. }
  25604. // (c0) + (c1 - v) --> (cov) (c0 + c1) - v
  25605. else if ((details::e_add == o0) && (details::e_sub == o1))
  25606. {
  25607. exprtk_debug(("(c0) + (c1 - v) --> (cov) (c0 + c1) - v\n"));
  25608. return expr_gen.node_allocator_->
  25609. template allocate_cr<typename details::cov_node<Type,details::sub_op<Type> > >(c0 + c1, v);
  25610. }
  25611. // (c0) - (c1 + v) --> (cov) (c0 - c1) - v
  25612. else if ((details::e_sub == o0) && (details::e_add == o1))
  25613. {
  25614. exprtk_debug(("(c0) - (c1 + v) --> (cov) (c0 - c1) - v\n"));
  25615. return expr_gen.node_allocator_->
  25616. template allocate_cr<typename details::cov_node<Type,details::sub_op<Type> > >(c0 - c1, v);
  25617. }
  25618. // (c0) - (c1 - v) --> (cov) (c0 - c1) + v
  25619. else if ((details::e_sub == o0) && (details::e_sub == o1))
  25620. {
  25621. exprtk_debug(("(c0) - (c1 - v) --> (cov) (c0 - c1) + v\n"));
  25622. return expr_gen.node_allocator_->
  25623. template allocate_cr<typename details::cov_node<Type,details::add_op<Type> > >(c0 - c1, v);
  25624. }
  25625. // (c0) * (c1 * v) --> (cov) (c0 * c1) * v
  25626. else if ((details::e_mul == o0) && (details::e_mul == o1))
  25627. {
  25628. exprtk_debug(("(c0) * (c1 * v) --> (cov) (c0 * c1) * v\n"));
  25629. return expr_gen.node_allocator_->
  25630. template allocate_cr<typename details::cov_node<Type,details::mul_op<Type> > >(c0 * c1, v);
  25631. }
  25632. // (c0) * (c1 / v) --> (cov) (c0 * c1) / v
  25633. else if ((details::e_mul == o0) && (details::e_div == o1))
  25634. {
  25635. exprtk_debug(("(c0) * (c1 / v) --> (cov) (c0 * c1) / v\n"));
  25636. return expr_gen.node_allocator_->
  25637. template allocate_cr<typename details::cov_node<Type,details::div_op<Type> > >(c0 * c1, v);
  25638. }
  25639. // (c0) / (c1 * v) --> (cov) (c0 / c1) / v
  25640. else if ((details::e_div == o0) && (details::e_mul == o1))
  25641. {
  25642. exprtk_debug(("(c0) / (c1 * v) --> (cov) (c0 / c1) / v\n"));
  25643. return expr_gen.node_allocator_->
  25644. template allocate_cr<typename details::cov_node<Type,details::div_op<Type> > >(c0 / c1, v);
  25645. }
  25646. // (c0) / (c1 / v) --> (cov) (c0 / c1) * v
  25647. else if ((details::e_div == o0) && (details::e_div == o1))
  25648. {
  25649. exprtk_debug(("(c0) / (c1 / v) --> (cov) (c0 / c1) * v\n"));
  25650. return expr_gen.node_allocator_->
  25651. template allocate_cr<typename details::cov_node<Type,details::mul_op<Type> > >(c0 / c1, v);
  25652. }
  25653. }
  25654. const bool synthesis_result =
  25655. synthesize_sf3ext_expression::template compile<ctype, ctype, vtype>
  25656. (expr_gen, id(expr_gen, o0, o1), c0, c1, v, result);
  25657. if (synthesis_result)
  25658. return result;
  25659. else if (!expr_gen.valid_operator(o0,f0))
  25660. return error_node();
  25661. else if (!expr_gen.valid_operator(o1,f1))
  25662. return error_node();
  25663. else
  25664. return node_type::allocate(*(expr_gen.node_allocator_), c0, c1, v, f0, f1);
  25665. }
  25666. static inline std::string id(expression_generator<Type>& expr_gen, const details::operator_type o0, const details::operator_type o1)
  25667. {
  25668. return details::build_string()
  25669. << "t" << expr_gen.to_str(o0)
  25670. << "(t" << expr_gen.to_str(o1)
  25671. << "t)";
  25672. }
  25673. };
  25674. struct synthesize_vococ_expression0
  25675. {
  25676. typedef typename vococ_t::type0 node_type;
  25677. typedef typename vococ_t::sf3_type sf3_type;
  25678. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  25679. const details::operator_type& operation,
  25680. expression_node_ptr (&branch)[2])
  25681. {
  25682. // (v o0 c0) o1 (c1)
  25683. const details::voc_base_node<Type>* voc = static_cast<details::voc_base_node<Type>*>(branch[0]);
  25684. const Type& v = voc->v();
  25685. const Type& c0 = voc->c();
  25686. const Type& c1 = static_cast<details::literal_node<Type>*>(branch[1])->value();
  25687. const details::operator_type o0 = voc->operation();
  25688. const details::operator_type o1 = operation;
  25689. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  25690. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  25691. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  25692. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  25693. expression_node_ptr result = error_node();
  25694. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  25695. {
  25696. // (v + c0) + c1 --> (voc) v + (c0 + c1)
  25697. if ((details::e_add == o0) && (details::e_add == o1))
  25698. {
  25699. exprtk_debug(("(v + c0) + c1 --> (voc) v + (c0 + c1)\n"));
  25700. return expr_gen.node_allocator_->
  25701. template allocate_rc<typename details::voc_node<Type,details::add_op<Type> > >(v, c0 + c1);
  25702. }
  25703. // (v + c0) - c1 --> (voc) v + (c0 - c1)
  25704. else if ((details::e_add == o0) && (details::e_sub == o1))
  25705. {
  25706. exprtk_debug(("(v + c0) - c1 --> (voc) v + (c0 - c1)\n"));
  25707. return expr_gen.node_allocator_->
  25708. template allocate_rc<typename details::voc_node<Type,details::add_op<Type> > >(v, c0 - c1);
  25709. }
  25710. // (v - c0) + c1 --> (voc) v - (c0 + c1)
  25711. else if ((details::e_sub == o0) && (details::e_add == o1))
  25712. {
  25713. exprtk_debug(("(v - c0) + c1 --> (voc) v - (c0 + c1)\n"));
  25714. return expr_gen.node_allocator_->
  25715. template allocate_rc<typename details::voc_node<Type,details::add_op<Type> > >(v, c1 - c0);
  25716. }
  25717. // (v - c0) - c1 --> (voc) v - (c0 + c1)
  25718. else if ((details::e_sub == o0) && (details::e_sub == o1))
  25719. {
  25720. exprtk_debug(("(v - c0) - c1 --> (voc) v - (c0 + c1)\n"));
  25721. return expr_gen.node_allocator_->
  25722. template allocate_rc<typename details::voc_node<Type,details::sub_op<Type> > >(v, c0 + c1);
  25723. }
  25724. // (v * c0) * c1 --> (voc) v * (c0 * c1)
  25725. else if ((details::e_mul == o0) && (details::e_mul == o1))
  25726. {
  25727. exprtk_debug(("(v * c0) * c1 --> (voc) v * (c0 * c1)\n"));
  25728. return expr_gen.node_allocator_->
  25729. template allocate_rc<typename details::voc_node<Type,details::mul_op<Type> > >(v, c0 * c1);
  25730. }
  25731. // (v * c0) / c1 --> (voc) v * (c0 / c1)
  25732. else if ((details::e_mul == o0) && (details::e_div == o1))
  25733. {
  25734. exprtk_debug(("(v * c0) / c1 --> (voc) v * (c0 / c1)\n"));
  25735. return expr_gen.node_allocator_->
  25736. template allocate_rc<typename details::voc_node<Type,details::mul_op<Type> > >(v, c0 / c1);
  25737. }
  25738. // (v / c0) * c1 --> (voc) v * (c1 / c0)
  25739. else if ((details::e_div == o0) && (details::e_mul == o1))
  25740. {
  25741. exprtk_debug(("(v / c0) * c1 --> (voc) v * (c1 / c0)\n"));
  25742. return expr_gen.node_allocator_->
  25743. template allocate_rc<typename details::voc_node<Type,details::mul_op<Type> > >(v, c1 / c0);
  25744. }
  25745. // (v / c0) / c1 --> (voc) v / (c0 * c1)
  25746. else if ((details::e_div == o0) && (details::e_div == o1))
  25747. {
  25748. exprtk_debug(("(v / c0) / c1 --> (voc) v / (c0 * c1)\n"));
  25749. return expr_gen.node_allocator_->
  25750. template allocate_rc<typename details::voc_node<Type,details::div_op<Type> > >(v, c0 * c1);
  25751. }
  25752. // (v ^ c0) ^ c1 --> (voc) v ^ (c0 * c1)
  25753. else if ((details::e_pow == o0) && (details::e_pow == o1))
  25754. {
  25755. exprtk_debug(("(v ^ c0) ^ c1 --> (voc) v ^ (c0 * c1)\n"));
  25756. return expr_gen.node_allocator_->
  25757. template allocate_rc<typename details::voc_node<Type,details::pow_op<Type> > >(v, c0 * c1);
  25758. }
  25759. }
  25760. const bool synthesis_result =
  25761. synthesize_sf3ext_expression::template compile<vtype, ctype, ctype>
  25762. (expr_gen, id(expr_gen, o0, o1), v, c0, c1, result);
  25763. if (synthesis_result)
  25764. return result;
  25765. else if (!expr_gen.valid_operator(o0,f0))
  25766. return error_node();
  25767. else if (!expr_gen.valid_operator(o1,f1))
  25768. return error_node();
  25769. else
  25770. return node_type::allocate(*(expr_gen.node_allocator_), v, c0, c1, f0, f1);
  25771. }
  25772. static inline std::string id(expression_generator<Type>& expr_gen,
  25773. const details::operator_type o0, const details::operator_type o1)
  25774. {
  25775. return details::build_string()
  25776. << "(t" << expr_gen.to_str(o0)
  25777. << "t)" << expr_gen.to_str(o1)
  25778. << "t";
  25779. }
  25780. };
  25781. struct synthesize_vococ_expression1
  25782. {
  25783. typedef typename vococ_t::type0 node_type;
  25784. static inline expression_node_ptr process(expression_generator<Type>&, const details::operator_type&, expression_node_ptr (&)[2])
  25785. {
  25786. // (v) o0 (c0 o1 c1) - Not possible.
  25787. exprtk_debug(("(v) o0 (c0 o1 c1) - Not possible.\n"));
  25788. return error_node();
  25789. }
  25790. };
  25791. struct synthesize_vovovov_expression0
  25792. {
  25793. typedef typename vovovov_t::type0 node_type;
  25794. typedef typename vovovov_t::sf4_type sf4_type;
  25795. typedef typename node_type::T0 T0;
  25796. typedef typename node_type::T1 T1;
  25797. typedef typename node_type::T2 T2;
  25798. typedef typename node_type::T3 T3;
  25799. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  25800. const details::operator_type& operation,
  25801. expression_node_ptr (&branch)[2])
  25802. {
  25803. // (v0 o0 v1) o1 (v2 o2 v3)
  25804. const details::vov_base_node<Type>* vov0 = static_cast<details::vov_base_node<Type>*>(branch[0]);
  25805. const details::vov_base_node<Type>* vov1 = static_cast<details::vov_base_node<Type>*>(branch[1]);
  25806. const Type& v0 = vov0->v0();
  25807. const Type& v1 = vov0->v1();
  25808. const Type& v2 = vov1->v0();
  25809. const Type& v3 = vov1->v1();
  25810. const details::operator_type o0 = vov0->operation();
  25811. const details::operator_type o1 = operation;
  25812. const details::operator_type o2 = vov1->operation();
  25813. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  25814. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  25815. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  25816. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  25817. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  25818. expression_node_ptr result = error_node();
  25819. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  25820. {
  25821. // (v0 / v1) * (v2 / v3) --> (vovovov) (v0 * v2) / (v1 * v3)
  25822. if ((details::e_div == o0) && (details::e_mul == o1) && (details::e_div == o2))
  25823. {
  25824. const bool synthesis_result =
  25825. synthesize_sf4ext_expression::
  25826. template compile<vtype,vtype,vtype,vtype>(expr_gen, "(t*t)/(t*t)", v0, v2, v1, v3, result);
  25827. exprtk_debug(("(v0 / v1) * (v2 / v3) --> (vovovov) (v0 * v2) / (v1 * v3)\n"));
  25828. return (synthesis_result) ? result : error_node();
  25829. }
  25830. // (v0 / v1) / (v2 / v3) --> (vovovov) (v0 * v3) / (v1 * v2)
  25831. else if ((details::e_div == o0) && (details::e_div == o1) && (details::e_div == o2))
  25832. {
  25833. const bool synthesis_result =
  25834. synthesize_sf4ext_expression::
  25835. template compile<vtype,vtype,vtype,vtype>(expr_gen, "(t*t)/(t*t)", v0, v3, v1, v2, result);
  25836. exprtk_debug(("(v0 / v1) / (v2 / v3) --> (vovovov) (v0 * v3) / (v1 * v2)\n"));
  25837. return (synthesis_result) ? result : error_node();
  25838. }
  25839. // (v0 + v1) / (v2 / v3) --> (vovovov) (v0 + v1) * (v3 / v2)
  25840. else if ((details::e_add == o0) && (details::e_div == o1) && (details::e_div == o2))
  25841. {
  25842. const bool synthesis_result =
  25843. synthesize_sf4ext_expression::
  25844. template compile<vtype,vtype,vtype,vtype>(expr_gen, "(t+t)*(t/t)", v0, v1, v3, v2, result);
  25845. exprtk_debug(("(v0 + v1) / (v2 / v3) --> (vovovov) (v0 + v1) * (v3 / v2)\n"));
  25846. return (synthesis_result) ? result : error_node();
  25847. }
  25848. // (v0 - v1) / (v2 / v3) --> (vovovov) (v0 + v1) * (v3 / v2)
  25849. else if ((details::e_sub == o0) && (details::e_div == o1) && (details::e_div == o2))
  25850. {
  25851. const bool synthesis_result =
  25852. synthesize_sf4ext_expression::
  25853. template compile<vtype,vtype,vtype,vtype>(expr_gen, "(t-t)*(t/t)", v0, v1, v3, v2, result);
  25854. exprtk_debug(("(v0 - v1) / (v2 / v3) --> (vovovov) (v0 - v1) * (v3 / v2)\n"));
  25855. return (synthesis_result) ? result : error_node();
  25856. }
  25857. // (v0 * v1) / (v2 / v3) --> (vovovov) ((v0 * v1) * v3) / v2
  25858. else if ((details::e_mul == o0) && (details::e_div == o1) && (details::e_div == o2))
  25859. {
  25860. const bool synthesis_result =
  25861. synthesize_sf4ext_expression::
  25862. template compile<vtype,vtype,vtype,vtype>(expr_gen, "((t*t)*t)/t", v0, v1, v3, v2, result);
  25863. exprtk_debug(("(v0 * v1) / (v2 / v3) --> (vovovov) ((v0 * v1) * v3) / v2\n"));
  25864. return (synthesis_result) ? result : error_node();
  25865. }
  25866. }
  25867. const bool synthesis_result =
  25868. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  25869. (expr_gen, id(expr_gen, o0, o1, o2), v0, v1, v2, v3, result);
  25870. if (synthesis_result)
  25871. return result;
  25872. else if (!expr_gen.valid_operator(o0,f0))
  25873. return error_node();
  25874. else if (!expr_gen.valid_operator(o1,f1))
  25875. return error_node();
  25876. else if (!expr_gen.valid_operator(o2,f2))
  25877. return error_node();
  25878. else
  25879. return node_type::allocate(*(expr_gen.node_allocator_), v0, v1, v2, v3, f0, f1, f2);
  25880. }
  25881. static inline std::string id(expression_generator<Type>& expr_gen,
  25882. const details::operator_type o0,
  25883. const details::operator_type o1,
  25884. const details::operator_type o2)
  25885. {
  25886. return details::build_string()
  25887. << "(t" << expr_gen.to_str(o0)
  25888. << "t)" << expr_gen.to_str(o1)
  25889. << "(t" << expr_gen.to_str(o2)
  25890. << "t)";
  25891. }
  25892. };
  25893. struct synthesize_vovovoc_expression0
  25894. {
  25895. typedef typename vovovoc_t::type0 node_type;
  25896. typedef typename vovovoc_t::sf4_type sf4_type;
  25897. typedef typename node_type::T0 T0;
  25898. typedef typename node_type::T1 T1;
  25899. typedef typename node_type::T2 T2;
  25900. typedef typename node_type::T3 T3;
  25901. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  25902. const details::operator_type& operation,
  25903. expression_node_ptr (&branch)[2])
  25904. {
  25905. // (v0 o0 v1) o1 (v2 o2 c)
  25906. const details::vov_base_node<Type>* vov = static_cast<details::vov_base_node<Type>*>(branch[0]);
  25907. const details::voc_base_node<Type>* voc = static_cast<details::voc_base_node<Type>*>(branch[1]);
  25908. const Type& v0 = vov->v0();
  25909. const Type& v1 = vov->v1();
  25910. const Type& v2 = voc->v ();
  25911. const Type c = voc->c ();
  25912. const details::operator_type o0 = vov->operation();
  25913. const details::operator_type o1 = operation;
  25914. const details::operator_type o2 = voc->operation();
  25915. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  25916. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  25917. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  25918. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  25919. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  25920. expression_node_ptr result = error_node();
  25921. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  25922. {
  25923. // (v0 / v1) * (v2 / c) --> (vovovoc) (v0 * v2) / (v1 * c)
  25924. if ((details::e_div == o0) && (details::e_mul == o1) && (details::e_div == o2))
  25925. {
  25926. const bool synthesis_result =
  25927. synthesize_sf4ext_expression::
  25928. template compile<vtype,vtype,vtype,ctype>(expr_gen, "(t*t)/(t*t)", v0, v2, v1, c, result);
  25929. exprtk_debug(("(v0 / v1) * (v2 / c) --> (vovovoc) (v0 * v2) / (v1 * c)\n"));
  25930. return (synthesis_result) ? result : error_node();
  25931. }
  25932. // (v0 / v1) / (v2 / c) --> (vocovov) (v0 * c) / (v1 * v2)
  25933. if ((details::e_div == o0) && (details::e_div == o1) && (details::e_div == o2))
  25934. {
  25935. const bool synthesis_result =
  25936. synthesize_sf4ext_expression::
  25937. template compile<vtype,ctype,vtype,vtype>(expr_gen, "(t*t)/(t*t)", v0, c, v1, v2, result);
  25938. exprtk_debug(("(v0 / v1) / (v2 / c) --> (vocovov) (v0 * c) / (v1 * v2)\n"));
  25939. return (synthesis_result) ? result : error_node();
  25940. }
  25941. }
  25942. const bool synthesis_result =
  25943. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  25944. (expr_gen, id(expr_gen, o0, o1, o2), v0, v1, v2, c, result);
  25945. if (synthesis_result)
  25946. return result;
  25947. else if (!expr_gen.valid_operator(o0,f0))
  25948. return error_node();
  25949. else if (!expr_gen.valid_operator(o1,f1))
  25950. return error_node();
  25951. else if (!expr_gen.valid_operator(o2,f2))
  25952. return error_node();
  25953. else
  25954. return node_type::allocate(*(expr_gen.node_allocator_), v0, v1, v2, c, f0, f1, f2);
  25955. }
  25956. static inline std::string id(expression_generator<Type>& expr_gen,
  25957. const details::operator_type o0,
  25958. const details::operator_type o1,
  25959. const details::operator_type o2)
  25960. {
  25961. return details::build_string()
  25962. << "(t" << expr_gen.to_str(o0)
  25963. << "t)" << expr_gen.to_str(o1)
  25964. << "(t" << expr_gen.to_str(o2)
  25965. << "t)";
  25966. }
  25967. };
  25968. struct synthesize_vovocov_expression0
  25969. {
  25970. typedef typename vovocov_t::type0 node_type;
  25971. typedef typename vovocov_t::sf4_type sf4_type;
  25972. typedef typename node_type::T0 T0;
  25973. typedef typename node_type::T1 T1;
  25974. typedef typename node_type::T2 T2;
  25975. typedef typename node_type::T3 T3;
  25976. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  25977. const details::operator_type& operation,
  25978. expression_node_ptr (&branch)[2])
  25979. {
  25980. // (v0 o0 v1) o1 (c o2 v2)
  25981. const details::vov_base_node<Type>* vov = static_cast<details::vov_base_node<Type>*>(branch[0]);
  25982. const details::cov_base_node<Type>* cov = static_cast<details::cov_base_node<Type>*>(branch[1]);
  25983. const Type& v0 = vov->v0();
  25984. const Type& v1 = vov->v1();
  25985. const Type& v2 = cov->v ();
  25986. const Type c = cov->c ();
  25987. const details::operator_type o0 = vov->operation();
  25988. const details::operator_type o1 = operation;
  25989. const details::operator_type o2 = cov->operation();
  25990. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  25991. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  25992. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  25993. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  25994. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  25995. expression_node_ptr result = error_node();
  25996. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  25997. {
  25998. // (v0 / v1) * (c / v2) --> (vocovov) (v0 * c) / (v1 * v2)
  25999. if ((details::e_div == o0) && (details::e_mul == o1) && (details::e_div == o2))
  26000. {
  26001. const bool synthesis_result =
  26002. synthesize_sf4ext_expression::
  26003. template compile<vtype,ctype,vtype,vtype>(expr_gen, "(t*t)/(t*t)", v0, c, v1, v2, result);
  26004. exprtk_debug(("(v0 / v1) * (c / v2) --> (vocovov) (v0 * c) / (v1 * v2)\n"));
  26005. return (synthesis_result) ? result : error_node();
  26006. }
  26007. // (v0 / v1) / (c / v2) --> (vovovoc) (v0 * v2) / (v1 * c)
  26008. if ((details::e_div == o0) && (details::e_div == o1) && (details::e_div == o2))
  26009. {
  26010. const bool synthesis_result =
  26011. synthesize_sf4ext_expression::
  26012. template compile<vtype,vtype,vtype,ctype>(expr_gen, "(t*t)/(t*t)", v0, v2, v1, c, result);
  26013. exprtk_debug(("(v0 / v1) / (c / v2) --> (vovovoc) (v0 * v2) / (v1 * c)\n"));
  26014. return (synthesis_result) ? result : error_node();
  26015. }
  26016. }
  26017. const bool synthesis_result =
  26018. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  26019. (expr_gen, id(expr_gen, o0, o1, o2), v0, v1, c, v2, result);
  26020. if (synthesis_result)
  26021. return result;
  26022. else if (!expr_gen.valid_operator(o0,f0))
  26023. return error_node();
  26024. else if (!expr_gen.valid_operator(o1,f1))
  26025. return error_node();
  26026. else if (!expr_gen.valid_operator(o2,f2))
  26027. return error_node();
  26028. else
  26029. return node_type::allocate(*(expr_gen.node_allocator_), v0, v1, c, v2, f0, f1, f2);
  26030. }
  26031. static inline std::string id(expression_generator<Type>& expr_gen,
  26032. const details::operator_type o0,
  26033. const details::operator_type o1,
  26034. const details::operator_type o2)
  26035. {
  26036. return details::build_string()
  26037. << "(t" << expr_gen.to_str(o0)
  26038. << "t)" << expr_gen.to_str(o1)
  26039. << "(t" << expr_gen.to_str(o2)
  26040. << "t)";
  26041. }
  26042. };
  26043. struct synthesize_vocovov_expression0
  26044. {
  26045. typedef typename vocovov_t::type0 node_type;
  26046. typedef typename vocovov_t::sf4_type sf4_type;
  26047. typedef typename node_type::T0 T0;
  26048. typedef typename node_type::T1 T1;
  26049. typedef typename node_type::T2 T2;
  26050. typedef typename node_type::T3 T3;
  26051. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  26052. const details::operator_type& operation,
  26053. expression_node_ptr (&branch)[2])
  26054. {
  26055. // (v0 o0 c) o1 (v1 o2 v2)
  26056. const details::voc_base_node<Type>* voc = static_cast<details::voc_base_node<Type>*>(branch[0]);
  26057. const details::vov_base_node<Type>* vov = static_cast<details::vov_base_node<Type>*>(branch[1]);
  26058. const Type c = voc->c ();
  26059. const Type& v0 = voc->v ();
  26060. const Type& v1 = vov->v0();
  26061. const Type& v2 = vov->v1();
  26062. const details::operator_type o0 = voc->operation();
  26063. const details::operator_type o1 = operation;
  26064. const details::operator_type o2 = vov->operation();
  26065. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  26066. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  26067. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  26068. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  26069. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  26070. expression_node_ptr result = error_node();
  26071. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  26072. {
  26073. // (v0 / c) * (v1 / v2) --> (vovocov) (v0 * v1) / (c * v2)
  26074. if ((details::e_div == o0) && (details::e_mul == o1) && (details::e_div == o2))
  26075. {
  26076. const bool synthesis_result =
  26077. synthesize_sf4ext_expression::
  26078. template compile<vtype,vtype,ctype,vtype>(expr_gen, "(t*t)/(t*t)", v0, v1, c, v2, result);
  26079. exprtk_debug(("(v0 / c) * (v1 / v2) --> (vovocov) (v0 * v1) / (c * v2)\n"));
  26080. return (synthesis_result) ? result : error_node();
  26081. }
  26082. // (v0 / c) / (v1 / v2) --> (vovocov) (v0 * v2) / (c * v1)
  26083. if ((details::e_div == o0) && (details::e_div == o1) && (details::e_div == o2))
  26084. {
  26085. const bool synthesis_result =
  26086. synthesize_sf4ext_expression::
  26087. template compile<vtype,vtype,ctype,vtype>(expr_gen, "(t*t)/(t*t)", v0, v2, c, v1, result);
  26088. exprtk_debug(("(v0 / c) / (v1 / v2) --> (vovocov) (v0 * v2) / (c * v1)\n"));
  26089. return (synthesis_result) ? result : error_node();
  26090. }
  26091. }
  26092. const bool synthesis_result =
  26093. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  26094. (expr_gen, id(expr_gen, o0, o1, o2), v0, c, v1, v2, result);
  26095. if (synthesis_result)
  26096. return result;
  26097. else if (!expr_gen.valid_operator(o0,f0))
  26098. return error_node();
  26099. else if (!expr_gen.valid_operator(o1,f1))
  26100. return error_node();
  26101. else if (!expr_gen.valid_operator(o2,f2))
  26102. return error_node();
  26103. else
  26104. return node_type::allocate(*(expr_gen.node_allocator_), v0, c, v1, v2, f0, f1, f2);
  26105. }
  26106. static inline std::string id(expression_generator<Type>& expr_gen,
  26107. const details::operator_type o0,
  26108. const details::operator_type o1,
  26109. const details::operator_type o2)
  26110. {
  26111. return details::build_string()
  26112. << "(t" << expr_gen.to_str(o0)
  26113. << "t)" << expr_gen.to_str(o1)
  26114. << "(t" << expr_gen.to_str(o2)
  26115. << "t)";
  26116. }
  26117. };
  26118. struct synthesize_covovov_expression0
  26119. {
  26120. typedef typename covovov_t::type0 node_type;
  26121. typedef typename covovov_t::sf4_type sf4_type;
  26122. typedef typename node_type::T0 T0;
  26123. typedef typename node_type::T1 T1;
  26124. typedef typename node_type::T2 T2;
  26125. typedef typename node_type::T3 T3;
  26126. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  26127. const details::operator_type& operation,
  26128. expression_node_ptr (&branch)[2])
  26129. {
  26130. // (c o0 v0) o1 (v1 o2 v2)
  26131. const details::cov_base_node<Type>* cov = static_cast<details::cov_base_node<Type>*>(branch[0]);
  26132. const details::vov_base_node<Type>* vov = static_cast<details::vov_base_node<Type>*>(branch[1]);
  26133. const Type c = cov->c ();
  26134. const Type& v0 = cov->v ();
  26135. const Type& v1 = vov->v0();
  26136. const Type& v2 = vov->v1();
  26137. const details::operator_type o0 = cov->operation();
  26138. const details::operator_type o1 = operation;
  26139. const details::operator_type o2 = vov->operation();
  26140. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  26141. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  26142. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  26143. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  26144. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  26145. expression_node_ptr result = error_node();
  26146. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  26147. {
  26148. // (c / v0) * (v1 / v2) --> (covovov) (c * v1) / (v0 * v2)
  26149. if ((details::e_div == o0) && (details::e_mul == o1) && (details::e_div == o2))
  26150. {
  26151. const bool synthesis_result =
  26152. synthesize_sf4ext_expression::
  26153. template compile<ctype,vtype,vtype,vtype>(expr_gen, "(t*t)/(t*t)", c, v1, v0, v2, result);
  26154. exprtk_debug(("(c / v0) * (v1 / v2) --> (covovov) (c * v1) / (v0 * v2)\n"));
  26155. return (synthesis_result) ? result : error_node();
  26156. }
  26157. // (c / v0) / (v1 / v2) --> (covovov) (c * v2) / (v0 * v1)
  26158. if ((details::e_div == o0) && (details::e_div == o1) && (details::e_div == o2))
  26159. {
  26160. const bool synthesis_result =
  26161. synthesize_sf4ext_expression::
  26162. template compile<ctype,vtype,vtype,vtype>(expr_gen, "(t*t)/(t*t)", c, v2, v0, v1, result);
  26163. exprtk_debug(("(c / v0) / (v1 / v2) --> (covovov) (c * v2) / (v0 * v1)\n"));
  26164. return (synthesis_result) ? result : error_node();
  26165. }
  26166. }
  26167. const bool synthesis_result =
  26168. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  26169. (expr_gen, id(expr_gen, o0, o1, o2), c, v0, v1, v2, result);
  26170. if (synthesis_result)
  26171. return result;
  26172. else if (!expr_gen.valid_operator(o0,f0))
  26173. return error_node();
  26174. else if (!expr_gen.valid_operator(o1,f1))
  26175. return error_node();
  26176. else if (!expr_gen.valid_operator(o2,f2))
  26177. return error_node();
  26178. else
  26179. return node_type::allocate(*(expr_gen.node_allocator_), c, v0, v1, v2, f0, f1, f2);
  26180. }
  26181. static inline std::string id(expression_generator<Type>& expr_gen,
  26182. const details::operator_type o0,
  26183. const details::operator_type o1,
  26184. const details::operator_type o2)
  26185. {
  26186. return details::build_string()
  26187. << "(t" << expr_gen.to_str(o0)
  26188. << "t)" << expr_gen.to_str(o1)
  26189. << "(t" << expr_gen.to_str(o2)
  26190. << "t)";
  26191. }
  26192. };
  26193. struct synthesize_covocov_expression0
  26194. {
  26195. typedef typename covocov_t::type0 node_type;
  26196. typedef typename covocov_t::sf4_type sf4_type;
  26197. typedef typename node_type::T0 T0;
  26198. typedef typename node_type::T1 T1;
  26199. typedef typename node_type::T2 T2;
  26200. typedef typename node_type::T3 T3;
  26201. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  26202. const details::operator_type& operation,
  26203. expression_node_ptr (&branch)[2])
  26204. {
  26205. // (c0 o0 v0) o1 (c1 o2 v1)
  26206. const details::cov_base_node<Type>* cov0 = static_cast<details::cov_base_node<Type>*>(branch[0]);
  26207. const details::cov_base_node<Type>* cov1 = static_cast<details::cov_base_node<Type>*>(branch[1]);
  26208. const Type c0 = cov0->c();
  26209. const Type& v0 = cov0->v();
  26210. const Type c1 = cov1->c();
  26211. const Type& v1 = cov1->v();
  26212. const details::operator_type o0 = cov0->operation();
  26213. const details::operator_type o1 = operation;
  26214. const details::operator_type o2 = cov1->operation();
  26215. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  26216. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  26217. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  26218. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  26219. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  26220. expression_node_ptr result = error_node();
  26221. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  26222. {
  26223. // (c0 + v0) + (c1 + v1) --> (covov) (c0 + c1) + v0 + v1
  26224. if ((details::e_add == o0) && (details::e_add == o1) && (details::e_add == o2))
  26225. {
  26226. const bool synthesis_result =
  26227. synthesize_sf3ext_expression::
  26228. template compile<ctype,vtype,vtype>(expr_gen, "(t+t)+t", (c0 + c1), v0, v1, result);
  26229. exprtk_debug(("(c0 + v0) + (c1 + v1) --> (covov) (c0 + c1) + v0 + v1\n"));
  26230. return (synthesis_result) ? result : error_node();
  26231. }
  26232. // (c0 + v0) - (c1 + v1) --> (covov) (c0 - c1) + v0 - v1
  26233. else if ((details::e_add == o0) && (details::e_sub == o1) && (details::e_add == o2))
  26234. {
  26235. const bool synthesis_result =
  26236. synthesize_sf3ext_expression::
  26237. template compile<ctype,vtype,vtype>(expr_gen, "(t+t)-t", (c0 - c1), v0, v1, result);
  26238. exprtk_debug(("(c0 + v0) - (c1 + v1) --> (covov) (c0 - c1) + v0 - v1\n"));
  26239. return (synthesis_result) ? result : error_node();
  26240. }
  26241. // (c0 - v0) - (c1 - v1) --> (covov) (c0 - c1) - v0 + v1
  26242. else if ((details::e_sub == o0) && (details::e_sub == o1) && (details::e_sub == o2))
  26243. {
  26244. const bool synthesis_result =
  26245. synthesize_sf3ext_expression::
  26246. template compile<ctype,vtype,vtype>(expr_gen, "(t-t)+t", (c0 - c1), v0, v1, result);
  26247. exprtk_debug(("(c0 - v0) - (c1 - v1) --> (covov) (c0 - c1) - v0 + v1\n"));
  26248. return (synthesis_result) ? result : error_node();
  26249. }
  26250. // (c0 * v0) * (c1 * v1) --> (covov) (c0 * c1) * v0 * v1
  26251. else if ((details::e_mul == o0) && (details::e_mul == o1) && (details::e_mul == o2))
  26252. {
  26253. const bool synthesis_result =
  26254. synthesize_sf3ext_expression::
  26255. template compile<ctype,vtype,vtype>(expr_gen, "(t*t)*t", (c0 * c1), v0, v1, result);
  26256. exprtk_debug(("(c0 * v0) * (c1 * v1) --> (covov) (c0 * c1) * v0 * v1\n"));
  26257. return (synthesis_result) ? result : error_node();
  26258. }
  26259. // (c0 * v0) / (c1 * v1) --> (covov) (c0 / c1) * (v0 / v1)
  26260. else if ((details::e_mul == o0) && (details::e_div == o1) && (details::e_mul == o2))
  26261. {
  26262. const bool synthesis_result =
  26263. synthesize_sf3ext_expression::
  26264. template compile<ctype,vtype,vtype>(expr_gen, "(t*t)/t", (c0 / c1), v0, v1, result);
  26265. exprtk_debug(("(c0 * v0) / (c1 * v1) --> (covov) (c0 / c1) * (v0 / v1)\n"));
  26266. return (synthesis_result) ? result : error_node();
  26267. }
  26268. // (c0 / v0) * (c1 / v1) --> (covov) (c0 * c1) / (v0 * v1)
  26269. else if ((details::e_div == o0) && (details::e_mul == o1) && (details::e_div == o2))
  26270. {
  26271. const bool synthesis_result =
  26272. synthesize_sf3ext_expression::
  26273. template compile<ctype,vtype,vtype>(expr_gen, "t/(t*t)", (c0 * c1), v0, v1, result);
  26274. exprtk_debug(("(c0 / v0) * (c1 / v1) --> (covov) (c0 * c1) / (v0 * v1)\n"));
  26275. return (synthesis_result) ? result : error_node();
  26276. }
  26277. // (c0 / v0) / (c1 / v1) --> (covov) ((c0 / c1) * v1) / v0
  26278. else if ((details::e_div == o0) && (details::e_div == o1) && (details::e_div == o2))
  26279. {
  26280. const bool synthesis_result =
  26281. synthesize_sf3ext_expression::
  26282. template compile<ctype,vtype,vtype>(expr_gen, "(t*t)/t", (c0 / c1), v1, v0, result);
  26283. exprtk_debug(("(c0 / v0) / (c1 / v1) --> (covov) ((c0 / c1) * v1) / v0\n"));
  26284. return (synthesis_result) ? result : error_node();
  26285. }
  26286. // (c0 * v0) / (c1 / v1) --> (covov) (c0 / c1) * (v0 * v1)
  26287. else if ((details::e_mul == o0) && (details::e_div == o1) && (details::e_div == o2))
  26288. {
  26289. const bool synthesis_result =
  26290. synthesize_sf3ext_expression::
  26291. template compile<ctype,vtype,vtype>(expr_gen, "t*(t*t)", (c0 / c1), v0, v1, result);
  26292. exprtk_debug(("(c0 * v0) / (c1 / v1) --> (covov) (c0 / c1) * (v0 * v1)\n"));
  26293. return (synthesis_result) ? result : error_node();
  26294. }
  26295. // (c0 / v0) / (c1 * v1) --> (covov) (c0 / c1) / (v0 * v1)
  26296. else if ((details::e_div == o0) && (details::e_div == o1) && (details::e_mul == o2))
  26297. {
  26298. const bool synthesis_result =
  26299. synthesize_sf3ext_expression::
  26300. template compile<ctype,vtype,vtype>(expr_gen, "t/(t*t)", (c0 / c1), v0, v1, result);
  26301. exprtk_debug(("(c0 / v0) / (c1 * v1) --> (covov) (c0 / c1) / (v0 * v1)\n"));
  26302. return (synthesis_result) ? result : error_node();
  26303. }
  26304. // (c * v0) +/- (c * v1) --> (covov) c * (v0 +/- v1)
  26305. else if (
  26306. (std::equal_to<T>()(c0,c1)) &&
  26307. (details::e_mul == o0) &&
  26308. (details::e_mul == o2) &&
  26309. (
  26310. (details::e_add == o1) ||
  26311. (details::e_sub == o1)
  26312. )
  26313. )
  26314. {
  26315. std::string specfunc;
  26316. switch (o1)
  26317. {
  26318. case details::e_add : specfunc = "t*(t+t)"; break;
  26319. case details::e_sub : specfunc = "t*(t-t)"; break;
  26320. default : return error_node();
  26321. }
  26322. const bool synthesis_result =
  26323. synthesize_sf3ext_expression::
  26324. template compile<ctype, vtype, vtype>(expr_gen, specfunc, c0, v0, v1, result);
  26325. exprtk_debug(("(c * v0) +/- (c * v1) --> (covov) c * (v0 +/- v1)\n"));
  26326. return (synthesis_result) ? result : error_node();
  26327. }
  26328. }
  26329. const bool synthesis_result =
  26330. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  26331. (expr_gen, id(expr_gen, o0, o1, o2), c0, v0, c1, v1, result);
  26332. if (synthesis_result)
  26333. return result;
  26334. else if (!expr_gen.valid_operator(o0,f0))
  26335. return error_node();
  26336. else if (!expr_gen.valid_operator(o1,f1))
  26337. return error_node();
  26338. else if (!expr_gen.valid_operator(o2,f2))
  26339. return error_node();
  26340. else
  26341. return node_type::allocate(*(expr_gen.node_allocator_), c0, v0, c1, v1, f0, f1, f2);
  26342. }
  26343. static inline std::string id(expression_generator<Type>& expr_gen,
  26344. const details::operator_type o0,
  26345. const details::operator_type o1,
  26346. const details::operator_type o2)
  26347. {
  26348. return details::build_string()
  26349. << "(t" << expr_gen.to_str(o0)
  26350. << "t)" << expr_gen.to_str(o1)
  26351. << "(t" << expr_gen.to_str(o2)
  26352. << "t)";
  26353. }
  26354. };
  26355. struct synthesize_vocovoc_expression0
  26356. {
  26357. typedef typename vocovoc_t::type0 node_type;
  26358. typedef typename vocovoc_t::sf4_type sf4_type;
  26359. typedef typename node_type::T0 T0;
  26360. typedef typename node_type::T1 T1;
  26361. typedef typename node_type::T2 T2;
  26362. typedef typename node_type::T3 T3;
  26363. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  26364. const details::operator_type& operation,
  26365. expression_node_ptr (&branch)[2])
  26366. {
  26367. // (v0 o0 c0) o1 (v1 o2 c1)
  26368. const details::voc_base_node<Type>* voc0 = static_cast<details::voc_base_node<Type>*>(branch[0]);
  26369. const details::voc_base_node<Type>* voc1 = static_cast<details::voc_base_node<Type>*>(branch[1]);
  26370. const Type c0 = voc0->c();
  26371. const Type& v0 = voc0->v();
  26372. const Type c1 = voc1->c();
  26373. const Type& v1 = voc1->v();
  26374. const details::operator_type o0 = voc0->operation();
  26375. const details::operator_type o1 = operation;
  26376. const details::operator_type o2 = voc1->operation();
  26377. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  26378. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  26379. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  26380. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  26381. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  26382. expression_node_ptr result = error_node();
  26383. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  26384. {
  26385. // (v0 + c0) + (v1 + c1) --> (covov) (c0 + c1) + v0 + v1
  26386. if ((details::e_add == o0) && (details::e_add == o1) && (details::e_add == o2))
  26387. {
  26388. const bool synthesis_result =
  26389. synthesize_sf3ext_expression::
  26390. template compile<ctype,vtype,vtype>(expr_gen, "(t+t)+t", (c0 + c1), v0, v1, result);
  26391. exprtk_debug(("(v0 + c0) + (v1 + c1) --> (covov) (c0 + c1) + v0 + v1\n"));
  26392. return (synthesis_result) ? result : error_node();
  26393. }
  26394. // (v0 + c0) - (v1 + c1) --> (covov) (c0 - c1) + v0 - v1
  26395. else if ((details::e_add == o0) && (details::e_sub == o1) && (details::e_add == o2))
  26396. {
  26397. const bool synthesis_result =
  26398. synthesize_sf3ext_expression::
  26399. template compile<ctype,vtype,vtype>(expr_gen, "(t+t)-t", (c0 - c1), v0, v1, result);
  26400. exprtk_debug(("(v0 + c0) - (v1 + c1) --> (covov) (c0 - c1) + v0 - v1\n"));
  26401. return (synthesis_result) ? result : error_node();
  26402. }
  26403. // (v0 - c0) - (v1 - c1) --> (covov) (c1 - c0) + v0 - v1
  26404. else if ((details::e_sub == o0) && (details::e_sub == o1) && (details::e_sub == o2))
  26405. {
  26406. const bool synthesis_result =
  26407. synthesize_sf3ext_expression::
  26408. template compile<ctype,vtype,vtype>(expr_gen, "(t+t)-t", (c1 - c0), v0, v1, result);
  26409. exprtk_debug(("(v0 - c0) - (v1 - c1) --> (covov) (c1 - c0) + v0 - v1\n"));
  26410. return (synthesis_result) ? result : error_node();
  26411. }
  26412. // (v0 * c0) * (v1 * c1) --> (covov) (c0 * c1) * v0 * v1
  26413. else if ((details::e_mul == o0) && (details::e_mul == o1) && (details::e_mul == o2))
  26414. {
  26415. const bool synthesis_result =
  26416. synthesize_sf3ext_expression::
  26417. template compile<ctype,vtype,vtype>(expr_gen, "(t*t)*t", (c0 * c1), v0, v1, result);
  26418. exprtk_debug(("(v0 * c0) * (v1 * c1) --> (covov) (c0 * c1) * v0 * v1\n"));
  26419. return (synthesis_result) ? result : error_node();
  26420. }
  26421. // (v0 * c0) / (v1 * c1) --> (covov) (c0 / c1) * (v0 / v1)
  26422. else if ((details::e_mul == o0) && (details::e_div == o1) && (details::e_mul == o2))
  26423. {
  26424. const bool synthesis_result =
  26425. synthesize_sf3ext_expression::
  26426. template compile<ctype,vtype,vtype>(expr_gen, "(t*t)/t", (c0 / c1), v0, v1, result);
  26427. exprtk_debug(("(v0 * c0) / (v1 * c1) --> (covov) (c0 / c1) * (v0 / v1)\n"));
  26428. return (synthesis_result) ? result : error_node();
  26429. }
  26430. // (v0 / c0) * (v1 / c1) --> (covov) (1 / (c0 * c1)) * v0 * v1
  26431. else if ((details::e_div == o0) && (details::e_mul == o1) && (details::e_div == o2))
  26432. {
  26433. const bool synthesis_result =
  26434. synthesize_sf3ext_expression::
  26435. template compile<ctype,vtype,vtype>(expr_gen, "(t*t)*t", Type(1) / (c0 * c1), v0, v1, result);
  26436. exprtk_debug(("(v0 / c0) * (v1 / c1) --> (covov) (1 / (c0 * c1)) * v0 * v1\n"));
  26437. return (synthesis_result) ? result : error_node();
  26438. }
  26439. // (v0 / c0) / (v1 / c1) --> (covov) ((c1 / c0) * v0) / v1
  26440. else if ((details::e_div == o0) && (details::e_div == o1) && (details::e_div == o2))
  26441. {
  26442. const bool synthesis_result =
  26443. synthesize_sf3ext_expression::
  26444. template compile<ctype,vtype,vtype>(expr_gen, "(t*t)/t", (c1 / c0), v0, v1, result);
  26445. exprtk_debug(("(v0 / c0) / (v1 / c1) --> (covov) ((c1 / c0) * v0) / v1\n"));
  26446. return (synthesis_result) ? result : error_node();
  26447. }
  26448. // (v0 * c0) / (v1 / c1) --> (covov) (c0 * c1) * (v0 / v1)
  26449. else if ((details::e_mul == o0) && (details::e_div == o1) && (details::e_div == o2))
  26450. {
  26451. const bool synthesis_result =
  26452. synthesize_sf3ext_expression::
  26453. template compile<ctype,vtype,vtype>(expr_gen, "t*(t/t)", (c0 * c1), v0, v1, result);
  26454. exprtk_debug(("(v0 * c0) / (v1 / c1) --> (covov) (c0 * c1) * (v0 / v1)\n"));
  26455. return (synthesis_result) ? result : error_node();
  26456. }
  26457. // (v0 / c0) / (v1 * c1) --> (covov) (1 / (c0 * c1)) * v0 / v1
  26458. else if ((details::e_div == o0) && (details::e_div == o1) && (details::e_mul == o2))
  26459. {
  26460. const bool synthesis_result =
  26461. synthesize_sf3ext_expression::
  26462. template compile<ctype,vtype,vtype>(expr_gen, "t*(t/t)", Type(1) / (c0 * c1), v0, v1, result);
  26463. exprtk_debug(("(v0 / c0) / (v1 * c1) --> (covov) (1 / (c0 * c1)) * v0 / v1\n"));
  26464. return (synthesis_result) ? result : error_node();
  26465. }
  26466. // (v0 / c0) * (v1 + c1) --> (vocovoc) (v0 * (1 / c0)) * (v1 + c1)
  26467. else if ((details::e_div == o0) && (details::e_mul == o1) && (details::e_add == o2))
  26468. {
  26469. const bool synthesis_result =
  26470. synthesize_sf4ext_expression::
  26471. template compile<vtype,ctype,vtype,ctype>(expr_gen, "(t*t)*(t+t)", v0, T(1) / c0, v1, c1, result);
  26472. exprtk_debug(("(v0 / c0) * (v1 + c1) --> (vocovoc) (v0 * (1 / c0)) * (v1 + c1)\n"));
  26473. return (synthesis_result) ? result : error_node();
  26474. }
  26475. // (v0 / c0) * (v1 - c1) --> (vocovoc) (v0 * (1 / c0)) * (v1 - c1)
  26476. else if ((details::e_div == o0) && (details::e_mul == o1) && (details::e_sub == o2))
  26477. {
  26478. const bool synthesis_result =
  26479. synthesize_sf4ext_expression::
  26480. template compile<vtype,ctype,vtype,ctype>(expr_gen, "(t*t)*(t-t)", v0, T(1) / c0, v1, c1, result);
  26481. exprtk_debug(("(v0 / c0) * (v1 - c1) --> (vocovoc) (v0 * (1 / c0)) * (v1 - c1)\n"));
  26482. return (synthesis_result) ? result : error_node();
  26483. }
  26484. // (v0 * c) +/- (v1 * c) --> (covov) c * (v0 +/- v1)
  26485. else if (
  26486. (std::equal_to<T>()(c0,c1)) &&
  26487. (details::e_mul == o0) &&
  26488. (details::e_mul == o2) &&
  26489. (
  26490. (details::e_add == o1) ||
  26491. (details::e_sub == o1)
  26492. )
  26493. )
  26494. {
  26495. std::string specfunc;
  26496. switch (o1)
  26497. {
  26498. case details::e_add : specfunc = "t*(t+t)"; break;
  26499. case details::e_sub : specfunc = "t*(t-t)"; break;
  26500. default : return error_node();
  26501. }
  26502. const bool synthesis_result =
  26503. synthesize_sf3ext_expression::
  26504. template compile<ctype,vtype,vtype>(expr_gen, specfunc, c0, v0, v1, result);
  26505. exprtk_debug(("(v0 * c) +/- (v1 * c) --> (covov) c * (v0 +/- v1)\n"));
  26506. return (synthesis_result) ? result : error_node();
  26507. }
  26508. // (v0 / c) +/- (v1 / c) --> (vovoc) (v0 +/- v1) / c
  26509. else if (
  26510. (std::equal_to<T>()(c0,c1)) &&
  26511. (details::e_div == o0) &&
  26512. (details::e_div == o2) &&
  26513. (
  26514. (details::e_add == o1) ||
  26515. (details::e_sub == o1)
  26516. )
  26517. )
  26518. {
  26519. std::string specfunc;
  26520. switch (o1)
  26521. {
  26522. case details::e_add : specfunc = "(t+t)/t"; break;
  26523. case details::e_sub : specfunc = "(t-t)/t"; break;
  26524. default : return error_node();
  26525. }
  26526. const bool synthesis_result =
  26527. synthesize_sf3ext_expression::
  26528. template compile<vtype,vtype,ctype>(expr_gen, specfunc, v0, v1, c0, result);
  26529. exprtk_debug(("(v0 / c) +/- (v1 / c) --> (vovoc) (v0 +/- v1) / c\n"));
  26530. return (synthesis_result) ? result : error_node();
  26531. }
  26532. }
  26533. const bool synthesis_result =
  26534. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  26535. (expr_gen, id(expr_gen, o0, o1, o2), v0, c0, v1, c1, result);
  26536. if (synthesis_result)
  26537. return result;
  26538. else if (!expr_gen.valid_operator(o0,f0))
  26539. return error_node();
  26540. else if (!expr_gen.valid_operator(o1,f1))
  26541. return error_node();
  26542. else if (!expr_gen.valid_operator(o2,f2))
  26543. return error_node();
  26544. else
  26545. return node_type::allocate(*(expr_gen.node_allocator_), v0, c0, v1, c1, f0, f1, f2);
  26546. }
  26547. static inline std::string id(expression_generator<Type>& expr_gen,
  26548. const details::operator_type o0,
  26549. const details::operator_type o1,
  26550. const details::operator_type o2)
  26551. {
  26552. return details::build_string()
  26553. << "(t" << expr_gen.to_str(o0)
  26554. << "t)" << expr_gen.to_str(o1)
  26555. << "(t" << expr_gen.to_str(o2)
  26556. << "t)";
  26557. }
  26558. };
  26559. struct synthesize_covovoc_expression0
  26560. {
  26561. typedef typename covovoc_t::type0 node_type;
  26562. typedef typename covovoc_t::sf4_type sf4_type;
  26563. typedef typename node_type::T0 T0;
  26564. typedef typename node_type::T1 T1;
  26565. typedef typename node_type::T2 T2;
  26566. typedef typename node_type::T3 T3;
  26567. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  26568. const details::operator_type& operation,
  26569. expression_node_ptr (&branch)[2])
  26570. {
  26571. // (c0 o0 v0) o1 (v1 o2 c1)
  26572. const details::cov_base_node<Type>* cov = static_cast<details::cov_base_node<Type>*>(branch[0]);
  26573. const details::voc_base_node<Type>* voc = static_cast<details::voc_base_node<Type>*>(branch[1]);
  26574. const Type c0 = cov->c();
  26575. const Type& v0 = cov->v();
  26576. const Type c1 = voc->c();
  26577. const Type& v1 = voc->v();
  26578. const details::operator_type o0 = cov->operation();
  26579. const details::operator_type o1 = operation;
  26580. const details::operator_type o2 = voc->operation();
  26581. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  26582. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  26583. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  26584. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  26585. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  26586. expression_node_ptr result = error_node();
  26587. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  26588. {
  26589. // (c0 + v0) + (v1 + c1) --> (covov) (c0 + c1) + v0 + v1
  26590. if ((details::e_add == o0) && (details::e_add == o1) && (details::e_add == o2))
  26591. {
  26592. const bool synthesis_result =
  26593. synthesize_sf3ext_expression::
  26594. template compile<ctype,vtype,vtype>(expr_gen, "(t+t)+t", (c0 + c1), v0, v1, result);
  26595. exprtk_debug(("(c0 + v0) + (v1 + c1) --> (covov) (c0 + c1) + v0 + v1\n"));
  26596. return (synthesis_result) ? result : error_node();
  26597. }
  26598. // (c0 + v0) - (v1 + c1) --> (covov) (c0 - c1) + v0 - v1
  26599. else if ((details::e_add == o0) && (details::e_sub == o1) && (details::e_add == o2))
  26600. {
  26601. const bool synthesis_result =
  26602. synthesize_sf3ext_expression::
  26603. template compile<ctype,vtype,vtype>(expr_gen, "(t+t)-t", (c0 - c1), v0, v1, result);
  26604. exprtk_debug(("(c0 + v0) - (v1 + c1) --> (covov) (c0 - c1) + v0 - v1\n"));
  26605. return (synthesis_result) ? result : error_node();
  26606. }
  26607. // (c0 - v0) - (v1 - c1) --> (covov) (c0 + c1) - v0 - v1
  26608. else if ((details::e_sub == o0) && (details::e_sub == o1) && (details::e_sub == o2))
  26609. {
  26610. const bool synthesis_result =
  26611. synthesize_sf3ext_expression::
  26612. template compile<ctype,vtype,vtype>(expr_gen, "t-(t+t)", (c0 + c1), v0, v1, result);
  26613. exprtk_debug(("(c0 - v0) - (v1 - c1) --> (covov) (c0 + c1) - v0 - v1\n"));
  26614. return (synthesis_result) ? result : error_node();
  26615. }
  26616. // (c0 * v0) * (v1 * c1) --> (covov) (c0 * c1) * v0 * v1
  26617. else if ((details::e_mul == o0) && (details::e_mul == o1) && (details::e_mul == o2))
  26618. {
  26619. const bool synthesis_result =
  26620. synthesize_sf3ext_expression::
  26621. template compile<ctype,vtype,vtype>(expr_gen, "(t*t)*t", (c0 * c1), v0, v1, result);
  26622. exprtk_debug(("(c0 * v0) * (v1 * c1) --> (covov) (c0 * c1) * v0 * v1\n"));
  26623. return (synthesis_result) ? result : error_node();
  26624. }
  26625. // (c0 * v0) / (v1 * c1) --> (covov) (c0 / c1) * (v0 / v1)
  26626. else if ((details::e_mul == o0) && (details::e_div == o1) && (details::e_mul == o2))
  26627. {
  26628. const bool synthesis_result =
  26629. synthesize_sf3ext_expression::
  26630. template compile<ctype,vtype,vtype>(expr_gen, "(t*t)/t", (c0 / c1), v0, v1, result);
  26631. exprtk_debug(("(c0 * v0) / (v1 * c1) --> (covov) (c0 / c1) * (v0 / v1)\n"));
  26632. return (synthesis_result) ? result : error_node();
  26633. }
  26634. // (c0 / v0) * (v1 / c1) --> (covov) (c0 / c1) * (v1 / v0)
  26635. else if ((details::e_div == o0) && (details::e_mul == o1) && (details::e_div == o2))
  26636. {
  26637. const bool synthesis_result =
  26638. synthesize_sf3ext_expression::
  26639. template compile<ctype,vtype,vtype>(expr_gen, "t*(t/t)", (c0 / c1), v1, v0, result);
  26640. exprtk_debug(("(c0 / v0) * (v1 / c1) --> (covov) (c0 / c1) * (v1 / v0)\n"));
  26641. return (synthesis_result) ? result : error_node();
  26642. }
  26643. // (c0 / v0) / (v1 / c1) --> (covov) (c0 * c1) / (v0 * v1)
  26644. else if ((details::e_div == o0) && (details::e_div == o1) && (details::e_div == o2))
  26645. {
  26646. const bool synthesis_result =
  26647. synthesize_sf3ext_expression::
  26648. template compile<ctype,vtype,vtype>(expr_gen, "t/(t*t)", (c0 * c1), v0, v1, result);
  26649. exprtk_debug(("(c0 / v0) / (v1 / c1) --> (covov) (c0 * c1) / (v0 * v1)\n"));
  26650. return (synthesis_result) ? result : error_node();
  26651. }
  26652. // (c0 * v0) / (v1 / c1) --> (covov) (c0 * c1) * (v0 / v1)
  26653. else if ((details::e_mul == o0) && (details::e_div == o1) && (details::e_div == o2))
  26654. {
  26655. const bool synthesis_result =
  26656. synthesize_sf3ext_expression::
  26657. template compile<ctype,vtype,vtype>(expr_gen, "(t*t)/t", (c0 * c1), v0, v1, result);
  26658. exprtk_debug(("(c0 * v0) / (v1 / c1) --> (covov) (c0 * c1) * (v0 / v1)\n"));
  26659. return (synthesis_result) ? result : error_node();
  26660. }
  26661. // (c0 / v0) / (v1 * c1) --> (covov) (c0 / c1) / (v0 * v1)
  26662. else if ((details::e_div == o0) && (details::e_div == o1) && (details::e_mul == o2))
  26663. {
  26664. const bool synthesis_result =
  26665. synthesize_sf3ext_expression::
  26666. template compile<ctype,vtype,vtype>(expr_gen, "t/(t*t)", (c0 / c1), v0, v1, result);
  26667. exprtk_debug(("(c0 / v0) / (v1 * c1) --> (covov) (c0 / c1) / (v0 * v1)\n"));
  26668. return (synthesis_result) ? result : error_node();
  26669. }
  26670. // (c * v0) +/- (v1 * c) --> (covov) c * (v0 +/- v1)
  26671. else if (
  26672. (std::equal_to<T>()(c0,c1)) &&
  26673. (details::e_mul == o0) &&
  26674. (details::e_mul == o2) &&
  26675. (
  26676. (details::e_add == o1) ||
  26677. (details::e_sub == o1)
  26678. )
  26679. )
  26680. {
  26681. std::string specfunc;
  26682. switch (o1)
  26683. {
  26684. case details::e_add : specfunc = "t*(t+t)"; break;
  26685. case details::e_sub : specfunc = "t*(t-t)"; break;
  26686. default : return error_node();
  26687. }
  26688. const bool synthesis_result =
  26689. synthesize_sf3ext_expression::
  26690. template compile<ctype,vtype,vtype>(expr_gen,specfunc, c0, v0, v1, result);
  26691. exprtk_debug(("(c * v0) +/- (v1 * c) --> (covov) c * (v0 +/- v1)\n"));
  26692. return (synthesis_result) ? result : error_node();
  26693. }
  26694. }
  26695. const bool synthesis_result =
  26696. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  26697. (expr_gen, id(expr_gen, o0, o1, o2), c0, v0, v1, c1, result);
  26698. if (synthesis_result)
  26699. return result;
  26700. else if (!expr_gen.valid_operator(o0,f0))
  26701. return error_node();
  26702. else if (!expr_gen.valid_operator(o1,f1))
  26703. return error_node();
  26704. else if (!expr_gen.valid_operator(o2,f2))
  26705. return error_node();
  26706. else
  26707. return node_type::allocate(*(expr_gen.node_allocator_), c0, v0, v1, c1, f0, f1, f2);
  26708. }
  26709. static inline std::string id(expression_generator<Type>& expr_gen,
  26710. const details::operator_type o0,
  26711. const details::operator_type o1,
  26712. const details::operator_type o2)
  26713. {
  26714. return details::build_string()
  26715. << "(t" << expr_gen.to_str(o0)
  26716. << "t)" << expr_gen.to_str(o1)
  26717. << "(t" << expr_gen.to_str(o2)
  26718. << "t)";
  26719. }
  26720. };
  26721. struct synthesize_vococov_expression0
  26722. {
  26723. typedef typename vococov_t::type0 node_type;
  26724. typedef typename vococov_t::sf4_type sf4_type;
  26725. typedef typename node_type::T0 T0;
  26726. typedef typename node_type::T1 T1;
  26727. typedef typename node_type::T2 T2;
  26728. typedef typename node_type::T3 T3;
  26729. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  26730. const details::operator_type& operation,
  26731. expression_node_ptr (&branch)[2])
  26732. {
  26733. // (v0 o0 c0) o1 (c1 o2 v1)
  26734. const details::voc_base_node<Type>* voc = static_cast<details::voc_base_node<Type>*>(branch[0]);
  26735. const details::cov_base_node<Type>* cov = static_cast<details::cov_base_node<Type>*>(branch[1]);
  26736. const Type c0 = voc->c();
  26737. const Type& v0 = voc->v();
  26738. const Type c1 = cov->c();
  26739. const Type& v1 = cov->v();
  26740. const details::operator_type o0 = voc->operation();
  26741. const details::operator_type o1 = operation;
  26742. const details::operator_type o2 = cov->operation();
  26743. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  26744. binary_functor_t f1 = reinterpret_cast<binary_functor_t>(0);
  26745. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  26746. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  26747. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  26748. expression_node_ptr result = error_node();
  26749. if (expr_gen.parser_->settings_.strength_reduction_enabled())
  26750. {
  26751. // (v0 + c0) + (c1 + v1) --> (covov) (c0 + c1) + v0 + v1
  26752. if ((details::e_add == o0) && (details::e_add == o1) && (details::e_add == o2))
  26753. {
  26754. const bool synthesis_result =
  26755. synthesize_sf3ext_expression::
  26756. template compile<ctype,vtype,vtype>(expr_gen, "(t+t)+t", (c0 + c1), v0, v1, result);
  26757. exprtk_debug(("(v0 + c0) + (c1 + v1) --> (covov) (c0 + c1) + v0 + v1\n"));
  26758. return (synthesis_result) ? result : error_node();
  26759. }
  26760. // (v0 + c0) - (c1 + v1) --> (covov) (c0 - c1) + v0 - v1
  26761. else if ((details::e_add == o0) && (details::e_sub == o1) && (details::e_add == o2))
  26762. {
  26763. const bool synthesis_result =
  26764. synthesize_sf3ext_expression::
  26765. template compile<ctype,vtype,vtype>(expr_gen, "(t+t)-t", (c0 - c1), v0, v1, result);
  26766. exprtk_debug(("(v0 + c0) - (c1 + v1) --> (covov) (c0 - c1) + v0 - v1\n"));
  26767. return (synthesis_result) ? result : error_node();
  26768. }
  26769. // (v0 - c0) - (c1 - v1) --> (vovoc) v0 + v1 - (c1 + c0)
  26770. else if ((details::e_sub == o0) && (details::e_sub == o1) && (details::e_sub == o2))
  26771. {
  26772. const bool synthesis_result =
  26773. synthesize_sf3ext_expression::
  26774. template compile<vtype,vtype,ctype>(expr_gen, "(t+t)-t", v0, v1, (c1 + c0), result);
  26775. exprtk_debug(("(v0 - c0) - (c1 - v1) --> (vovoc) v0 + v1 - (c1 + c0)\n"));
  26776. return (synthesis_result) ? result : error_node();
  26777. }
  26778. // (v0 * c0) * (c1 * v1) --> (covov) (c0 * c1) * v0 * v1
  26779. else if ((details::e_mul == o0) && (details::e_mul == o1) && (details::e_mul == o2))
  26780. {
  26781. const bool synthesis_result =
  26782. synthesize_sf3ext_expression::
  26783. template compile<ctype,vtype,vtype>(expr_gen, "(t*t)*t", (c0 * c1), v0, v1, result);
  26784. exprtk_debug(("(v0 * c0) * (c1 * v1) --> (covov) (c0 * c1) * v0 * v1\n"));
  26785. return (synthesis_result) ? result : error_node();
  26786. }
  26787. // (v0 * c0) / (c1 * v1) --> (covov) (c0 / c1) * (v0 * v1)
  26788. else if ((details::e_mul == o0) && (details::e_div == o1) && (details::e_mul == o2))
  26789. {
  26790. const bool synthesis_result =
  26791. synthesize_sf3ext_expression::
  26792. template compile<ctype,vtype,vtype>(expr_gen, "(t*t)/t", (c0 / c1), v0, v1, result);
  26793. exprtk_debug(("(v0 * c0) / (c1 * v1) --> (covov) (c0 / c1) * (v0 * v1)\n"));
  26794. return (synthesis_result) ? result : error_node();
  26795. }
  26796. // (v0 / c0) * (c1 / v1) --> (covov) (c1 / c0) * (v0 / v1)
  26797. else if ((details::e_div == o0) && (details::e_mul == o1) && (details::e_div == o2))
  26798. {
  26799. const bool synthesis_result =
  26800. synthesize_sf3ext_expression::
  26801. template compile<ctype,vtype,vtype>(expr_gen, "(t*t)/t", (c1 / c0), v0, v1, result);
  26802. exprtk_debug(("(v0 / c0) * (c1 / v1) --> (covov) (c1 / c0) * (v0 / v1)\n"));
  26803. return (synthesis_result) ? result : error_node();
  26804. }
  26805. // (v0 * c0) / (c1 / v1) --> (covov) (c0 / c1) * (v0 * v1)
  26806. else if ((details::e_mul == o0) && (details::e_div == o1) && (details::e_div == o2))
  26807. {
  26808. const bool synthesis_result =
  26809. synthesize_sf3ext_expression::
  26810. template compile<ctype,vtype,vtype>(expr_gen, "(t*t)*t", (c0 / c1), v0, v1, result);
  26811. exprtk_debug(("(v0 * c0) / (c1 / v1) --> (covov) (c0 / c1) * (v0 * v1)\n"));
  26812. return (synthesis_result) ? result : error_node();
  26813. }
  26814. // (v0 / c0) / (c1 * v1) --> (covov) (1 / (c0 * c1)) * (v0 / v1)
  26815. else if ((details::e_div == o0) && (details::e_div == o1) && (details::e_mul == o2))
  26816. {
  26817. const bool synthesis_result =
  26818. synthesize_sf3ext_expression::
  26819. template compile<ctype,vtype,vtype>(expr_gen, "(t*t)/t", Type(1) / (c0 * c1), v0, v1, result);
  26820. exprtk_debug(("(v0 / c0) / (c1 * v1) --> (covov) (1 / (c0 * c1)) * (v0 / v1)\n"));
  26821. return (synthesis_result) ? result : error_node();
  26822. }
  26823. // (v0 / c0) / (c1 / v1) --> (vovoc) (v0 * v1) * (1 / (c0 * c1))
  26824. else if ((details::e_div == o0) && (details::e_div == o1) && (details::e_div == o2))
  26825. {
  26826. const bool synthesis_result =
  26827. synthesize_sf3ext_expression::
  26828. template compile<vtype,vtype,ctype>(expr_gen, "(t*t)*t", v0, v1, Type(1) / (c0 * c1), result);
  26829. exprtk_debug(("(v0 / c0) / (c1 / v1) --> (vovoc) (v0 * v1) * (1 / (c0 * c1))\n"));
  26830. return (synthesis_result) ? result : error_node();
  26831. }
  26832. // (v0 * c) +/- (c * v1) --> (covov) c * (v0 +/- v1)
  26833. else if (
  26834. (std::equal_to<T>()(c0,c1)) &&
  26835. (details::e_mul == o0) &&
  26836. (details::e_mul == o2) &&
  26837. (
  26838. (details::e_add == o1) || (details::e_sub == o1)
  26839. )
  26840. )
  26841. {
  26842. std::string specfunc;
  26843. switch (o1)
  26844. {
  26845. case details::e_add : specfunc = "t*(t+t)"; break;
  26846. case details::e_sub : specfunc = "t*(t-t)"; break;
  26847. default : return error_node();
  26848. }
  26849. const bool synthesis_result =
  26850. synthesize_sf3ext_expression::
  26851. template compile<ctype,vtype,vtype>(expr_gen, specfunc, c0, v0, v1, result);
  26852. exprtk_debug(("(v0 * c) +/- (c * v1) --> (covov) c * (v0 +/- v1)\n"));
  26853. return (synthesis_result) ? result : error_node();
  26854. }
  26855. }
  26856. const bool synthesis_result =
  26857. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  26858. (expr_gen, id(expr_gen, o0, o1, o2), v0, c0, c1, v1, result);
  26859. if (synthesis_result)
  26860. return result;
  26861. else if (!expr_gen.valid_operator(o0,f0))
  26862. return error_node();
  26863. else if (!expr_gen.valid_operator(o1,f1))
  26864. return error_node();
  26865. else if (!expr_gen.valid_operator(o2,f2))
  26866. return error_node();
  26867. else
  26868. return node_type::allocate(*(expr_gen.node_allocator_), v0, c0, c1, v1, f0, f1, f2);
  26869. }
  26870. static inline std::string id(expression_generator<Type>& expr_gen,
  26871. const details::operator_type o0,
  26872. const details::operator_type o1,
  26873. const details::operator_type o2)
  26874. {
  26875. return details::build_string()
  26876. << "(t" << expr_gen.to_str(o0)
  26877. << "t)" << expr_gen.to_str(o1)
  26878. << "(t" << expr_gen.to_str(o2)
  26879. << "t)";
  26880. }
  26881. };
  26882. struct synthesize_vovovov_expression1
  26883. {
  26884. typedef typename vovovov_t::type1 node_type;
  26885. typedef typename vovovov_t::sf4_type sf4_type;
  26886. typedef typename node_type::T0 T0;
  26887. typedef typename node_type::T1 T1;
  26888. typedef typename node_type::T2 T2;
  26889. typedef typename node_type::T3 T3;
  26890. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  26891. const details::operator_type& operation,
  26892. expression_node_ptr (&branch)[2])
  26893. {
  26894. // v0 o0 (v1 o1 (v2 o2 v3))
  26895. typedef typename synthesize_vovov_expression1::node_type lcl_vovov_t;
  26896. const lcl_vovov_t* vovov = static_cast<const lcl_vovov_t*>(branch[1]);
  26897. const Type& v0 = static_cast<details::variable_node<Type>*>(branch[0])->ref();
  26898. const Type& v1 = vovov->t0();
  26899. const Type& v2 = vovov->t1();
  26900. const Type& v3 = vovov->t2();
  26901. const details::operator_type o0 = operation;
  26902. const details::operator_type o1 = expr_gen.get_operator(vovov->f0());
  26903. const details::operator_type o2 = expr_gen.get_operator(vovov->f1());
  26904. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  26905. binary_functor_t f1 = vovov->f0();
  26906. binary_functor_t f2 = vovov->f1();
  26907. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  26908. expression_node_ptr result = error_node();
  26909. if (synthesize_sf4ext_expression::template compile<T0,T1,T2,T3>(expr_gen,id(expr_gen,o0,o1,o2),v0,v1,v2,v3,result))
  26910. return result;
  26911. else if (!expr_gen.valid_operator(o0,f0))
  26912. return error_node();
  26913. exprtk_debug(("v0 o0 (v1 o1 (v2 o2 v3))\n"));
  26914. return node_type::allocate(*(expr_gen.node_allocator_),v0,v1,v2,v3,f0,f1,f2);
  26915. }
  26916. static inline std::string id(expression_generator<Type>& expr_gen,
  26917. const details::operator_type o0,
  26918. const details::operator_type o1,
  26919. const details::operator_type o2)
  26920. {
  26921. return details::build_string()
  26922. << "t" << expr_gen.to_str(o0)
  26923. << "(t" << expr_gen.to_str(o1)
  26924. << "(t" << expr_gen.to_str(o2)
  26925. << "t))";
  26926. }
  26927. };
  26928. struct synthesize_vovovoc_expression1
  26929. {
  26930. typedef typename vovovoc_t::type1 node_type;
  26931. typedef typename vovovoc_t::sf4_type sf4_type;
  26932. typedef typename node_type::T0 T0;
  26933. typedef typename node_type::T1 T1;
  26934. typedef typename node_type::T2 T2;
  26935. typedef typename node_type::T3 T3;
  26936. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  26937. const details::operator_type& operation,
  26938. expression_node_ptr (&branch)[2])
  26939. {
  26940. // v0 o0 (v1 o1 (v2 o2 c))
  26941. typedef typename synthesize_vovoc_expression1::node_type lcl_vovoc_t;
  26942. const lcl_vovoc_t* vovoc = static_cast<const lcl_vovoc_t*>(branch[1]);
  26943. const Type& v0 = static_cast<details::variable_node<Type>*>(branch[0])->ref();
  26944. const Type& v1 = vovoc->t0();
  26945. const Type& v2 = vovoc->t1();
  26946. const Type c = vovoc->t2();
  26947. const details::operator_type o0 = operation;
  26948. const details::operator_type o1 = expr_gen.get_operator(vovoc->f0());
  26949. const details::operator_type o2 = expr_gen.get_operator(vovoc->f1());
  26950. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  26951. binary_functor_t f1 = vovoc->f0();
  26952. binary_functor_t f2 = vovoc->f1();
  26953. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  26954. expression_node_ptr result = error_node();
  26955. const bool synthesis_result =
  26956. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  26957. (expr_gen, id(expr_gen, o0, o1, o2), v0, v1, v2, c, result);
  26958. if (synthesis_result)
  26959. return result;
  26960. else if (!expr_gen.valid_operator(o0,f0))
  26961. return error_node();
  26962. exprtk_debug(("v0 o0 (v1 o1 (v2 o2 c))\n"));
  26963. return node_type::allocate(*(expr_gen.node_allocator_), v0, v1, v2, c, f0, f1, f2);
  26964. }
  26965. static inline std::string id(expression_generator<Type>& expr_gen,
  26966. const details::operator_type o0,
  26967. const details::operator_type o1,
  26968. const details::operator_type o2)
  26969. {
  26970. return details::build_string()
  26971. << "t" << expr_gen.to_str(o0)
  26972. << "(t" << expr_gen.to_str(o1)
  26973. << "(t" << expr_gen.to_str(o2)
  26974. << "t))";
  26975. }
  26976. };
  26977. struct synthesize_vovocov_expression1
  26978. {
  26979. typedef typename vovocov_t::type1 node_type;
  26980. typedef typename vovocov_t::sf4_type sf4_type;
  26981. typedef typename node_type::T0 T0;
  26982. typedef typename node_type::T1 T1;
  26983. typedef typename node_type::T2 T2;
  26984. typedef typename node_type::T3 T3;
  26985. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  26986. const details::operator_type& operation,
  26987. expression_node_ptr (&branch)[2])
  26988. {
  26989. // v0 o0 (v1 o1 (c o2 v2))
  26990. typedef typename synthesize_vocov_expression1::node_type lcl_vocov_t;
  26991. const lcl_vocov_t* vocov = static_cast<const lcl_vocov_t*>(branch[1]);
  26992. const Type& v0 = static_cast<details::variable_node<Type>*>(branch[0])->ref();
  26993. const Type& v1 = vocov->t0();
  26994. const Type c = vocov->t1();
  26995. const Type& v2 = vocov->t2();
  26996. const details::operator_type o0 = operation;
  26997. const details::operator_type o1 = expr_gen.get_operator(vocov->f0());
  26998. const details::operator_type o2 = expr_gen.get_operator(vocov->f1());
  26999. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  27000. binary_functor_t f1 = vocov->f0();
  27001. binary_functor_t f2 = vocov->f1();
  27002. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  27003. expression_node_ptr result = error_node();
  27004. const bool synthesis_result =
  27005. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  27006. (expr_gen, id(expr_gen, o0, o1, o2), v0, v1, c, v2, result);
  27007. if (synthesis_result)
  27008. return result;
  27009. if (!expr_gen.valid_operator(o0,f0))
  27010. return error_node();
  27011. exprtk_debug(("v0 o0 (v1 o1 (c o2 v2))\n"));
  27012. return node_type::allocate(*(expr_gen.node_allocator_), v0, v1, c, v2, f0, f1, f2);
  27013. }
  27014. static inline std::string id(expression_generator<Type>& expr_gen,
  27015. const details::operator_type o0,
  27016. const details::operator_type o1,
  27017. const details::operator_type o2)
  27018. {
  27019. return details::build_string()
  27020. << "t" << expr_gen.to_str(o0)
  27021. << "(t" << expr_gen.to_str(o1)
  27022. << "(t" << expr_gen.to_str(o2)
  27023. << "t))";
  27024. }
  27025. };
  27026. struct synthesize_vocovov_expression1
  27027. {
  27028. typedef typename vocovov_t::type1 node_type;
  27029. typedef typename vocovov_t::sf4_type sf4_type;
  27030. typedef typename node_type::T0 T0;
  27031. typedef typename node_type::T1 T1;
  27032. typedef typename node_type::T2 T2;
  27033. typedef typename node_type::T3 T3;
  27034. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  27035. const details::operator_type& operation,
  27036. expression_node_ptr (&branch)[2])
  27037. {
  27038. // v0 o0 (c o1 (v1 o2 v2))
  27039. typedef typename synthesize_covov_expression1::node_type lcl_covov_t;
  27040. const lcl_covov_t* covov = static_cast<const lcl_covov_t*>(branch[1]);
  27041. const Type& v0 = static_cast<details::variable_node<Type>*>(branch[0])->ref();
  27042. const Type c = covov->t0();
  27043. const Type& v1 = covov->t1();
  27044. const Type& v2 = covov->t2();
  27045. const details::operator_type o0 = operation;
  27046. const details::operator_type o1 = expr_gen.get_operator(covov->f0());
  27047. const details::operator_type o2 = expr_gen.get_operator(covov->f1());
  27048. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  27049. binary_functor_t f1 = covov->f0();
  27050. binary_functor_t f2 = covov->f1();
  27051. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  27052. expression_node_ptr result = error_node();
  27053. const bool synthesis_result =
  27054. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  27055. (expr_gen, id(expr_gen, o0, o1, o2), v0, c, v1, v2, result);
  27056. if (synthesis_result)
  27057. return result;
  27058. else if (!expr_gen.valid_operator(o0,f0))
  27059. return error_node();
  27060. exprtk_debug(("v0 o0 (c o1 (v1 o2 v2))\n"));
  27061. return node_type::allocate(*(expr_gen.node_allocator_), v0, c, v1, v2, f0, f1, f2);
  27062. }
  27063. static inline std::string id(expression_generator<Type>& expr_gen,
  27064. const details::operator_type o0,
  27065. const details::operator_type o1,
  27066. const details::operator_type o2)
  27067. {
  27068. return details::build_string()
  27069. << "t" << expr_gen.to_str(o0)
  27070. << "(t" << expr_gen.to_str(o1)
  27071. << "(t" << expr_gen.to_str(o2)
  27072. << "t))";
  27073. }
  27074. };
  27075. struct synthesize_covovov_expression1
  27076. {
  27077. typedef typename covovov_t::type1 node_type;
  27078. typedef typename covovov_t::sf4_type sf4_type;
  27079. typedef typename node_type::T0 T0;
  27080. typedef typename node_type::T1 T1;
  27081. typedef typename node_type::T2 T2;
  27082. typedef typename node_type::T3 T3;
  27083. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  27084. const details::operator_type& operation,
  27085. expression_node_ptr (&branch)[2])
  27086. {
  27087. // c o0 (v0 o1 (v1 o2 v2))
  27088. typedef typename synthesize_vovov_expression1::node_type lcl_vovov_t;
  27089. const lcl_vovov_t* vovov = static_cast<const lcl_vovov_t*>(branch[1]);
  27090. const Type c = static_cast<details::literal_node<Type>*>(branch[0])->value();
  27091. const Type& v0 = vovov->t0();
  27092. const Type& v1 = vovov->t1();
  27093. const Type& v2 = vovov->t2();
  27094. const details::operator_type o0 = operation;
  27095. const details::operator_type o1 = expr_gen.get_operator(vovov->f0());
  27096. const details::operator_type o2 = expr_gen.get_operator(vovov->f1());
  27097. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  27098. binary_functor_t f1 = vovov->f0();
  27099. binary_functor_t f2 = vovov->f1();
  27100. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  27101. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  27102. expression_node_ptr result = error_node();
  27103. const bool synthesis_result =
  27104. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  27105. (expr_gen, id(expr_gen, o0, o1, o2), c, v0, v1, v2, result);
  27106. if (synthesis_result)
  27107. return result;
  27108. if (!expr_gen.valid_operator(o0,f0))
  27109. return error_node();
  27110. exprtk_debug(("c o0 (v0 o1 (v1 o2 v2))\n"));
  27111. return node_type::allocate(*(expr_gen.node_allocator_), c, v0, v1, v2, f0, f1, f2);
  27112. }
  27113. static inline std::string id(expression_generator<Type>& expr_gen,
  27114. const details::operator_type o0,
  27115. const details::operator_type o1,
  27116. const details::operator_type o2)
  27117. {
  27118. return details::build_string()
  27119. << "t" << expr_gen.to_str(o0)
  27120. << "(t" << expr_gen.to_str(o1)
  27121. << "(t" << expr_gen.to_str(o2)
  27122. << "t))";
  27123. }
  27124. };
  27125. struct synthesize_covocov_expression1
  27126. {
  27127. typedef typename covocov_t::type1 node_type;
  27128. typedef typename covocov_t::sf4_type sf4_type;
  27129. typedef typename node_type::T0 T0;
  27130. typedef typename node_type::T1 T1;
  27131. typedef typename node_type::T2 T2;
  27132. typedef typename node_type::T3 T3;
  27133. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  27134. const details::operator_type& operation,
  27135. expression_node_ptr (&branch)[2])
  27136. {
  27137. // c0 o0 (v0 o1 (c1 o2 v1))
  27138. typedef typename synthesize_vocov_expression1::node_type lcl_vocov_t;
  27139. const lcl_vocov_t* vocov = static_cast<const lcl_vocov_t*>(branch[1]);
  27140. const Type c0 = static_cast<details::literal_node<Type>*>(branch[0])->value();
  27141. const Type& v0 = vocov->t0();
  27142. const Type c1 = vocov->t1();
  27143. const Type& v1 = vocov->t2();
  27144. const details::operator_type o0 = operation;
  27145. const details::operator_type o1 = expr_gen.get_operator(vocov->f0());
  27146. const details::operator_type o2 = expr_gen.get_operator(vocov->f1());
  27147. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  27148. binary_functor_t f1 = vocov->f0();
  27149. binary_functor_t f2 = vocov->f1();
  27150. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  27151. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  27152. expression_node_ptr result = error_node();
  27153. const bool synthesis_result =
  27154. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  27155. (expr_gen, id(expr_gen, o0, o1, o2), c0, v0, c1, v1, result);
  27156. if (synthesis_result)
  27157. return result;
  27158. else if (!expr_gen.valid_operator(o0,f0))
  27159. return error_node();
  27160. exprtk_debug(("c0 o0 (v0 o1 (c1 o2 v1))\n"));
  27161. return node_type::allocate(*(expr_gen.node_allocator_), c0, v0, c1, v1, f0, f1, f2);
  27162. }
  27163. static inline std::string id(expression_generator<Type>& expr_gen,
  27164. const details::operator_type o0,
  27165. const details::operator_type o1,
  27166. const details::operator_type o2)
  27167. {
  27168. return details::build_string()
  27169. << "t" << expr_gen.to_str(o0)
  27170. << "(t" << expr_gen.to_str(o1)
  27171. << "(t" << expr_gen.to_str(o2)
  27172. << "t))";
  27173. }
  27174. };
  27175. struct synthesize_vocovoc_expression1
  27176. {
  27177. typedef typename vocovoc_t::type1 node_type;
  27178. typedef typename vocovoc_t::sf4_type sf4_type;
  27179. typedef typename node_type::T0 T0;
  27180. typedef typename node_type::T1 T1;
  27181. typedef typename node_type::T2 T2;
  27182. typedef typename node_type::T3 T3;
  27183. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  27184. const details::operator_type& operation,
  27185. expression_node_ptr (&branch)[2])
  27186. {
  27187. // v0 o0 (c0 o1 (v1 o2 c2))
  27188. typedef typename synthesize_covoc_expression1::node_type lcl_covoc_t;
  27189. const lcl_covoc_t* covoc = static_cast<const lcl_covoc_t*>(branch[1]);
  27190. const Type& v0 = static_cast<details::variable_node<Type>*>(branch[0])->ref();
  27191. const Type c0 = covoc->t0();
  27192. const Type& v1 = covoc->t1();
  27193. const Type c1 = covoc->t2();
  27194. const details::operator_type o0 = operation;
  27195. const details::operator_type o1 = expr_gen.get_operator(covoc->f0());
  27196. const details::operator_type o2 = expr_gen.get_operator(covoc->f1());
  27197. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  27198. binary_functor_t f1 = covoc->f0();
  27199. binary_functor_t f2 = covoc->f1();
  27200. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  27201. expression_node_ptr result = error_node();
  27202. const bool synthesis_result =
  27203. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  27204. (expr_gen, id(expr_gen, o0, o1, o2), v0, c0, v1, c1, result);
  27205. if (synthesis_result)
  27206. return result;
  27207. else if (!expr_gen.valid_operator(o0,f0))
  27208. return error_node();
  27209. exprtk_debug(("v0 o0 (c0 o1 (v1 o2 c2))\n"));
  27210. return node_type::allocate(*(expr_gen.node_allocator_), v0, c0, v1, c1, f0, f1, f2);
  27211. }
  27212. static inline std::string id(expression_generator<Type>& expr_gen,
  27213. const details::operator_type o0,
  27214. const details::operator_type o1,
  27215. const details::operator_type o2)
  27216. {
  27217. return details::build_string()
  27218. << "t" << expr_gen.to_str(o0)
  27219. << "(t" << expr_gen.to_str(o1)
  27220. << "(t" << expr_gen.to_str(o2)
  27221. << "t))";
  27222. }
  27223. };
  27224. struct synthesize_covovoc_expression1
  27225. {
  27226. typedef typename covovoc_t::type1 node_type;
  27227. typedef typename covovoc_t::sf4_type sf4_type;
  27228. typedef typename node_type::T0 T0;
  27229. typedef typename node_type::T1 T1;
  27230. typedef typename node_type::T2 T2;
  27231. typedef typename node_type::T3 T3;
  27232. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  27233. const details::operator_type& operation,
  27234. expression_node_ptr (&branch)[2])
  27235. {
  27236. // c0 o0 (v0 o1 (v1 o2 c1))
  27237. typedef typename synthesize_vovoc_expression1::node_type lcl_vovoc_t;
  27238. const lcl_vovoc_t* vovoc = static_cast<const lcl_vovoc_t*>(branch[1]);
  27239. const Type c0 = static_cast<details::literal_node<Type>*>(branch[0])->value();
  27240. const Type& v0 = vovoc->t0();
  27241. const Type& v1 = vovoc->t1();
  27242. const Type c1 = vovoc->t2();
  27243. const details::operator_type o0 = operation;
  27244. const details::operator_type o1 = expr_gen.get_operator(vovoc->f0());
  27245. const details::operator_type o2 = expr_gen.get_operator(vovoc->f1());
  27246. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  27247. binary_functor_t f1 = vovoc->f0();
  27248. binary_functor_t f2 = vovoc->f1();
  27249. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  27250. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  27251. expression_node_ptr result = error_node();
  27252. const bool synthesis_result =
  27253. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  27254. (expr_gen, id(expr_gen, o0, o1, o2), c0, v0, v1, c1, result);
  27255. if (synthesis_result)
  27256. return result;
  27257. else if (!expr_gen.valid_operator(o0,f0))
  27258. return error_node();
  27259. exprtk_debug(("c0 o0 (v0 o1 (v1 o2 c1))\n"));
  27260. return node_type::allocate(*(expr_gen.node_allocator_), c0, v0, v1, c1, f0, f1, f2);
  27261. }
  27262. static inline std::string id(expression_generator<Type>& expr_gen,
  27263. const details::operator_type o0,
  27264. const details::operator_type o1,
  27265. const details::operator_type o2)
  27266. {
  27267. return details::build_string()
  27268. << "t" << expr_gen.to_str(o0)
  27269. << "(t" << expr_gen.to_str(o1)
  27270. << "(t" << expr_gen.to_str(o2)
  27271. << "t))";
  27272. }
  27273. };
  27274. struct synthesize_vococov_expression1
  27275. {
  27276. typedef typename vococov_t::type1 node_type;
  27277. typedef typename vococov_t::sf4_type sf4_type;
  27278. typedef typename node_type::T0 T0;
  27279. typedef typename node_type::T1 T1;
  27280. typedef typename node_type::T2 T2;
  27281. typedef typename node_type::T3 T3;
  27282. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  27283. const details::operator_type& operation,
  27284. expression_node_ptr (&branch)[2])
  27285. {
  27286. // v0 o0 (c0 o1 (c1 o2 v1))
  27287. typedef typename synthesize_cocov_expression1::node_type lcl_cocov_t;
  27288. const lcl_cocov_t* cocov = static_cast<const lcl_cocov_t*>(branch[1]);
  27289. const Type& v0 = static_cast<details::variable_node<Type>*>(branch[0])->ref();
  27290. const Type c0 = cocov->t0();
  27291. const Type c1 = cocov->t1();
  27292. const Type& v1 = cocov->t2();
  27293. const details::operator_type o0 = operation;
  27294. const details::operator_type o1 = expr_gen.get_operator(cocov->f0());
  27295. const details::operator_type o2 = expr_gen.get_operator(cocov->f1());
  27296. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  27297. binary_functor_t f1 = cocov->f0();
  27298. binary_functor_t f2 = cocov->f1();
  27299. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  27300. expression_node_ptr result = error_node();
  27301. const bool synthesis_result =
  27302. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  27303. (expr_gen, id(expr_gen, o0, o1, o2), v0, c0, c1, v1, result);
  27304. if (synthesis_result)
  27305. return result;
  27306. else if (!expr_gen.valid_operator(o0,f0))
  27307. return error_node();
  27308. exprtk_debug(("v0 o0 (c0 o1 (c1 o2 v1))\n"));
  27309. return node_type::allocate(*(expr_gen.node_allocator_), v0, c0, c1, v1, f0, f1, f2);
  27310. }
  27311. static inline std::string id(expression_generator<Type>& expr_gen,
  27312. const details::operator_type o0,
  27313. const details::operator_type o1,
  27314. const details::operator_type o2)
  27315. {
  27316. return details::build_string()
  27317. << "t" << expr_gen.to_str(o0)
  27318. << "(t" << expr_gen.to_str(o1)
  27319. << "(t" << expr_gen.to_str(o2)
  27320. << "t))";
  27321. }
  27322. };
  27323. struct synthesize_vovovov_expression2
  27324. {
  27325. typedef typename vovovov_t::type2 node_type;
  27326. typedef typename vovovov_t::sf4_type sf4_type;
  27327. typedef typename node_type::T0 T0;
  27328. typedef typename node_type::T1 T1;
  27329. typedef typename node_type::T2 T2;
  27330. typedef typename node_type::T3 T3;
  27331. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  27332. const details::operator_type& operation,
  27333. expression_node_ptr (&branch)[2])
  27334. {
  27335. // v0 o0 ((v1 o1 v2) o2 v3)
  27336. typedef typename synthesize_vovov_expression0::node_type lcl_vovov_t;
  27337. const lcl_vovov_t* vovov = static_cast<const lcl_vovov_t*>(branch[1]);
  27338. const Type& v0 = static_cast<details::variable_node<Type>*>(branch[0])->ref();
  27339. const Type& v1 = vovov->t0();
  27340. const Type& v2 = vovov->t1();
  27341. const Type& v3 = vovov->t2();
  27342. const details::operator_type o0 = operation;
  27343. const details::operator_type o1 = expr_gen.get_operator(vovov->f0());
  27344. const details::operator_type o2 = expr_gen.get_operator(vovov->f1());
  27345. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  27346. binary_functor_t f1 = vovov->f0();
  27347. binary_functor_t f2 = vovov->f1();
  27348. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  27349. expression_node_ptr result = error_node();
  27350. const bool synthesis_result =
  27351. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  27352. (expr_gen, id(expr_gen, o0, o1, o2), v0, v1, v2, v3, result);
  27353. if (synthesis_result)
  27354. return result;
  27355. else if (!expr_gen.valid_operator(o0,f0))
  27356. return error_node();
  27357. exprtk_debug(("v0 o0 ((v1 o1 v2) o2 v3)\n"));
  27358. return node_type::allocate(*(expr_gen.node_allocator_), v0, v1, v2, v3, f0, f1, f2);
  27359. }
  27360. static inline std::string id(expression_generator<Type>& expr_gen,
  27361. const details::operator_type o0,
  27362. const details::operator_type o1,
  27363. const details::operator_type o2)
  27364. {
  27365. return details::build_string()
  27366. << "t" << expr_gen.to_str(o0)
  27367. << "((t" << expr_gen.to_str(o1)
  27368. << "t)" << expr_gen.to_str(o2)
  27369. << "t)";
  27370. }
  27371. };
  27372. struct synthesize_vovovoc_expression2
  27373. {
  27374. typedef typename vovovoc_t::type2 node_type;
  27375. typedef typename vovovoc_t::sf4_type sf4_type;
  27376. typedef typename node_type::T0 T0;
  27377. typedef typename node_type::T1 T1;
  27378. typedef typename node_type::T2 T2;
  27379. typedef typename node_type::T3 T3;
  27380. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  27381. const details::operator_type& operation,
  27382. expression_node_ptr (&branch)[2])
  27383. {
  27384. // v0 o0 ((v1 o1 v2) o2 c)
  27385. typedef typename synthesize_vovoc_expression0::node_type lcl_vovoc_t;
  27386. const lcl_vovoc_t* vovoc = static_cast<const lcl_vovoc_t*>(branch[1]);
  27387. const Type& v0 = static_cast<details::variable_node<Type>*>(branch[0])->ref();
  27388. const Type& v1 = vovoc->t0();
  27389. const Type& v2 = vovoc->t1();
  27390. const Type c = vovoc->t2();
  27391. const details::operator_type o0 = operation;
  27392. const details::operator_type o1 = expr_gen.get_operator(vovoc->f0());
  27393. const details::operator_type o2 = expr_gen.get_operator(vovoc->f1());
  27394. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  27395. binary_functor_t f1 = vovoc->f0();
  27396. binary_functor_t f2 = vovoc->f1();
  27397. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  27398. expression_node_ptr result = error_node();
  27399. const bool synthesis_result =
  27400. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  27401. (expr_gen, id(expr_gen, o0, o1, o2), v0, v1, v2, c, result);
  27402. if (synthesis_result)
  27403. return result;
  27404. else if (!expr_gen.valid_operator(o0,f0))
  27405. return error_node();
  27406. exprtk_debug(("v0 o0 ((v1 o1 v2) o2 c)\n"));
  27407. return node_type::allocate(*(expr_gen.node_allocator_), v0, v1, v2, c, f0, f1, f2);
  27408. }
  27409. static inline std::string id(expression_generator<Type>& expr_gen,
  27410. const details::operator_type o0,
  27411. const details::operator_type o1,
  27412. const details::operator_type o2)
  27413. {
  27414. return details::build_string()
  27415. << "t" << expr_gen.to_str(o0)
  27416. << "((t" << expr_gen.to_str(o1)
  27417. << "t)" << expr_gen.to_str(o2)
  27418. << "t)";
  27419. }
  27420. };
  27421. struct synthesize_vovocov_expression2
  27422. {
  27423. typedef typename vovocov_t::type2 node_type;
  27424. typedef typename vovocov_t::sf4_type sf4_type;
  27425. typedef typename node_type::T0 T0;
  27426. typedef typename node_type::T1 T1;
  27427. typedef typename node_type::T2 T2;
  27428. typedef typename node_type::T3 T3;
  27429. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  27430. const details::operator_type& operation,
  27431. expression_node_ptr (&branch)[2])
  27432. {
  27433. // v0 o0 ((v1 o1 c) o2 v2)
  27434. typedef typename synthesize_vocov_expression0::node_type lcl_vocov_t;
  27435. const lcl_vocov_t* vocov = static_cast<const lcl_vocov_t*>(branch[1]);
  27436. const Type& v0 = static_cast<details::variable_node<Type>*>(branch[0])->ref();
  27437. const Type& v1 = vocov->t0();
  27438. const Type c = vocov->t1();
  27439. const Type& v2 = vocov->t2();
  27440. const details::operator_type o0 = operation;
  27441. const details::operator_type o1 = expr_gen.get_operator(vocov->f0());
  27442. const details::operator_type o2 = expr_gen.get_operator(vocov->f1());
  27443. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  27444. binary_functor_t f1 = vocov->f0();
  27445. binary_functor_t f2 = vocov->f1();
  27446. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  27447. expression_node_ptr result = error_node();
  27448. const bool synthesis_result =
  27449. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  27450. (expr_gen, id(expr_gen, o0, o1, o2), v0, v1, c, v2, result);
  27451. if (synthesis_result)
  27452. return result;
  27453. else if (!expr_gen.valid_operator(o0,f0))
  27454. return error_node();
  27455. exprtk_debug(("v0 o0 ((v1 o1 c) o2 v2)\n"));
  27456. return node_type::allocate(*(expr_gen.node_allocator_), v0, v1, c, v2, f0, f1, f2);
  27457. }
  27458. static inline std::string id(expression_generator<Type>& expr_gen,
  27459. const details::operator_type o0,
  27460. const details::operator_type o1,
  27461. const details::operator_type o2)
  27462. {
  27463. return details::build_string()
  27464. << "t" << expr_gen.to_str(o0)
  27465. << "((t" << expr_gen.to_str(o1)
  27466. << "t)" << expr_gen.to_str(o2)
  27467. << "t)";
  27468. }
  27469. };
  27470. struct synthesize_vocovov_expression2
  27471. {
  27472. typedef typename vocovov_t::type2 node_type;
  27473. typedef typename vocovov_t::sf4_type sf4_type;
  27474. typedef typename node_type::T0 T0;
  27475. typedef typename node_type::T1 T1;
  27476. typedef typename node_type::T2 T2;
  27477. typedef typename node_type::T3 T3;
  27478. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  27479. const details::operator_type& operation,
  27480. expression_node_ptr (&branch)[2])
  27481. {
  27482. // v0 o0 ((c o1 v1) o2 v2)
  27483. typedef typename synthesize_covov_expression0::node_type lcl_covov_t;
  27484. const lcl_covov_t* covov = static_cast<const lcl_covov_t*>(branch[1]);
  27485. const Type& v0 = static_cast<details::variable_node<Type>*>(branch[0])->ref();
  27486. const Type c = covov->t0();
  27487. const Type& v1 = covov->t1();
  27488. const Type& v2 = covov->t2();
  27489. const details::operator_type o0 = operation;
  27490. const details::operator_type o1 = expr_gen.get_operator(covov->f0());
  27491. const details::operator_type o2 = expr_gen.get_operator(covov->f1());
  27492. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  27493. binary_functor_t f1 = covov->f0();
  27494. binary_functor_t f2 = covov->f1();
  27495. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  27496. expression_node_ptr result = error_node();
  27497. const bool synthesis_result =
  27498. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  27499. (expr_gen, id(expr_gen, o0, o1, o2), v0, c, v1, v2, result);
  27500. if (synthesis_result)
  27501. return result;
  27502. else if (!expr_gen.valid_operator(o0,f0))
  27503. return error_node();
  27504. exprtk_debug(("v0 o0 ((c o1 v1) o2 v2)\n"));
  27505. return node_type::allocate(*(expr_gen.node_allocator_), v0, c, v1, v2, f0, f1, f2);
  27506. }
  27507. static inline std::string id(expression_generator<Type>& expr_gen,
  27508. const details::operator_type o0,
  27509. const details::operator_type o1,
  27510. const details::operator_type o2)
  27511. {
  27512. return details::build_string()
  27513. << "t" << expr_gen.to_str(o0)
  27514. << "((t" << expr_gen.to_str(o1)
  27515. << "t)" << expr_gen.to_str(o2)
  27516. << "t)";
  27517. }
  27518. };
  27519. struct synthesize_covovov_expression2
  27520. {
  27521. typedef typename covovov_t::type2 node_type;
  27522. typedef typename covovov_t::sf4_type sf4_type;
  27523. typedef typename node_type::T0 T0;
  27524. typedef typename node_type::T1 T1;
  27525. typedef typename node_type::T2 T2;
  27526. typedef typename node_type::T3 T3;
  27527. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  27528. const details::operator_type& operation,
  27529. expression_node_ptr (&branch)[2])
  27530. {
  27531. // c o0 ((v1 o1 v2) o2 v3)
  27532. typedef typename synthesize_vovov_expression0::node_type lcl_vovov_t;
  27533. const lcl_vovov_t* vovov = static_cast<const lcl_vovov_t*>(branch[1]);
  27534. const Type c = static_cast<details::literal_node<Type>*>(branch[0])->value();
  27535. const Type& v0 = vovov->t0();
  27536. const Type& v1 = vovov->t1();
  27537. const Type& v2 = vovov->t2();
  27538. const details::operator_type o0 = operation;
  27539. const details::operator_type o1 = expr_gen.get_operator(vovov->f0());
  27540. const details::operator_type o2 = expr_gen.get_operator(vovov->f1());
  27541. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  27542. binary_functor_t f1 = vovov->f0();
  27543. binary_functor_t f2 = vovov->f1();
  27544. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  27545. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  27546. expression_node_ptr result = error_node();
  27547. const bool synthesis_result =
  27548. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  27549. (expr_gen, id(expr_gen, o0, o1, o2), c, v0, v1, v2, result);
  27550. if (synthesis_result)
  27551. return result;
  27552. else if (!expr_gen.valid_operator(o0,f0))
  27553. return error_node();
  27554. exprtk_debug(("c o0 ((v1 o1 v2) o2 v3)\n"));
  27555. return node_type::allocate(*(expr_gen.node_allocator_), c, v0, v1, v2, f0, f1, f2);
  27556. }
  27557. static inline std::string id(expression_generator<Type>& expr_gen,
  27558. const details::operator_type o0,
  27559. const details::operator_type o1,
  27560. const details::operator_type o2)
  27561. {
  27562. return details::build_string()
  27563. << "t" << expr_gen.to_str(o0)
  27564. << "((t" << expr_gen.to_str(o1)
  27565. << "t)" << expr_gen.to_str(o2)
  27566. << "t)";
  27567. }
  27568. };
  27569. struct synthesize_covocov_expression2
  27570. {
  27571. typedef typename covocov_t::type2 node_type;
  27572. typedef typename covocov_t::sf4_type sf4_type;
  27573. typedef typename node_type::T0 T0;
  27574. typedef typename node_type::T1 T1;
  27575. typedef typename node_type::T2 T2;
  27576. typedef typename node_type::T3 T3;
  27577. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  27578. const details::operator_type& operation,
  27579. expression_node_ptr (&branch)[2])
  27580. {
  27581. // c0 o0 ((v0 o1 c1) o2 v1)
  27582. typedef typename synthesize_vocov_expression0::node_type lcl_vocov_t;
  27583. const lcl_vocov_t* vocov = static_cast<const lcl_vocov_t*>(branch[1]);
  27584. const Type c0 = static_cast<details::literal_node<Type>*>(branch[0])->value();
  27585. const Type& v0 = vocov->t0();
  27586. const Type c1 = vocov->t1();
  27587. const Type& v1 = vocov->t2();
  27588. const details::operator_type o0 = operation;
  27589. const details::operator_type o1 = expr_gen.get_operator(vocov->f0());
  27590. const details::operator_type o2 = expr_gen.get_operator(vocov->f1());
  27591. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  27592. binary_functor_t f1 = vocov->f0();
  27593. binary_functor_t f2 = vocov->f1();
  27594. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  27595. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  27596. expression_node_ptr result = error_node();
  27597. const bool synthesis_result =
  27598. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  27599. (expr_gen, id(expr_gen, o0, o1, o2), c0, v0, c1, v1, result);
  27600. if (synthesis_result)
  27601. return result;
  27602. else if (!expr_gen.valid_operator(o0,f0))
  27603. return error_node();
  27604. exprtk_debug(("c0 o0 ((v0 o1 c1) o2 v1)\n"));
  27605. return node_type::allocate(*(expr_gen.node_allocator_), c0, v0, c1, v1, f0, f1, f2);
  27606. }
  27607. static inline std::string id(expression_generator<Type>& expr_gen,
  27608. const details::operator_type o0,
  27609. const details::operator_type o1,
  27610. const details::operator_type o2)
  27611. {
  27612. return details::build_string()
  27613. << "t" << expr_gen.to_str(o0)
  27614. << "((t" << expr_gen.to_str(o1)
  27615. << "t)" << expr_gen.to_str(o2)
  27616. << "t)";
  27617. }
  27618. };
  27619. struct synthesize_vocovoc_expression2
  27620. {
  27621. typedef typename vocovoc_t::type2 node_type;
  27622. typedef typename vocovoc_t::sf4_type sf4_type;
  27623. typedef typename node_type::T0 T0;
  27624. typedef typename node_type::T1 T1;
  27625. typedef typename node_type::T2 T2;
  27626. typedef typename node_type::T3 T3;
  27627. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  27628. const details::operator_type& operation,
  27629. expression_node_ptr (&branch)[2])
  27630. {
  27631. // v0 o0 ((c0 o1 v1) o2 c1)
  27632. typedef typename synthesize_covoc_expression0::node_type lcl_covoc_t;
  27633. const lcl_covoc_t* covoc = static_cast<const lcl_covoc_t*>(branch[1]);
  27634. const Type& v0 = static_cast<details::variable_node<Type>*>(branch[0])->ref();
  27635. const Type c0 = covoc->t0();
  27636. const Type& v1 = covoc->t1();
  27637. const Type c1 = covoc->t2();
  27638. const details::operator_type o0 = operation;
  27639. const details::operator_type o1 = expr_gen.get_operator(covoc->f0());
  27640. const details::operator_type o2 = expr_gen.get_operator(covoc->f1());
  27641. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  27642. binary_functor_t f1 = covoc->f0();
  27643. binary_functor_t f2 = covoc->f1();
  27644. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  27645. expression_node_ptr result = error_node();
  27646. const bool synthesis_result =
  27647. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  27648. (expr_gen, id(expr_gen, o0, o1, o2), v0, c0, v1, c1, result);
  27649. if (synthesis_result)
  27650. return result;
  27651. else if (!expr_gen.valid_operator(o0,f0))
  27652. return error_node();
  27653. exprtk_debug(("v0 o0 ((c0 o1 v1) o2 c1)\n"));
  27654. return node_type::allocate(*(expr_gen.node_allocator_), v0, c0, v1, c1, f0, f1, f2);
  27655. }
  27656. static inline std::string id(expression_generator<Type>& expr_gen,
  27657. const details::operator_type o0,
  27658. const details::operator_type o1,
  27659. const details::operator_type o2)
  27660. {
  27661. return details::build_string()
  27662. << "t" << expr_gen.to_str(o0)
  27663. << "((t" << expr_gen.to_str(o1)
  27664. << "t)" << expr_gen.to_str(o2)
  27665. << "t)";
  27666. }
  27667. };
  27668. struct synthesize_covovoc_expression2
  27669. {
  27670. typedef typename covovoc_t::type2 node_type;
  27671. typedef typename covovoc_t::sf4_type sf4_type;
  27672. typedef typename node_type::T0 T0;
  27673. typedef typename node_type::T1 T1;
  27674. typedef typename node_type::T2 T2;
  27675. typedef typename node_type::T3 T3;
  27676. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  27677. const details::operator_type& operation,
  27678. expression_node_ptr (&branch)[2])
  27679. {
  27680. // c0 o0 ((v0 o1 v1) o2 c1)
  27681. typedef typename synthesize_vovoc_expression0::node_type lcl_vovoc_t;
  27682. const lcl_vovoc_t* vovoc = static_cast<const lcl_vovoc_t*>(branch[1]);
  27683. const Type c0 = static_cast<details::literal_node<Type>*>(branch[0])->value();
  27684. const Type& v0 = vovoc->t0();
  27685. const Type& v1 = vovoc->t1();
  27686. const Type c1 = vovoc->t2();
  27687. const details::operator_type o0 = operation;
  27688. const details::operator_type o1 = expr_gen.get_operator(vovoc->f0());
  27689. const details::operator_type o2 = expr_gen.get_operator(vovoc->f1());
  27690. binary_functor_t f0 = reinterpret_cast<binary_functor_t>(0);
  27691. binary_functor_t f1 = vovoc->f0();
  27692. binary_functor_t f2 = vovoc->f1();
  27693. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  27694. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  27695. expression_node_ptr result = error_node();
  27696. const bool synthesis_result =
  27697. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  27698. (expr_gen, id(expr_gen, o0, o1, o2), c0, v0, v1, c1, result);
  27699. if (synthesis_result)
  27700. return result;
  27701. else if (!expr_gen.valid_operator(o0,f0))
  27702. return error_node();
  27703. exprtk_debug(("c0 o0 ((v0 o1 v1) o2 c1)\n"));
  27704. return node_type::allocate(*(expr_gen.node_allocator_), c0, v0, v1, c1, f0, f1, f2);
  27705. }
  27706. static inline std::string id(expression_generator<Type>& expr_gen,
  27707. const details::operator_type o0,
  27708. const details::operator_type o1,
  27709. const details::operator_type o2)
  27710. {
  27711. return details::build_string()
  27712. << "t" << expr_gen.to_str(o0)
  27713. << "((t" << expr_gen.to_str(o1)
  27714. << "t)" << expr_gen.to_str(o2)
  27715. << "t)";
  27716. }
  27717. };
  27718. struct synthesize_vococov_expression2
  27719. {
  27720. typedef typename vococov_t::type2 node_type;
  27721. static inline expression_node_ptr process(expression_generator<Type>&, const details::operator_type&, expression_node_ptr (&)[2])
  27722. {
  27723. // v0 o0 ((c0 o1 c1) o2 v1) - Not possible
  27724. exprtk_debug(("v0 o0 ((c0 o1 c1) o2 v1) - Not possible\n"));
  27725. return error_node();
  27726. }
  27727. static inline std::string id(expression_generator<Type>&,
  27728. const details::operator_type, const details::operator_type, const details::operator_type)
  27729. {
  27730. return "INVALID";
  27731. }
  27732. };
  27733. struct synthesize_vovovov_expression3
  27734. {
  27735. typedef typename vovovov_t::type3 node_type;
  27736. typedef typename vovovov_t::sf4_type sf4_type;
  27737. typedef typename node_type::T0 T0;
  27738. typedef typename node_type::T1 T1;
  27739. typedef typename node_type::T2 T2;
  27740. typedef typename node_type::T3 T3;
  27741. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  27742. const details::operator_type& operation,
  27743. expression_node_ptr (&branch)[2])
  27744. {
  27745. // ((v0 o0 v1) o1 v2) o2 v3
  27746. typedef typename synthesize_vovov_expression0::node_type lcl_vovov_t;
  27747. const lcl_vovov_t* vovov = static_cast<const lcl_vovov_t*>(branch[0]);
  27748. const Type& v0 = vovov->t0();
  27749. const Type& v1 = vovov->t1();
  27750. const Type& v2 = vovov->t2();
  27751. const Type& v3 = static_cast<details::variable_node<Type>*>(branch[1])->ref();
  27752. const details::operator_type o0 = expr_gen.get_operator(vovov->f0());
  27753. const details::operator_type o1 = expr_gen.get_operator(vovov->f1());
  27754. const details::operator_type o2 = operation;
  27755. binary_functor_t f0 = vovov->f0();
  27756. binary_functor_t f1 = vovov->f1();
  27757. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  27758. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  27759. expression_node_ptr result = error_node();
  27760. const bool synthesis_result =
  27761. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  27762. (expr_gen, id(expr_gen, o0, o1, o2), v0, v1, v2, v3, result);
  27763. if (synthesis_result)
  27764. return result;
  27765. else if (!expr_gen.valid_operator(o2,f2))
  27766. return error_node();
  27767. exprtk_debug(("((v0 o0 v1) o1 v2) o2 v3\n"));
  27768. return node_type::allocate(*(expr_gen.node_allocator_), v0, v1, v2, v3, f0, f1, f2);
  27769. }
  27770. static inline std::string id(expression_generator<Type>& expr_gen,
  27771. const details::operator_type o0,
  27772. const details::operator_type o1,
  27773. const details::operator_type o2)
  27774. {
  27775. return details::build_string()
  27776. << "((t" << expr_gen.to_str(o0)
  27777. << "t)" << expr_gen.to_str(o1)
  27778. << "t)" << expr_gen.to_str(o2)
  27779. << "t";
  27780. }
  27781. };
  27782. struct synthesize_vovovoc_expression3
  27783. {
  27784. typedef typename vovovoc_t::type3 node_type;
  27785. typedef typename vovovoc_t::sf4_type sf4_type;
  27786. typedef typename node_type::T0 T0;
  27787. typedef typename node_type::T1 T1;
  27788. typedef typename node_type::T2 T2;
  27789. typedef typename node_type::T3 T3;
  27790. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  27791. const details::operator_type& operation,
  27792. expression_node_ptr (&branch)[2])
  27793. {
  27794. // ((v0 o0 v1) o1 v2) o2 c
  27795. typedef typename synthesize_vovov_expression0::node_type lcl_vovov_t;
  27796. const lcl_vovov_t* vovov = static_cast<const lcl_vovov_t*>(branch[0]);
  27797. const Type& v0 = vovov->t0();
  27798. const Type& v1 = vovov->t1();
  27799. const Type& v2 = vovov->t2();
  27800. const Type c = static_cast<details::literal_node<Type>*>(branch[1])->value();
  27801. const details::operator_type o0 = expr_gen.get_operator(vovov->f0());
  27802. const details::operator_type o1 = expr_gen.get_operator(vovov->f1());
  27803. const details::operator_type o2 = operation;
  27804. binary_functor_t f0 = vovov->f0();
  27805. binary_functor_t f1 = vovov->f1();
  27806. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  27807. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  27808. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  27809. expression_node_ptr result = error_node();
  27810. const bool synthesis_result =
  27811. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  27812. (expr_gen, id(expr_gen, o0, o1, o2), v0, v1, v2, c, result);
  27813. if (synthesis_result)
  27814. return result;
  27815. else if (!expr_gen.valid_operator(o2,f2))
  27816. return error_node();
  27817. exprtk_debug(("((v0 o0 v1) o1 v2) o2 c\n"));
  27818. return node_type::allocate(*(expr_gen.node_allocator_), v0, v1, v2, c, f0, f1, f2);
  27819. }
  27820. static inline std::string id(expression_generator<Type>& expr_gen,
  27821. const details::operator_type o0,
  27822. const details::operator_type o1,
  27823. const details::operator_type o2)
  27824. {
  27825. return details::build_string()
  27826. << "((t" << expr_gen.to_str(o0)
  27827. << "t)" << expr_gen.to_str(o1)
  27828. << "t)" << expr_gen.to_str(o2)
  27829. << "t";
  27830. }
  27831. };
  27832. struct synthesize_vovocov_expression3
  27833. {
  27834. typedef typename vovocov_t::type3 node_type;
  27835. typedef typename vovocov_t::sf4_type sf4_type;
  27836. typedef typename node_type::T0 T0;
  27837. typedef typename node_type::T1 T1;
  27838. typedef typename node_type::T2 T2;
  27839. typedef typename node_type::T3 T3;
  27840. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  27841. const details::operator_type& operation,
  27842. expression_node_ptr (&branch)[2])
  27843. {
  27844. // ((v0 o0 v1) o1 c) o2 v2
  27845. typedef typename synthesize_vovoc_expression0::node_type lcl_vovoc_t;
  27846. const lcl_vovoc_t* vovoc = static_cast<const lcl_vovoc_t*>(branch[0]);
  27847. const Type& v0 = vovoc->t0();
  27848. const Type& v1 = vovoc->t1();
  27849. const Type c = vovoc->t2();
  27850. const Type& v2 = static_cast<details::variable_node<Type>*>(branch[1])->ref();
  27851. const details::operator_type o0 = expr_gen.get_operator(vovoc->f0());
  27852. const details::operator_type o1 = expr_gen.get_operator(vovoc->f1());
  27853. const details::operator_type o2 = operation;
  27854. binary_functor_t f0 = vovoc->f0();
  27855. binary_functor_t f1 = vovoc->f1();
  27856. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  27857. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  27858. expression_node_ptr result = error_node();
  27859. const bool synthesis_result =
  27860. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  27861. (expr_gen, id(expr_gen, o0, o1, o2), v0, v1, c, v2, result);
  27862. if (synthesis_result)
  27863. return result;
  27864. else if (!expr_gen.valid_operator(o2,f2))
  27865. return error_node();
  27866. exprtk_debug(("((v0 o0 v1) o1 c) o2 v2\n"));
  27867. return node_type::allocate(*(expr_gen.node_allocator_), v0, v1, c, v2, f0, f1, f2);
  27868. }
  27869. static inline std::string id(expression_generator<Type>& expr_gen,
  27870. const details::operator_type o0,
  27871. const details::operator_type o1,
  27872. const details::operator_type o2)
  27873. {
  27874. return details::build_string()
  27875. << "((t" << expr_gen.to_str(o0)
  27876. << "t)" << expr_gen.to_str(o1)
  27877. << "t)" << expr_gen.to_str(o2)
  27878. << "t";
  27879. }
  27880. };
  27881. struct synthesize_vocovov_expression3
  27882. {
  27883. typedef typename vocovov_t::type3 node_type;
  27884. typedef typename vocovov_t::sf4_type sf4_type;
  27885. typedef typename node_type::T0 T0;
  27886. typedef typename node_type::T1 T1;
  27887. typedef typename node_type::T2 T2;
  27888. typedef typename node_type::T3 T3;
  27889. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  27890. const details::operator_type& operation,
  27891. expression_node_ptr (&branch)[2])
  27892. {
  27893. // ((v0 o0 c) o1 v1) o2 v2
  27894. typedef typename synthesize_vocov_expression0::node_type lcl_vocov_t;
  27895. const lcl_vocov_t* vocov = static_cast<const lcl_vocov_t*>(branch[0]);
  27896. const Type& v0 = vocov->t0();
  27897. const Type c = vocov->t1();
  27898. const Type& v1 = vocov->t2();
  27899. const Type& v2 = static_cast<details::variable_node<Type>*>(branch[1])->ref();
  27900. const details::operator_type o0 = expr_gen.get_operator(vocov->f0());
  27901. const details::operator_type o1 = expr_gen.get_operator(vocov->f1());
  27902. const details::operator_type o2 = operation;
  27903. binary_functor_t f0 = vocov->f0();
  27904. binary_functor_t f1 = vocov->f1();
  27905. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  27906. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  27907. expression_node_ptr result = error_node();
  27908. const bool synthesis_result =
  27909. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  27910. (expr_gen, id(expr_gen, o0, o1, o2), v0, c, v1, v2, result);
  27911. if (synthesis_result)
  27912. return result;
  27913. else if (!expr_gen.valid_operator(o2,f2))
  27914. return error_node();
  27915. exprtk_debug(("((v0 o0 c) o1 v1) o2 v2\n"));
  27916. return node_type::allocate(*(expr_gen.node_allocator_), v0, c, v1, v2, f0, f1, f2);
  27917. }
  27918. static inline std::string id(expression_generator<Type>& expr_gen,
  27919. const details::operator_type o0,
  27920. const details::operator_type o1,
  27921. const details::operator_type o2)
  27922. {
  27923. return details::build_string()
  27924. << "((t" << expr_gen.to_str(o0)
  27925. << "t)" << expr_gen.to_str(o1)
  27926. << "t)" << expr_gen.to_str(o2)
  27927. << "t";
  27928. }
  27929. };
  27930. struct synthesize_covovov_expression3
  27931. {
  27932. typedef typename covovov_t::type3 node_type;
  27933. typedef typename covovov_t::sf4_type sf4_type;
  27934. typedef typename node_type::T0 T0;
  27935. typedef typename node_type::T1 T1;
  27936. typedef typename node_type::T2 T2;
  27937. typedef typename node_type::T3 T3;
  27938. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  27939. const details::operator_type& operation,
  27940. expression_node_ptr (&branch)[2])
  27941. {
  27942. // ((c o0 v0) o1 v1) o2 v2
  27943. typedef typename synthesize_covov_expression0::node_type lcl_covov_t;
  27944. const lcl_covov_t* covov = static_cast<const lcl_covov_t*>(branch[0]);
  27945. const Type c = covov->t0();
  27946. const Type& v0 = covov->t1();
  27947. const Type& v1 = covov->t2();
  27948. const Type& v2 = static_cast<details::variable_node<Type>*>(branch[1])->ref();
  27949. const details::operator_type o0 = expr_gen.get_operator(covov->f0());
  27950. const details::operator_type o1 = expr_gen.get_operator(covov->f1());
  27951. const details::operator_type o2 = operation;
  27952. binary_functor_t f0 = covov->f0();
  27953. binary_functor_t f1 = covov->f1();
  27954. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  27955. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  27956. expression_node_ptr result = error_node();
  27957. const bool synthesis_result =
  27958. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  27959. (expr_gen, id(expr_gen, o0, o1, o2), c, v0, v1, v2, result);
  27960. if (synthesis_result)
  27961. return result;
  27962. else if (!expr_gen.valid_operator(o2,f2))
  27963. return error_node();
  27964. exprtk_debug(("((c o0 v0) o1 v1) o2 v2\n"));
  27965. return node_type::allocate(*(expr_gen.node_allocator_), c, v0, v1, v2, f0, f1, f2);
  27966. }
  27967. static inline std::string id(expression_generator<Type>& expr_gen,
  27968. const details::operator_type o0,
  27969. const details::operator_type o1,
  27970. const details::operator_type o2)
  27971. {
  27972. return details::build_string()
  27973. << "((t" << expr_gen.to_str(o0)
  27974. << "t)" << expr_gen.to_str(o1)
  27975. << "t)" << expr_gen.to_str(o2)
  27976. << "t";
  27977. }
  27978. };
  27979. struct synthesize_covocov_expression3
  27980. {
  27981. typedef typename covocov_t::type3 node_type;
  27982. typedef typename covocov_t::sf4_type sf4_type;
  27983. typedef typename node_type::T0 T0;
  27984. typedef typename node_type::T1 T1;
  27985. typedef typename node_type::T2 T2;
  27986. typedef typename node_type::T3 T3;
  27987. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  27988. const details::operator_type& operation,
  27989. expression_node_ptr (&branch)[2])
  27990. {
  27991. // ((c0 o0 v0) o1 c1) o2 v1
  27992. typedef typename synthesize_covoc_expression0::node_type lcl_covoc_t;
  27993. const lcl_covoc_t* covoc = static_cast<const lcl_covoc_t*>(branch[0]);
  27994. const Type c0 = covoc->t0();
  27995. const Type& v0 = covoc->t1();
  27996. const Type c1 = covoc->t2();
  27997. const Type& v1 = static_cast<details::variable_node<Type>*>(branch[1])->ref();
  27998. const details::operator_type o0 = expr_gen.get_operator(covoc->f0());
  27999. const details::operator_type o1 = expr_gen.get_operator(covoc->f1());
  28000. const details::operator_type o2 = operation;
  28001. binary_functor_t f0 = covoc->f0();
  28002. binary_functor_t f1 = covoc->f1();
  28003. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  28004. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  28005. expression_node_ptr result = error_node();
  28006. const bool synthesis_result =
  28007. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  28008. (expr_gen, id(expr_gen, o0, o1, o2), c0, v0, c1, v1, result);
  28009. if (synthesis_result)
  28010. return result;
  28011. else if (!expr_gen.valid_operator(o2,f2))
  28012. return error_node();
  28013. exprtk_debug(("((c0 o0 v0) o1 c1) o2 v1\n"));
  28014. return node_type::allocate(*(expr_gen.node_allocator_), c0, v0, c1, v1, f0, f1, f2);
  28015. }
  28016. static inline std::string id(expression_generator<Type>& expr_gen,
  28017. const details::operator_type o0,
  28018. const details::operator_type o1,
  28019. const details::operator_type o2)
  28020. {
  28021. return details::build_string()
  28022. << "((t" << expr_gen.to_str(o0)
  28023. << "t)" << expr_gen.to_str(o1)
  28024. << "t)" << expr_gen.to_str(o2)
  28025. << "t";
  28026. }
  28027. };
  28028. struct synthesize_vocovoc_expression3
  28029. {
  28030. typedef typename vocovoc_t::type3 node_type;
  28031. typedef typename vocovoc_t::sf4_type sf4_type;
  28032. typedef typename node_type::T0 T0;
  28033. typedef typename node_type::T1 T1;
  28034. typedef typename node_type::T2 T2;
  28035. typedef typename node_type::T3 T3;
  28036. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  28037. const details::operator_type& operation,
  28038. expression_node_ptr (&branch)[2])
  28039. {
  28040. // ((v0 o0 c0) o1 v1) o2 c1
  28041. typedef typename synthesize_vocov_expression0::node_type lcl_vocov_t;
  28042. const lcl_vocov_t* vocov = static_cast<const lcl_vocov_t*>(branch[0]);
  28043. const Type& v0 = vocov->t0();
  28044. const Type c0 = vocov->t1();
  28045. const Type& v1 = vocov->t2();
  28046. const Type c1 = static_cast<details::literal_node<Type>*>(branch[1])->value();
  28047. const details::operator_type o0 = expr_gen.get_operator(vocov->f0());
  28048. const details::operator_type o1 = expr_gen.get_operator(vocov->f1());
  28049. const details::operator_type o2 = operation;
  28050. binary_functor_t f0 = vocov->f0();
  28051. binary_functor_t f1 = vocov->f1();
  28052. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  28053. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  28054. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  28055. expression_node_ptr result = error_node();
  28056. const bool synthesis_result =
  28057. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  28058. (expr_gen, id(expr_gen, o0, o1, o2), v0, c0, v1, c1, result);
  28059. if (synthesis_result)
  28060. return result;
  28061. else if (!expr_gen.valid_operator(o2,f2))
  28062. return error_node();
  28063. exprtk_debug(("((v0 o0 c0) o1 v1) o2 c1\n"));
  28064. return node_type::allocate(*(expr_gen.node_allocator_), v0, c0, v1, c1, f0, f1, f2);
  28065. }
  28066. static inline std::string id(expression_generator<Type>& expr_gen,
  28067. const details::operator_type o0,
  28068. const details::operator_type o1,
  28069. const details::operator_type o2)
  28070. {
  28071. return details::build_string()
  28072. << "((t" << expr_gen.to_str(o0)
  28073. << "t)" << expr_gen.to_str(o1)
  28074. << "t)" << expr_gen.to_str(o2)
  28075. << "t";
  28076. }
  28077. };
  28078. struct synthesize_covovoc_expression3
  28079. {
  28080. typedef typename covovoc_t::type3 node_type;
  28081. typedef typename covovoc_t::sf4_type sf4_type;
  28082. typedef typename node_type::T0 T0;
  28083. typedef typename node_type::T1 T1;
  28084. typedef typename node_type::T2 T2;
  28085. typedef typename node_type::T3 T3;
  28086. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  28087. const details::operator_type& operation,
  28088. expression_node_ptr (&branch)[2])
  28089. {
  28090. // ((c0 o0 v0) o1 v1) o2 c1
  28091. typedef typename synthesize_covov_expression0::node_type lcl_covov_t;
  28092. const lcl_covov_t* covov = static_cast<const lcl_covov_t*>(branch[0]);
  28093. const Type c0 = covov->t0();
  28094. const Type& v0 = covov->t1();
  28095. const Type& v1 = covov->t2();
  28096. const Type c1 = static_cast<details::literal_node<Type>*>(branch[1])->value();
  28097. const details::operator_type o0 = expr_gen.get_operator(covov->f0());
  28098. const details::operator_type o1 = expr_gen.get_operator(covov->f1());
  28099. const details::operator_type o2 = operation;
  28100. binary_functor_t f0 = covov->f0();
  28101. binary_functor_t f1 = covov->f1();
  28102. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  28103. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  28104. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  28105. expression_node_ptr result = error_node();
  28106. const bool synthesis_result =
  28107. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  28108. (expr_gen, id(expr_gen, o0, o1, o2), c0, v0, v1, c1, result);
  28109. if (synthesis_result)
  28110. return result;
  28111. else if (!expr_gen.valid_operator(o2,f2))
  28112. return error_node();
  28113. exprtk_debug(("((c0 o0 v0) o1 v1) o2 c1\n"));
  28114. return node_type::allocate(*(expr_gen.node_allocator_), c0, v0, v1, c1, f0, f1, f2);
  28115. }
  28116. static inline std::string id(expression_generator<Type>& expr_gen,
  28117. const details::operator_type o0,
  28118. const details::operator_type o1,
  28119. const details::operator_type o2)
  28120. {
  28121. return details::build_string()
  28122. << "((t" << expr_gen.to_str(o0)
  28123. << "t)" << expr_gen.to_str(o1)
  28124. << "t)" << expr_gen.to_str(o2)
  28125. << "t";
  28126. }
  28127. };
  28128. struct synthesize_vococov_expression3
  28129. {
  28130. typedef typename vococov_t::type3 node_type;
  28131. typedef typename vococov_t::sf4_type sf4_type;
  28132. typedef typename node_type::T0 T0;
  28133. typedef typename node_type::T1 T1;
  28134. typedef typename node_type::T2 T2;
  28135. typedef typename node_type::T3 T3;
  28136. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  28137. const details::operator_type& operation,
  28138. expression_node_ptr (&branch)[2])
  28139. {
  28140. // ((v0 o0 c0) o1 c1) o2 v1
  28141. typedef typename synthesize_vococ_expression0::node_type lcl_vococ_t;
  28142. const lcl_vococ_t* vococ = static_cast<const lcl_vococ_t*>(branch[0]);
  28143. const Type& v0 = vococ->t0();
  28144. const Type c0 = vococ->t1();
  28145. const Type c1 = vococ->t2();
  28146. const Type& v1 = static_cast<details::variable_node<Type>*>(branch[1])->ref();
  28147. const details::operator_type o0 = expr_gen.get_operator(vococ->f0());
  28148. const details::operator_type o1 = expr_gen.get_operator(vococ->f1());
  28149. const details::operator_type o2 = operation;
  28150. binary_functor_t f0 = vococ->f0();
  28151. binary_functor_t f1 = vococ->f1();
  28152. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  28153. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  28154. expression_node_ptr result = error_node();
  28155. const bool synthesis_result =
  28156. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  28157. (expr_gen, id(expr_gen, o0, o1, o2), v0, c0, c1, v1, result);
  28158. if (synthesis_result)
  28159. return result;
  28160. else if (!expr_gen.valid_operator(o2,f2))
  28161. return error_node();
  28162. exprtk_debug(("((v0 o0 c0) o1 c1) o2 v1\n"));
  28163. return node_type::allocate(*(expr_gen.node_allocator_), v0, c0, c1, v1, f0, f1, f2);
  28164. }
  28165. static inline std::string id(expression_generator<Type>& expr_gen,
  28166. const details::operator_type o0,
  28167. const details::operator_type o1,
  28168. const details::operator_type o2)
  28169. {
  28170. return details::build_string()
  28171. << "((t" << expr_gen.to_str(o0)
  28172. << "t)" << expr_gen.to_str(o1)
  28173. << "t)" << expr_gen.to_str(o2)
  28174. << "t";
  28175. }
  28176. };
  28177. struct synthesize_vovovov_expression4
  28178. {
  28179. typedef typename vovovov_t::type4 node_type;
  28180. typedef typename vovovov_t::sf4_type sf4_type;
  28181. typedef typename node_type::T0 T0;
  28182. typedef typename node_type::T1 T1;
  28183. typedef typename node_type::T2 T2;
  28184. typedef typename node_type::T3 T3;
  28185. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  28186. const details::operator_type& operation,
  28187. expression_node_ptr (&branch)[2])
  28188. {
  28189. // (v0 o0 (v1 o1 v2)) o2 v3
  28190. typedef typename synthesize_vovov_expression1::node_type lcl_vovov_t;
  28191. const lcl_vovov_t* vovov = static_cast<const lcl_vovov_t*>(branch[0]);
  28192. const Type& v0 = vovov->t0();
  28193. const Type& v1 = vovov->t1();
  28194. const Type& v2 = vovov->t2();
  28195. const Type& v3 = static_cast<details::variable_node<Type>*>(branch[1])->ref();
  28196. const details::operator_type o0 = expr_gen.get_operator(vovov->f0());
  28197. const details::operator_type o1 = expr_gen.get_operator(vovov->f1());
  28198. const details::operator_type o2 = operation;
  28199. binary_functor_t f0 = vovov->f0();
  28200. binary_functor_t f1 = vovov->f1();
  28201. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  28202. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  28203. expression_node_ptr result = error_node();
  28204. const bool synthesis_result =
  28205. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  28206. (expr_gen, id(expr_gen, o0, o1, o2), v0, v1, v2, v3, result);
  28207. if (synthesis_result)
  28208. return result;
  28209. else if (!expr_gen.valid_operator(o2,f2))
  28210. return error_node();
  28211. exprtk_debug(("(v0 o0 (v1 o1 v2)) o2 v3\n"));
  28212. return node_type::allocate(*(expr_gen.node_allocator_), v0, v1, v2, v3, f0, f1, f2);
  28213. }
  28214. static inline std::string id(expression_generator<Type>& expr_gen,
  28215. const details::operator_type o0,
  28216. const details::operator_type o1,
  28217. const details::operator_type o2)
  28218. {
  28219. return details::build_string()
  28220. << "(t" << expr_gen.to_str(o0)
  28221. << "(t" << expr_gen.to_str(o1)
  28222. << "t)" << expr_gen.to_str(o2)
  28223. << "t";
  28224. }
  28225. };
  28226. struct synthesize_vovovoc_expression4
  28227. {
  28228. typedef typename vovovoc_t::type4 node_type;
  28229. typedef typename vovovoc_t::sf4_type sf4_type;
  28230. typedef typename node_type::T0 T0;
  28231. typedef typename node_type::T1 T1;
  28232. typedef typename node_type::T2 T2;
  28233. typedef typename node_type::T3 T3;
  28234. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  28235. const details::operator_type& operation,
  28236. expression_node_ptr (&branch)[2])
  28237. {
  28238. // ((v0 o0 (v1 o1 v2)) o2 c)
  28239. typedef typename synthesize_vovov_expression1::node_type lcl_vovov_t;
  28240. const lcl_vovov_t* vovov = static_cast<const lcl_vovov_t*>(branch[0]);
  28241. const Type& v0 = vovov->t0();
  28242. const Type& v1 = vovov->t1();
  28243. const Type& v2 = vovov->t2();
  28244. const Type c = static_cast<details::literal_node<Type>*>(branch[1])->value();
  28245. const details::operator_type o0 = expr_gen.get_operator(vovov->f0());
  28246. const details::operator_type o1 = expr_gen.get_operator(vovov->f1());
  28247. const details::operator_type o2 = operation;
  28248. binary_functor_t f0 = vovov->f0();
  28249. binary_functor_t f1 = vovov->f1();
  28250. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  28251. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  28252. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  28253. expression_node_ptr result = error_node();
  28254. const bool synthesis_result =
  28255. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  28256. (expr_gen, id(expr_gen, o0, o1, o2), v0, v1, v2, c, result);
  28257. if (synthesis_result)
  28258. return result;
  28259. else if (!expr_gen.valid_operator(o2,f2))
  28260. return error_node();
  28261. exprtk_debug(("((v0 o0 (v1 o1 v2)) o2 c)\n"));
  28262. return node_type::allocate(*(expr_gen.node_allocator_), v0, v1, v2, c, f0, f1, f2);
  28263. }
  28264. static inline std::string id(expression_generator<Type>& expr_gen,
  28265. const details::operator_type o0,
  28266. const details::operator_type o1,
  28267. const details::operator_type o2)
  28268. {
  28269. return details::build_string()
  28270. << "(t" << expr_gen.to_str(o0)
  28271. << "(t" << expr_gen.to_str(o1)
  28272. << "t)" << expr_gen.to_str(o2)
  28273. << "t";
  28274. }
  28275. };
  28276. struct synthesize_vovocov_expression4
  28277. {
  28278. typedef typename vovocov_t::type4 node_type;
  28279. typedef typename vovocov_t::sf4_type sf4_type;
  28280. typedef typename node_type::T0 T0;
  28281. typedef typename node_type::T1 T1;
  28282. typedef typename node_type::T2 T2;
  28283. typedef typename node_type::T3 T3;
  28284. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  28285. const details::operator_type& operation,
  28286. expression_node_ptr (&branch)[2])
  28287. {
  28288. // ((v0 o0 (v1 o1 c)) o2 v1)
  28289. typedef typename synthesize_vovoc_expression1::node_type lcl_vovoc_t;
  28290. const lcl_vovoc_t* vovoc = static_cast<const lcl_vovoc_t*>(branch[0]);
  28291. const Type& v0 = vovoc->t0();
  28292. const Type& v1 = vovoc->t1();
  28293. const Type c = vovoc->t2();
  28294. const Type& v2 = static_cast<details::variable_node<Type>*>(branch[1])->ref();
  28295. const details::operator_type o0 = expr_gen.get_operator(vovoc->f0());
  28296. const details::operator_type o1 = expr_gen.get_operator(vovoc->f1());
  28297. const details::operator_type o2 = operation;
  28298. binary_functor_t f0 = vovoc->f0();
  28299. binary_functor_t f1 = vovoc->f1();
  28300. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  28301. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  28302. expression_node_ptr result = error_node();
  28303. const bool synthesis_result =
  28304. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  28305. (expr_gen, id(expr_gen, o0, o1, o2), v0, v1, c, v2, result);
  28306. if (synthesis_result)
  28307. return result;
  28308. else if (!expr_gen.valid_operator(o2,f2))
  28309. return error_node();
  28310. exprtk_debug(("((v0 o0 (v1 o1 c)) o2 v1)\n"));
  28311. return node_type::allocate(*(expr_gen.node_allocator_), v0, v1, c, v2, f0, f1, f2);
  28312. }
  28313. static inline std::string id(expression_generator<Type>& expr_gen,
  28314. const details::operator_type o0,
  28315. const details::operator_type o1,
  28316. const details::operator_type o2)
  28317. {
  28318. return details::build_string()
  28319. << "(t" << expr_gen.to_str(o0)
  28320. << "(t" << expr_gen.to_str(o1)
  28321. << "t)" << expr_gen.to_str(o2)
  28322. << "t";
  28323. }
  28324. };
  28325. struct synthesize_vocovov_expression4
  28326. {
  28327. typedef typename vocovov_t::type4 node_type;
  28328. typedef typename vocovov_t::sf4_type sf4_type;
  28329. typedef typename node_type::T0 T0;
  28330. typedef typename node_type::T1 T1;
  28331. typedef typename node_type::T2 T2;
  28332. typedef typename node_type::T3 T3;
  28333. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  28334. const details::operator_type& operation,
  28335. expression_node_ptr (&branch)[2])
  28336. {
  28337. // ((v0 o0 (c o1 v1)) o2 v2)
  28338. typedef typename synthesize_vocov_expression1::node_type lcl_vocov_t;
  28339. const lcl_vocov_t* vocov = static_cast<const lcl_vocov_t*>(branch[0]);
  28340. const Type& v0 = vocov->t0();
  28341. const Type c = vocov->t1();
  28342. const Type& v1 = vocov->t2();
  28343. const Type& v2 = static_cast<details::variable_node<Type>*>(branch[1])->ref();
  28344. const details::operator_type o0 = expr_gen.get_operator(vocov->f0());
  28345. const details::operator_type o1 = expr_gen.get_operator(vocov->f1());
  28346. const details::operator_type o2 = operation;
  28347. binary_functor_t f0 = vocov->f0();
  28348. binary_functor_t f1 = vocov->f1();
  28349. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  28350. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  28351. expression_node_ptr result = error_node();
  28352. const bool synthesis_result =
  28353. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  28354. (expr_gen, id(expr_gen, o0, o1, o2), v0, c, v1, v2, result);
  28355. if (synthesis_result)
  28356. return result;
  28357. else if (!expr_gen.valid_operator(o2,f2))
  28358. return error_node();
  28359. exprtk_debug(("((v0 o0 (c o1 v1)) o2 v2)\n"));
  28360. return node_type::allocate(*(expr_gen.node_allocator_), v0, c, v1, v2, f0, f1, f2);
  28361. }
  28362. static inline std::string id(expression_generator<Type>& expr_gen,
  28363. const details::operator_type o0,
  28364. const details::operator_type o1,
  28365. const details::operator_type o2)
  28366. {
  28367. return details::build_string()
  28368. << "(t" << expr_gen.to_str(o0)
  28369. << "(t" << expr_gen.to_str(o1)
  28370. << "t)" << expr_gen.to_str(o2)
  28371. << "t";
  28372. }
  28373. };
  28374. struct synthesize_covovov_expression4
  28375. {
  28376. typedef typename covovov_t::type4 node_type;
  28377. typedef typename covovov_t::sf4_type sf4_type;
  28378. typedef typename node_type::T0 T0;
  28379. typedef typename node_type::T1 T1;
  28380. typedef typename node_type::T2 T2;
  28381. typedef typename node_type::T3 T3;
  28382. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  28383. const details::operator_type& operation,
  28384. expression_node_ptr (&branch)[2])
  28385. {
  28386. // ((c o0 (v0 o1 v1)) o2 v2)
  28387. typedef typename synthesize_covov_expression1::node_type lcl_covov_t;
  28388. const lcl_covov_t* covov = static_cast<const lcl_covov_t*>(branch[0]);
  28389. const Type c = covov->t0();
  28390. const Type& v0 = covov->t1();
  28391. const Type& v1 = covov->t2();
  28392. const Type& v2 = static_cast<details::variable_node<Type>*>(branch[1])->ref();
  28393. const details::operator_type o0 = expr_gen.get_operator(covov->f0());
  28394. const details::operator_type o1 = expr_gen.get_operator(covov->f1());
  28395. const details::operator_type o2 = operation;
  28396. binary_functor_t f0 = covov->f0();
  28397. binary_functor_t f1 = covov->f1();
  28398. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  28399. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  28400. expression_node_ptr result = error_node();
  28401. const bool synthesis_result =
  28402. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  28403. (expr_gen, id(expr_gen, o0, o1, o2), c, v0, v1, v2, result);
  28404. if (synthesis_result)
  28405. return result;
  28406. else if (!expr_gen.valid_operator(o2,f2))
  28407. return error_node();
  28408. exprtk_debug(("((c o0 (v0 o1 v1)) o2 v2)\n"));
  28409. return node_type::allocate(*(expr_gen.node_allocator_), c, v0, v1, v2, f0, f1, f2);
  28410. }
  28411. static inline std::string id(expression_generator<Type>& expr_gen,
  28412. const details::operator_type o0,
  28413. const details::operator_type o1,
  28414. const details::operator_type o2)
  28415. {
  28416. return details::build_string()
  28417. << "(t" << expr_gen.to_str(o0)
  28418. << "(t" << expr_gen.to_str(o1)
  28419. << "t)" << expr_gen.to_str(o2)
  28420. << "t";
  28421. }
  28422. };
  28423. struct synthesize_covocov_expression4
  28424. {
  28425. typedef typename covocov_t::type4 node_type;
  28426. typedef typename covocov_t::sf4_type sf4_type;
  28427. typedef typename node_type::T0 T0;
  28428. typedef typename node_type::T1 T1;
  28429. typedef typename node_type::T2 T2;
  28430. typedef typename node_type::T3 T3;
  28431. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  28432. const details::operator_type& operation,
  28433. expression_node_ptr (&branch)[2])
  28434. {
  28435. // ((c0 o0 (v0 o1 c1)) o2 v1)
  28436. typedef typename synthesize_covoc_expression1::node_type lcl_covoc_t;
  28437. const lcl_covoc_t* covoc = static_cast<const lcl_covoc_t*>(branch[0]);
  28438. const Type c0 = covoc->t0();
  28439. const Type& v0 = covoc->t1();
  28440. const Type c1 = covoc->t2();
  28441. const Type& v1 = static_cast<details::variable_node<Type>*>(branch[1])->ref();
  28442. const details::operator_type o0 = expr_gen.get_operator(covoc->f0());
  28443. const details::operator_type o1 = expr_gen.get_operator(covoc->f1());
  28444. const details::operator_type o2 = operation;
  28445. binary_functor_t f0 = covoc->f0();
  28446. binary_functor_t f1 = covoc->f1();
  28447. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  28448. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  28449. expression_node_ptr result = error_node();
  28450. const bool synthesis_result =
  28451. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  28452. (expr_gen, id(expr_gen, o0, o1, o2), c0, v0, c1, v1, result);
  28453. if (synthesis_result)
  28454. return result;
  28455. else if (!expr_gen.valid_operator(o2,f2))
  28456. return error_node();
  28457. exprtk_debug(("((c0 o0 (v0 o1 c1)) o2 v1)\n"));
  28458. return node_type::allocate(*(expr_gen.node_allocator_), c0, v0, c1, v1, f0, f1, f2);
  28459. }
  28460. static inline std::string id(expression_generator<Type>& expr_gen,
  28461. const details::operator_type o0,
  28462. const details::operator_type o1,
  28463. const details::operator_type o2)
  28464. {
  28465. return details::build_string()
  28466. << "(t" << expr_gen.to_str(o0)
  28467. << "(t" << expr_gen.to_str(o1)
  28468. << "t)" << expr_gen.to_str(o2)
  28469. << "t";
  28470. }
  28471. };
  28472. struct synthesize_vocovoc_expression4
  28473. {
  28474. typedef typename vocovoc_t::type4 node_type;
  28475. typedef typename vocovoc_t::sf4_type sf4_type;
  28476. typedef typename node_type::T0 T0;
  28477. typedef typename node_type::T1 T1;
  28478. typedef typename node_type::T2 T2;
  28479. typedef typename node_type::T3 T3;
  28480. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  28481. const details::operator_type& operation,
  28482. expression_node_ptr (&branch)[2])
  28483. {
  28484. // ((v0 o0 (c0 o1 v1)) o2 c1)
  28485. typedef typename synthesize_vocov_expression1::node_type lcl_vocov_t;
  28486. const lcl_vocov_t* vocov = static_cast<const lcl_vocov_t*>(branch[0]);
  28487. const Type& v0 = vocov->t0();
  28488. const Type c0 = vocov->t1();
  28489. const Type& v1 = vocov->t2();
  28490. const Type c1 = static_cast<details::literal_node<Type>*>(branch[1])->value();
  28491. const details::operator_type o0 = expr_gen.get_operator(vocov->f0());
  28492. const details::operator_type o1 = expr_gen.get_operator(vocov->f1());
  28493. const details::operator_type o2 = operation;
  28494. binary_functor_t f0 = vocov->f0();
  28495. binary_functor_t f1 = vocov->f1();
  28496. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  28497. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  28498. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  28499. expression_node_ptr result = error_node();
  28500. const bool synthesis_result =
  28501. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  28502. (expr_gen, id(expr_gen, o0, o1, o2), v0, c0, v1, c1, result);
  28503. if (synthesis_result)
  28504. return result;
  28505. else if (!expr_gen.valid_operator(o2,f2))
  28506. return error_node();
  28507. exprtk_debug(("((v0 o0 (c0 o1 v1)) o2 c1)\n"));
  28508. return node_type::allocate(*(expr_gen.node_allocator_), v0, c0, v1, c1, f0, f1, f2);
  28509. }
  28510. static inline std::string id(expression_generator<Type>& expr_gen,
  28511. const details::operator_type o0,
  28512. const details::operator_type o1,
  28513. const details::operator_type o2)
  28514. {
  28515. return details::build_string()
  28516. << "(t" << expr_gen.to_str(o0)
  28517. << "(t" << expr_gen.to_str(o1)
  28518. << "t)" << expr_gen.to_str(o2)
  28519. << "t";
  28520. }
  28521. };
  28522. struct synthesize_covovoc_expression4
  28523. {
  28524. typedef typename covovoc_t::type4 node_type;
  28525. typedef typename covovoc_t::sf4_type sf4_type;
  28526. typedef typename node_type::T0 T0;
  28527. typedef typename node_type::T1 T1;
  28528. typedef typename node_type::T2 T2;
  28529. typedef typename node_type::T3 T3;
  28530. static inline expression_node_ptr process(expression_generator<Type>& expr_gen,
  28531. const details::operator_type& operation,
  28532. expression_node_ptr (&branch)[2])
  28533. {
  28534. // ((c0 o0 (v0 o1 v1)) o2 c1)
  28535. typedef typename synthesize_covov_expression1::node_type lcl_covov_t;
  28536. const lcl_covov_t* covov = static_cast<const lcl_covov_t*>(branch[0]);
  28537. const Type c0 = covov->t0();
  28538. const Type& v0 = covov->t1();
  28539. const Type& v1 = covov->t2();
  28540. const Type c1 = static_cast<details::literal_node<Type>*>(branch[1])->value();
  28541. const details::operator_type o0 = expr_gen.get_operator(covov->f0());
  28542. const details::operator_type o1 = expr_gen.get_operator(covov->f1());
  28543. const details::operator_type o2 = operation;
  28544. binary_functor_t f0 = covov->f0();
  28545. binary_functor_t f1 = covov->f1();
  28546. binary_functor_t f2 = reinterpret_cast<binary_functor_t>(0);
  28547. details::free_node(*(expr_gen.node_allocator_),branch[0]);
  28548. details::free_node(*(expr_gen.node_allocator_),branch[1]);
  28549. expression_node_ptr result = error_node();
  28550. const bool synthesis_result =
  28551. synthesize_sf4ext_expression::template compile<T0, T1, T2, T3>
  28552. (expr_gen, id(expr_gen, o0, o1, o2), c0, v0, v1, c1, result);
  28553. if (synthesis_result)
  28554. return result;
  28555. else if (!expr_gen.valid_operator(o2,f2))
  28556. return error_node();
  28557. exprtk_debug(("((c0 o0 (v0 o1 v1)) o2 c1)\n"));
  28558. return node_type::allocate(*(expr_gen.node_allocator_), c0, v0, v1, c1, f0, f1, f2);
  28559. }
  28560. static inline std::string id(expression_generator<Type>& expr_gen,
  28561. const details::operator_type o0,
  28562. const details::operator_type o1,
  28563. const details::operator_type o2)
  28564. {
  28565. return details::build_string()
  28566. << "(t" << expr_gen.to_str(o0)
  28567. << "(t" << expr_gen.to_str(o1)
  28568. << "t)" << expr_gen.to_str(o2)
  28569. << "t";
  28570. }
  28571. };
  28572. struct synthesize_vococov_expression4
  28573. {
  28574. typedef typename vococov_t::type4 node_type;
  28575. static inline expression_node_ptr process(expression_generator<Type>&, const details::operator_type&, expression_node_ptr (&)[2])
  28576. {
  28577. // ((v0 o0 (c0 o1 c1)) o2 v1) - Not possible
  28578. exprtk_debug(("((v0 o0 (c0 o1 c1)) o2 v1) - Not possible\n"));
  28579. return error_node();
  28580. }
  28581. static inline std::string id(expression_generator<Type>&,
  28582. const details::operator_type, const details::operator_type, const details::operator_type)
  28583. {
  28584. return "INVALID";
  28585. }
  28586. };
  28587. #endif
  28588. inline expression_node_ptr synthesize_uvouv_expression(const details::operator_type& operation, expression_node_ptr (&branch)[2])
  28589. {
  28590. // Definition: uv o uv
  28591. details::operator_type o0 = static_cast<details::uv_base_node<Type>*>(branch[0])->operation();
  28592. details::operator_type o1 = static_cast<details::uv_base_node<Type>*>(branch[1])->operation();
  28593. const Type& v0 = static_cast<details::uv_base_node<Type>*>(branch[0])->v();
  28594. const Type& v1 = static_cast<details::uv_base_node<Type>*>(branch[1])->v();
  28595. unary_functor_t u0 = reinterpret_cast<unary_functor_t> (0);
  28596. unary_functor_t u1 = reinterpret_cast<unary_functor_t> (0);
  28597. binary_functor_t f = reinterpret_cast<binary_functor_t>(0);
  28598. if (!valid_operator(o0,u0))
  28599. return error_node();
  28600. else if (!valid_operator(o1,u1))
  28601. return error_node();
  28602. else if (!valid_operator(operation,f))
  28603. return error_node();
  28604. expression_node_ptr result = error_node();
  28605. if (
  28606. (details::e_neg == o0) &&
  28607. (details::e_neg == o1)
  28608. )
  28609. {
  28610. switch (operation)
  28611. {
  28612. // (-v0 + -v1) --> -(v0 + v1)
  28613. case details::e_add : result = (*this)(details::e_neg,
  28614. node_allocator_->
  28615. allocate_rr<typename details::
  28616. vov_node<Type,details::add_op<Type> > >(v0, v1));
  28617. exprtk_debug(("(-v0 + -v1) --> -(v0 + v1)\n"));
  28618. break;
  28619. // (-v0 - -v1) --> (v1 - v0)
  28620. case details::e_sub : result = node_allocator_->
  28621. allocate_rr<typename details::
  28622. vov_node<Type,details::sub_op<Type> > >(v1, v0);
  28623. exprtk_debug(("(-v0 - -v1) --> (v1 - v0)\n"));
  28624. break;
  28625. // (-v0 * -v1) --> (v0 * v1)
  28626. case details::e_mul : result = node_allocator_->
  28627. allocate_rr<typename details::
  28628. vov_node<Type,details::mul_op<Type> > >(v0, v1);
  28629. exprtk_debug(("(-v0 * -v1) --> (v0 * v1)\n"));
  28630. break;
  28631. // (-v0 / -v1) --> (v0 / v1)
  28632. case details::e_div : result = node_allocator_->
  28633. allocate_rr<typename details::
  28634. vov_node<Type,details::div_op<Type> > >(v0, v1);
  28635. exprtk_debug(("(-v0 / -v1) --> (v0 / v1)\n"));
  28636. break;
  28637. default : break;
  28638. }
  28639. }
  28640. if (0 == result)
  28641. {
  28642. result = node_allocator_->
  28643. allocate_rrrrr<typename details::uvouv_node<Type> >(v0, v1, u0, u1, f);
  28644. }
  28645. details::free_all_nodes(*node_allocator_,branch);
  28646. return result;
  28647. }
  28648. #undef basic_opr_switch_statements
  28649. #undef extended_opr_switch_statements
  28650. #undef unary_opr_switch_statements
  28651. #ifndef exprtk_disable_string_capabilities
  28652. #define string_opr_switch_statements \
  28653. case_stmt(details:: e_lt ,details:: lt_op) \
  28654. case_stmt(details:: e_lte ,details:: lte_op) \
  28655. case_stmt(details:: e_gt ,details:: gt_op) \
  28656. case_stmt(details:: e_gte ,details:: gte_op) \
  28657. case_stmt(details:: e_eq ,details:: eq_op) \
  28658. case_stmt(details:: e_ne ,details:: ne_op) \
  28659. case_stmt(details::e_in ,details:: in_op) \
  28660. case_stmt(details::e_like ,details:: like_op) \
  28661. case_stmt(details::e_ilike,details::ilike_op) \
  28662. template <typename T0, typename T1>
  28663. inline expression_node_ptr synthesize_str_xrox_expression_impl(const details::operator_type& opr,
  28664. T0 s0, T1 s1,
  28665. range_t rp0)
  28666. {
  28667. switch (opr)
  28668. {
  28669. #define case_stmt(op0,op1) \
  28670. case op0 : return node_allocator_-> \
  28671. allocate_ttt<typename details::str_xrox_node<Type,T0,T1,range_t,op1<Type> >,T0,T1> \
  28672. (s0, s1, rp0); \
  28673. string_opr_switch_statements
  28674. #undef case_stmt
  28675. default : return error_node();
  28676. }
  28677. }
  28678. template <typename T0, typename T1>
  28679. inline expression_node_ptr synthesize_str_xoxr_expression_impl(const details::operator_type& opr,
  28680. T0 s0, T1 s1,
  28681. range_t rp1)
  28682. {
  28683. switch (opr)
  28684. {
  28685. #define case_stmt(op0,op1) \
  28686. case op0 : return node_allocator_-> \
  28687. allocate_ttt<typename details::str_xoxr_node<Type,T0,T1,range_t,op1<Type> >,T0,T1> \
  28688. (s0, s1, rp1); \
  28689. string_opr_switch_statements
  28690. #undef case_stmt
  28691. default : return error_node();
  28692. }
  28693. }
  28694. template <typename T0, typename T1>
  28695. inline expression_node_ptr synthesize_str_xroxr_expression_impl(const details::operator_type& opr,
  28696. T0 s0, T1 s1,
  28697. range_t rp0, range_t rp1)
  28698. {
  28699. switch (opr)
  28700. {
  28701. #define case_stmt(op0,op1) \
  28702. case op0 : return node_allocator_-> \
  28703. allocate_tttt<typename details::str_xroxr_node<Type,T0,T1,range_t,op1<Type> >,T0,T1> \
  28704. (s0, s1, rp0, rp1); \
  28705. string_opr_switch_statements
  28706. #undef case_stmt
  28707. default : return error_node();
  28708. }
  28709. }
  28710. template <typename T0, typename T1>
  28711. inline expression_node_ptr synthesize_sos_expression_impl(const details::operator_type& opr, T0 s0, T1 s1)
  28712. {
  28713. switch (opr)
  28714. {
  28715. #define case_stmt(op0,op1) \
  28716. case op0 : return node_allocator_-> \
  28717. allocate_tt<typename details::sos_node<Type,T0,T1,op1<Type> >,T0,T1>(s0, s1); \
  28718. string_opr_switch_statements
  28719. #undef case_stmt
  28720. default : return error_node();
  28721. }
  28722. }
  28723. inline expression_node_ptr synthesize_sos_expression(const details::operator_type& opr, expression_node_ptr (&branch)[2])
  28724. {
  28725. std::string& s0 = static_cast<details::stringvar_node<Type>*>(branch[0])->ref();
  28726. std::string& s1 = static_cast<details::stringvar_node<Type>*>(branch[1])->ref();
  28727. return synthesize_sos_expression_impl<std::string&,std::string&>(opr, s0, s1);
  28728. }
  28729. inline expression_node_ptr synthesize_sros_expression(const details::operator_type& opr, expression_node_ptr (&branch)[2])
  28730. {
  28731. std::string& s0 = static_cast<details::string_range_node<Type>*>(branch[0])->ref ();
  28732. std::string& s1 = static_cast<details::stringvar_node<Type>*> (branch[1])->ref ();
  28733. range_t rp0 = static_cast<details::string_range_node<Type>*>(branch[0])->range();
  28734. static_cast<details::string_range_node<Type>*>(branch[0])->range_ref().clear();
  28735. free_node(*node_allocator_,branch[0]);
  28736. return synthesize_str_xrox_expression_impl<std::string&,std::string&>(opr, s0, s1, rp0);
  28737. }
  28738. inline expression_node_ptr synthesize_sosr_expression(const details::operator_type& opr, expression_node_ptr (&branch)[2])
  28739. {
  28740. std::string& s0 = static_cast<details::stringvar_node<Type>*> (branch[0])->ref ();
  28741. std::string& s1 = static_cast<details::string_range_node<Type>*>(branch[1])->ref ();
  28742. range_t rp1 = static_cast<details::string_range_node<Type>*>(branch[1])->range();
  28743. static_cast<details::string_range_node<Type>*>(branch[1])->range_ref().clear();
  28744. free_node(*node_allocator_,branch[1]);
  28745. return synthesize_str_xoxr_expression_impl<std::string&,std::string&>(opr, s0, s1, rp1);
  28746. }
  28747. inline expression_node_ptr synthesize_socsr_expression(const details::operator_type& opr, expression_node_ptr (&branch)[2])
  28748. {
  28749. std::string& s0 = static_cast<details::stringvar_node<Type>*> (branch[0])->ref ();
  28750. std::string s1 = static_cast<details::const_string_range_node<Type>*>(branch[1])->str ();
  28751. range_t rp1 = static_cast<details::const_string_range_node<Type>*>(branch[1])->range();
  28752. static_cast<details::const_string_range_node<Type>*>(branch[1])->range_ref().clear();
  28753. free_node(*node_allocator_,branch[1]);
  28754. return synthesize_str_xoxr_expression_impl<std::string&, const std::string>(opr, s0, s1, rp1);
  28755. }
  28756. inline expression_node_ptr synthesize_srosr_expression(const details::operator_type& opr, expression_node_ptr (&branch)[2])
  28757. {
  28758. std::string& s0 = static_cast<details::string_range_node<Type>*>(branch[0])->ref ();
  28759. std::string& s1 = static_cast<details::string_range_node<Type>*>(branch[1])->ref ();
  28760. range_t rp0 = static_cast<details::string_range_node<Type>*>(branch[0])->range();
  28761. range_t rp1 = static_cast<details::string_range_node<Type>*>(branch[1])->range();
  28762. static_cast<details::string_range_node<Type>*>(branch[0])->range_ref().clear();
  28763. static_cast<details::string_range_node<Type>*>(branch[1])->range_ref().clear();
  28764. details::free_node(*node_allocator_,branch[0]);
  28765. details::free_node(*node_allocator_,branch[1]);
  28766. return synthesize_str_xroxr_expression_impl<std::string&,std::string&>(opr, s0, s1, rp0, rp1);
  28767. }
  28768. inline expression_node_ptr synthesize_socs_expression(const details::operator_type& opr, expression_node_ptr (&branch)[2])
  28769. {
  28770. std::string& s0 = static_cast< details::stringvar_node<Type>*>(branch[0])->ref();
  28771. std::string s1 = static_cast<details::string_literal_node<Type>*>(branch[1])->str();
  28772. details::free_node(*node_allocator_,branch[1]);
  28773. return synthesize_sos_expression_impl<std::string&, const std::string>(opr, s0, s1);
  28774. }
  28775. inline expression_node_ptr synthesize_csos_expression(const details::operator_type& opr, expression_node_ptr (&branch)[2])
  28776. {
  28777. std::string s0 = static_cast<details::string_literal_node<Type>*>(branch[0])->str();
  28778. std::string& s1 = static_cast< details::stringvar_node<Type>*>(branch[1])->ref();
  28779. details::free_node(*node_allocator_,branch[0]);
  28780. return synthesize_sos_expression_impl<const std::string,std::string&>(opr, s0, s1);
  28781. }
  28782. inline expression_node_ptr synthesize_csosr_expression(const details::operator_type& opr, expression_node_ptr (&branch)[2])
  28783. {
  28784. std::string s0 = static_cast<details::string_literal_node<Type>*>(branch[0])->str ();
  28785. std::string& s1 = static_cast<details::string_range_node<Type>*> (branch[1])->ref ();
  28786. range_t rp1 = static_cast<details::string_range_node<Type>*> (branch[1])->range();
  28787. static_cast<details::string_range_node<Type>*>(branch[1])->range_ref().clear();
  28788. details::free_node(*node_allocator_,branch[0]);
  28789. details::free_node(*node_allocator_,branch[1]);
  28790. return synthesize_str_xoxr_expression_impl<const std::string,std::string&>(opr, s0, s1, rp1);
  28791. }
  28792. inline expression_node_ptr synthesize_srocs_expression(const details::operator_type& opr, expression_node_ptr (&branch)[2])
  28793. {
  28794. std::string& s0 = static_cast<details::string_range_node<Type>*> (branch[0])->ref ();
  28795. std::string s1 = static_cast<details::string_literal_node<Type>*>(branch[1])->str ();
  28796. range_t rp0 = static_cast<details::string_range_node<Type>*> (branch[0])->range();
  28797. static_cast<details::string_range_node<Type>*>(branch[0])->range_ref().clear();
  28798. details::free_node(*node_allocator_,branch[0]);
  28799. details::free_node(*node_allocator_,branch[1]);
  28800. return synthesize_str_xrox_expression_impl<std::string&, const std::string>(opr, s0, s1, rp0);
  28801. }
  28802. inline expression_node_ptr synthesize_srocsr_expression(const details::operator_type& opr, expression_node_ptr (&branch)[2])
  28803. {
  28804. std::string& s0 = static_cast<details::string_range_node<Type>*> (branch[0])->ref ();
  28805. std::string s1 = static_cast<details::const_string_range_node<Type>*>(branch[1])->str ();
  28806. range_t rp0 = static_cast<details::string_range_node<Type>*> (branch[0])->range();
  28807. range_t rp1 = static_cast<details::const_string_range_node<Type>*>(branch[1])->range();
  28808. static_cast<details::string_range_node<Type>*> (branch[0])->range_ref().clear();
  28809. static_cast<details::const_string_range_node<Type>*>(branch[1])->range_ref().clear();
  28810. details::free_node(*node_allocator_,branch[0]);
  28811. details::free_node(*node_allocator_,branch[1]);
  28812. return synthesize_str_xroxr_expression_impl<std::string&, const std::string>(opr, s0, s1, rp0, rp1);
  28813. }
  28814. inline expression_node_ptr synthesize_csocs_expression(const details::operator_type& opr, expression_node_ptr (&branch)[2])
  28815. {
  28816. const std::string s0 = static_cast<details::string_literal_node<Type>*>(branch[0])->str();
  28817. const std::string s1 = static_cast<details::string_literal_node<Type>*>(branch[1])->str();
  28818. expression_node_ptr result = error_node();
  28819. if (details::e_add == opr)
  28820. result = node_allocator_->allocate_c<details::string_literal_node<Type> >(s0 + s1);
  28821. else if (details::e_in == opr)
  28822. result = node_allocator_->allocate_c<details::literal_node<Type> >(details::in_op <Type>::process(s0,s1));
  28823. else if (details::e_like == opr)
  28824. result = node_allocator_->allocate_c<details::literal_node<Type> >(details::like_op <Type>::process(s0,s1));
  28825. else if (details::e_ilike == opr)
  28826. result = node_allocator_->allocate_c<details::literal_node<Type> >(details::ilike_op<Type>::process(s0,s1));
  28827. else
  28828. {
  28829. expression_node_ptr temp = synthesize_sos_expression_impl<const std::string, const std::string>(opr, s0, s1);
  28830. const Type v = temp->value();
  28831. details::free_node(*node_allocator_,temp);
  28832. result = node_allocator_->allocate<literal_node_t>(v);
  28833. }
  28834. details::free_all_nodes(*node_allocator_,branch);
  28835. return result;
  28836. }
  28837. inline expression_node_ptr synthesize_csocsr_expression(const details::operator_type& opr, expression_node_ptr (&branch)[2])
  28838. {
  28839. const std::string s0 = static_cast<details::string_literal_node<Type>*> (branch[0])->str ();
  28840. std::string s1 = static_cast<details::const_string_range_node<Type>*>(branch[1])->str ();
  28841. range_t rp1 = static_cast<details::const_string_range_node<Type>*>(branch[1])->range();
  28842. static_cast<details::const_string_range_node<Type>*>(branch[1])->range_ref().clear();
  28843. free_node(*node_allocator_,branch[0]);
  28844. free_node(*node_allocator_,branch[1]);
  28845. return synthesize_str_xoxr_expression_impl<const std::string, const std::string>(opr, s0, s1, rp1);
  28846. }
  28847. inline expression_node_ptr synthesize_csros_expression(const details::operator_type& opr, expression_node_ptr (&branch)[2])
  28848. {
  28849. std::string s0 = static_cast<details::const_string_range_node<Type>*>(branch[0])->str ();
  28850. std::string& s1 = static_cast<details::stringvar_node<Type>*> (branch[1])->ref ();
  28851. range_t rp0 = static_cast<details::const_string_range_node<Type>*>(branch[0])->range();
  28852. static_cast<details::const_string_range_node<Type>*>(branch[0])->range_ref().clear();
  28853. free_node(*node_allocator_,branch[0]);
  28854. return synthesize_str_xrox_expression_impl<const std::string,std::string&>(opr, s0, s1, rp0);
  28855. }
  28856. inline expression_node_ptr synthesize_csrosr_expression(const details::operator_type& opr, expression_node_ptr (&branch)[2])
  28857. {
  28858. const std::string s0 = static_cast<details::const_string_range_node<Type>*>(branch[0])->str ();
  28859. std::string& s1 = static_cast<details::string_range_node<Type>*> (branch[1])->ref ();
  28860. const range_t rp0 = static_cast<details::const_string_range_node<Type>*>(branch[0])->range();
  28861. const range_t rp1 = static_cast<details::string_range_node<Type>*> (branch[1])->range();
  28862. static_cast<details::const_string_range_node<Type>*>(branch[0])->range_ref().clear();
  28863. static_cast<details::string_range_node<Type>*> (branch[1])->range_ref().clear();
  28864. free_node(*node_allocator_,branch[0]);
  28865. free_node(*node_allocator_,branch[1]);
  28866. return synthesize_str_xroxr_expression_impl<const std::string,std::string&>(opr, s0, s1, rp0, rp1);
  28867. }
  28868. inline expression_node_ptr synthesize_csrocs_expression(const details::operator_type& opr, expression_node_ptr (&branch)[2])
  28869. {
  28870. const std::string s0 = static_cast<details::const_string_range_node<Type>*>(branch[0])->str ();
  28871. const std::string s1 = static_cast<details::string_literal_node<Type>*> (branch[1])->str ();
  28872. const range_t rp0 = static_cast<details::const_string_range_node<Type>*>(branch[0])->range();
  28873. static_cast<details::const_string_range_node<Type>*>(branch[0])->range_ref().clear();
  28874. details::free_all_nodes(*node_allocator_,branch);
  28875. return synthesize_str_xrox_expression_impl<const std::string,std::string>(opr, s0, s1, rp0);
  28876. }
  28877. inline expression_node_ptr synthesize_csrocsr_expression(const details::operator_type& opr, expression_node_ptr (&branch)[2])
  28878. {
  28879. const std::string s0 = static_cast<details::const_string_range_node<Type>*>(branch[0])->str ();
  28880. const std::string s1 = static_cast<details::const_string_range_node<Type>*>(branch[1])->str ();
  28881. const range_t rp0 = static_cast<details::const_string_range_node<Type>*>(branch[0])->range();
  28882. const range_t rp1 = static_cast<details::const_string_range_node<Type>*>(branch[1])->range();
  28883. static_cast<details::const_string_range_node<Type>*>(branch[0])->range_ref().clear();
  28884. static_cast<details::const_string_range_node<Type>*>(branch[1])->range_ref().clear();
  28885. details::free_all_nodes(*node_allocator_,branch);
  28886. return synthesize_str_xroxr_expression_impl<const std::string, const std::string>(opr, s0, s1, rp0, rp1);
  28887. }
  28888. inline expression_node_ptr synthesize_strogen_expression(const details::operator_type& opr, expression_node_ptr (&branch)[2])
  28889. {
  28890. switch (opr)
  28891. {
  28892. #define case_stmt(op0,op1) \
  28893. case op0 : return node_allocator_-> \
  28894. allocate_ttt<typename details::str_sogens_node<Type,op1<Type> > > \
  28895. (opr, branch[0], branch[1]); \
  28896. string_opr_switch_statements
  28897. #undef case_stmt
  28898. default : return error_node();
  28899. }
  28900. }
  28901. #endif
  28902. #ifndef exprtk_disable_string_capabilities
  28903. inline expression_node_ptr synthesize_string_expression(const details::operator_type& opr, expression_node_ptr (&branch)[2])
  28904. {
  28905. if ((0 == branch[0]) || (0 == branch[1]))
  28906. {
  28907. details::free_all_nodes(*node_allocator_,branch);
  28908. return error_node();
  28909. }
  28910. const bool b0_is_s = details::is_string_node (branch[0]);
  28911. const bool b0_is_cs = details::is_const_string_node (branch[0]);
  28912. const bool b0_is_sr = details::is_string_range_node (branch[0]);
  28913. const bool b0_is_csr = details::is_const_string_range_node(branch[0]);
  28914. const bool b1_is_s = details::is_string_node (branch[1]);
  28915. const bool b1_is_cs = details::is_const_string_node (branch[1]);
  28916. const bool b1_is_sr = details::is_string_range_node (branch[1]);
  28917. const bool b1_is_csr = details::is_const_string_range_node(branch[1]);
  28918. const bool b0_is_gen = details::is_string_assignment_node (branch[0]) ||
  28919. details::is_genricstring_range_node(branch[0]) ||
  28920. details::is_string_concat_node (branch[0]) ||
  28921. details::is_string_function_node (branch[0]) ||
  28922. details::is_string_condition_node (branch[0]) ||
  28923. details::is_string_ccondition_node (branch[0]) ||
  28924. details::is_string_vararg_node (branch[0]) ;
  28925. const bool b1_is_gen = details::is_string_assignment_node (branch[1]) ||
  28926. details::is_genricstring_range_node(branch[1]) ||
  28927. details::is_string_concat_node (branch[1]) ||
  28928. details::is_string_function_node (branch[1]) ||
  28929. details::is_string_condition_node (branch[1]) ||
  28930. details::is_string_ccondition_node (branch[1]) ||
  28931. details::is_string_vararg_node (branch[1]) ;
  28932. if (details::e_add == opr)
  28933. {
  28934. if (!b0_is_cs || !b1_is_cs)
  28935. {
  28936. return synthesize_expression<string_concat_node_t,2>(opr,branch);
  28937. }
  28938. }
  28939. if (b0_is_gen || b1_is_gen)
  28940. {
  28941. return synthesize_strogen_expression(opr,branch);
  28942. }
  28943. else if (b0_is_s)
  28944. {
  28945. if (b1_is_s ) return synthesize_sos_expression (opr,branch);
  28946. else if (b1_is_cs ) return synthesize_socs_expression (opr,branch);
  28947. else if (b1_is_sr ) return synthesize_sosr_expression (opr,branch);
  28948. else if (b1_is_csr) return synthesize_socsr_expression (opr,branch);
  28949. }
  28950. else if (b0_is_cs)
  28951. {
  28952. if (b1_is_s ) return synthesize_csos_expression (opr,branch);
  28953. else if (b1_is_cs ) return synthesize_csocs_expression (opr,branch);
  28954. else if (b1_is_sr ) return synthesize_csosr_expression (opr,branch);
  28955. else if (b1_is_csr) return synthesize_csocsr_expression(opr,branch);
  28956. }
  28957. else if (b0_is_sr)
  28958. {
  28959. if (b1_is_s ) return synthesize_sros_expression (opr,branch);
  28960. else if (b1_is_sr ) return synthesize_srosr_expression (opr,branch);
  28961. else if (b1_is_cs ) return synthesize_srocs_expression (opr,branch);
  28962. else if (b1_is_csr) return synthesize_srocsr_expression(opr,branch);
  28963. }
  28964. else if (b0_is_csr)
  28965. {
  28966. if (b1_is_s ) return synthesize_csros_expression (opr,branch);
  28967. else if (b1_is_sr ) return synthesize_csrosr_expression (opr,branch);
  28968. else if (b1_is_cs ) return synthesize_csrocs_expression (opr,branch);
  28969. else if (b1_is_csr) return synthesize_csrocsr_expression(opr,branch);
  28970. }
  28971. return error_node();
  28972. }
  28973. #else
  28974. inline expression_node_ptr synthesize_string_expression(const details::operator_type&, expression_node_ptr (&branch)[2])
  28975. {
  28976. details::free_all_nodes(*node_allocator_,branch);
  28977. return error_node();
  28978. }
  28979. #endif
  28980. #ifndef exprtk_disable_string_capabilities
  28981. inline expression_node_ptr synthesize_string_expression(const details::operator_type& opr, expression_node_ptr (&branch)[3])
  28982. {
  28983. if (details::e_inrange != opr)
  28984. return error_node();
  28985. else if ((0 == branch[0]) || (0 == branch[1]) || (0 == branch[2]))
  28986. {
  28987. details::free_all_nodes(*node_allocator_,branch);
  28988. return error_node();
  28989. }
  28990. else if (
  28991. details::is_const_string_node(branch[0]) &&
  28992. details::is_const_string_node(branch[1]) &&
  28993. details::is_const_string_node(branch[2])
  28994. )
  28995. {
  28996. const std::string s0 = static_cast<details::string_literal_node<Type>*>(branch[0])->str();
  28997. const std::string s1 = static_cast<details::string_literal_node<Type>*>(branch[1])->str();
  28998. const std::string s2 = static_cast<details::string_literal_node<Type>*>(branch[2])->str();
  28999. const Type v = (((s0 <= s1) && (s1 <= s2)) ? Type(1) : Type(0));
  29000. details::free_all_nodes(*node_allocator_,branch);
  29001. return node_allocator_->allocate_c<details::literal_node<Type> >(v);
  29002. }
  29003. else if (
  29004. details::is_string_node(branch[0]) &&
  29005. details::is_string_node(branch[1]) &&
  29006. details::is_string_node(branch[2])
  29007. )
  29008. {
  29009. std::string& s0 = static_cast<details::stringvar_node<Type>*>(branch[0])->ref();
  29010. std::string& s1 = static_cast<details::stringvar_node<Type>*>(branch[1])->ref();
  29011. std::string& s2 = static_cast<details::stringvar_node<Type>*>(branch[2])->ref();
  29012. typedef typename details::sosos_node<Type, std::string&, std::string&, std::string&, details::inrange_op<Type> > inrange_t;
  29013. return node_allocator_->allocate_type<inrange_t, std::string&, std::string&, std::string&>(s0, s1, s2);
  29014. }
  29015. else if (
  29016. details::is_const_string_node(branch[0]) &&
  29017. details::is_string_node(branch[1]) &&
  29018. details::is_const_string_node(branch[2])
  29019. )
  29020. {
  29021. std::string s0 = static_cast<details::string_literal_node<Type>*>(branch[0])->str();
  29022. std::string& s1 = static_cast< details::stringvar_node<Type>*>(branch[1])->ref();
  29023. std::string s2 = static_cast<details::string_literal_node<Type>*>(branch[2])->str();
  29024. typedef typename details::sosos_node<Type, std::string, std::string&, std::string, details::inrange_op<Type> > inrange_t;
  29025. details::free_node(*node_allocator_,branch[0]);
  29026. details::free_node(*node_allocator_,branch[2]);
  29027. return node_allocator_->allocate_type<inrange_t, std::string, std::string&, std::string>(s0, s1, s2);
  29028. }
  29029. else if (
  29030. details::is_string_node(branch[0]) &&
  29031. details::is_const_string_node(branch[1]) &&
  29032. details::is_string_node(branch[2])
  29033. )
  29034. {
  29035. std::string& s0 = static_cast< details::stringvar_node<Type>*>(branch[0])->ref();
  29036. std::string s1 = static_cast<details::string_literal_node<Type>*>(branch[1])->str();
  29037. std::string& s2 = static_cast< details::stringvar_node<Type>*>(branch[2])->ref();
  29038. typedef typename details::sosos_node<Type, std::string&, std::string, std::string&, details::inrange_op<Type> > inrange_t;
  29039. details::free_node(*node_allocator_,branch[1]);
  29040. return node_allocator_->allocate_type<inrange_t, std::string&, std::string, std::string&>(s0, s1, s2);
  29041. }
  29042. else if (
  29043. details::is_string_node(branch[0]) &&
  29044. details::is_string_node(branch[1]) &&
  29045. details::is_const_string_node(branch[2])
  29046. )
  29047. {
  29048. std::string& s0 = static_cast< details::stringvar_node<Type>*>(branch[0])->ref();
  29049. std::string& s1 = static_cast< details::stringvar_node<Type>*>(branch[1])->ref();
  29050. std::string s2 = static_cast<details::string_literal_node<Type>*>(branch[2])->str();
  29051. typedef typename details::sosos_node<Type, std::string&, std::string&, std::string, details::inrange_op<Type> > inrange_t;
  29052. details::free_node(*node_allocator_,branch[2]);
  29053. return node_allocator_->allocate_type<inrange_t, std::string&, std::string&, std::string>(s0, s1, s2);
  29054. }
  29055. else if (
  29056. details::is_const_string_node(branch[0]) &&
  29057. details:: is_string_node(branch[1]) &&
  29058. details:: is_string_node(branch[2])
  29059. )
  29060. {
  29061. std::string s0 = static_cast<details::string_literal_node<Type>*>(branch[0])->str();
  29062. std::string& s1 = static_cast< details::stringvar_node<Type>*>(branch[1])->ref();
  29063. std::string& s2 = static_cast< details::stringvar_node<Type>*>(branch[2])->ref();
  29064. typedef typename details::sosos_node<Type, std::string, std::string&, std::string&, details::inrange_op<Type> > inrange_t;
  29065. details::free_node(*node_allocator_,branch[0]);
  29066. return node_allocator_->allocate_type<inrange_t, std::string, std::string&, std::string&>(s0, s1, s2);
  29067. }
  29068. else
  29069. return error_node();
  29070. }
  29071. #else
  29072. inline expression_node_ptr synthesize_string_expression(const details::operator_type&, expression_node_ptr (&branch)[3])
  29073. {
  29074. details::free_all_nodes(*node_allocator_,branch);
  29075. return error_node();
  29076. }
  29077. #endif
  29078. inline expression_node_ptr synthesize_null_expression(const details::operator_type& operation, expression_node_ptr (&branch)[2])
  29079. {
  29080. /*
  29081. Note: The following are the type promotion rules
  29082. that relate to operations that include 'null':
  29083. 0. null ==/!= null --> true false
  29084. 1. null operation null --> null
  29085. 2. x ==/!= null --> true/false
  29086. 3. null ==/!= x --> true/false
  29087. 4. x operation null --> x
  29088. 5. null operation x --> x
  29089. */
  29090. typedef typename details::null_eq_node<T> nulleq_node_t;
  29091. const bool b0_null = details::is_null_node(branch[0]);
  29092. const bool b1_null = details::is_null_node(branch[1]);
  29093. if (b0_null && b1_null)
  29094. {
  29095. expression_node_ptr result = error_node();
  29096. if (details::e_eq == operation)
  29097. result = node_allocator_->allocate_c<literal_node_t>(T(1));
  29098. else if (details::e_ne == operation)
  29099. result = node_allocator_->allocate_c<literal_node_t>(T(0));
  29100. if (result)
  29101. {
  29102. details::free_node(*node_allocator_,branch[0]);
  29103. details::free_node(*node_allocator_,branch[1]);
  29104. return result;
  29105. }
  29106. details::free_node(*node_allocator_,branch[1]);
  29107. return branch[0];
  29108. }
  29109. else if (details::e_eq == operation)
  29110. {
  29111. expression_node_ptr result = node_allocator_->
  29112. allocate_rc<nulleq_node_t>(branch[b0_null ? 0 : 1],true);
  29113. details::free_node(*node_allocator_,branch[b0_null ? 1 : 0]);
  29114. return result;
  29115. }
  29116. else if (details::e_ne == operation)
  29117. {
  29118. expression_node_ptr result = node_allocator_->
  29119. allocate_rc<nulleq_node_t>(branch[b0_null ? 0 : 1],false);
  29120. details::free_node(*node_allocator_,branch[b0_null ? 1 : 0]);
  29121. return result;
  29122. }
  29123. else if (b0_null)
  29124. {
  29125. details::free_node(*node_allocator_,branch[0]);
  29126. branch[0] = branch[1];
  29127. branch[1] = error_node();
  29128. }
  29129. else if (b1_null)
  29130. {
  29131. details::free_node(*node_allocator_,branch[1]);
  29132. branch[1] = error_node();
  29133. }
  29134. if (
  29135. (details::e_add == operation) || (details::e_sub == operation) ||
  29136. (details::e_mul == operation) || (details::e_div == operation) ||
  29137. (details::e_mod == operation) || (details::e_pow == operation)
  29138. )
  29139. {
  29140. return branch[0];
  29141. }
  29142. else if (
  29143. (details::e_lt == operation) || (details::e_lte == operation) ||
  29144. (details::e_gt == operation) || (details::e_gte == operation) ||
  29145. (details::e_and == operation) || (details::e_nand == operation) ||
  29146. (details::e_or == operation) || (details::e_nor == operation) ||
  29147. (details::e_xor == operation) || (details::e_xnor == operation) ||
  29148. (details::e_in == operation) || (details::e_like == operation) ||
  29149. (details::e_ilike == operation)
  29150. )
  29151. {
  29152. return node_allocator_->allocate_c<literal_node_t>(T(0));
  29153. }
  29154. details::free_node(*node_allocator_,branch[0]);
  29155. return node_allocator_->allocate<details::null_node<Type> >();
  29156. }
  29157. template <typename NodeType, std::size_t N>
  29158. inline expression_node_ptr synthesize_expression(const details::operator_type& operation, expression_node_ptr (&branch)[N])
  29159. {
  29160. if (
  29161. (details::e_in == operation) ||
  29162. (details::e_like == operation) ||
  29163. (details::e_ilike == operation)
  29164. )
  29165. {
  29166. free_all_nodes(*node_allocator_,branch);
  29167. return error_node();
  29168. }
  29169. else if (!details::all_nodes_valid<N>(branch))
  29170. {
  29171. free_all_nodes(*node_allocator_,branch);
  29172. return error_node();
  29173. }
  29174. else if ((details::e_default != operation))
  29175. {
  29176. // Attempt simple constant folding optimisation.
  29177. expression_node_ptr expression_point = node_allocator_->allocate<NodeType>(operation,branch);
  29178. if (is_constant_foldable<N>(branch))
  29179. {
  29180. const Type v = expression_point->value();
  29181. details::free_node(*node_allocator_,expression_point);
  29182. return node_allocator_->allocate<literal_node_t>(v);
  29183. }
  29184. else
  29185. return expression_point;
  29186. }
  29187. else
  29188. return error_node();
  29189. }
  29190. template <typename NodeType, std::size_t N>
  29191. inline expression_node_ptr synthesize_expression(F* f, expression_node_ptr (&branch)[N])
  29192. {
  29193. if (!details::all_nodes_valid<N>(branch))
  29194. {
  29195. free_all_nodes(*node_allocator_,branch);
  29196. return error_node();
  29197. }
  29198. typedef typename details::function_N_node<T,ifunction_t,N> function_N_node_t;
  29199. // Attempt simple constant folding optimisation.
  29200. expression_node_ptr expression_point = node_allocator_->allocate<NodeType>(f);
  29201. function_N_node_t* func_node_ptr = dynamic_cast<function_N_node_t*>(expression_point);
  29202. if (0 == func_node_ptr)
  29203. {
  29204. free_all_nodes(*node_allocator_,branch);
  29205. return error_node();
  29206. }
  29207. else
  29208. func_node_ptr->init_branches(branch);
  29209. if (is_constant_foldable<N>(branch) && !f->has_side_effects())
  29210. {
  29211. Type v = expression_point->value();
  29212. details::free_node(*node_allocator_,expression_point);
  29213. return node_allocator_->allocate<literal_node_t>(v);
  29214. }
  29215. parser_->state_.activate_side_effect("synthesize_expression(function<NT,N>)");
  29216. return expression_point;
  29217. }
  29218. bool strength_reduction_enabled_;
  29219. details::node_allocator* node_allocator_;
  29220. synthesize_map_t synthesize_map_;
  29221. unary_op_map_t* unary_op_map_;
  29222. binary_op_map_t* binary_op_map_;
  29223. inv_binary_op_map_t* inv_binary_op_map_;
  29224. sf3_map_t* sf3_map_;
  29225. sf4_map_t* sf4_map_;
  29226. parser_t* parser_;
  29227. };
  29228. inline void set_error(const parser_error::type& error_type)
  29229. {
  29230. error_list_.push_back(error_type);
  29231. }
  29232. inline void remove_last_error()
  29233. {
  29234. if (!error_list_.empty())
  29235. {
  29236. error_list_.pop_back();
  29237. }
  29238. }
  29239. inline void set_synthesis_error(const std::string& synthesis_error_message)
  29240. {
  29241. if (synthesis_error_.empty())
  29242. {
  29243. synthesis_error_ = synthesis_error_message;
  29244. }
  29245. }
  29246. inline void register_local_vars(expression<T>& e)
  29247. {
  29248. for (std::size_t i = 0; i < sem_.size(); ++i)
  29249. {
  29250. scope_element& se = sem_.get_element(i);
  29251. if (
  29252. (scope_element::e_variable == se.type) ||
  29253. (scope_element::e_vecelem == se.type)
  29254. )
  29255. {
  29256. if (se.var_node)
  29257. {
  29258. e.register_local_var(se.var_node);
  29259. }
  29260. if (se.data)
  29261. {
  29262. e.register_local_data(se.data, 1, 0);
  29263. }
  29264. }
  29265. else if (scope_element::e_vector == se.type)
  29266. {
  29267. if (se.vec_node)
  29268. {
  29269. e.register_local_var(se.vec_node);
  29270. }
  29271. if (se.data)
  29272. {
  29273. e.register_local_data(se.data, se.size, 1);
  29274. }
  29275. }
  29276. #ifndef exprtk_disable_string_capabilities
  29277. else if (scope_element::e_string == se.type)
  29278. {
  29279. if (se.str_node)
  29280. {
  29281. e.register_local_var(se.str_node);
  29282. }
  29283. if (se.data)
  29284. {
  29285. e.register_local_data(se.data, se.size, 2);
  29286. }
  29287. }
  29288. #endif
  29289. se.var_node = 0;
  29290. se.vec_node = 0;
  29291. #ifndef exprtk_disable_string_capabilities
  29292. se.str_node = 0;
  29293. #endif
  29294. se.data = 0;
  29295. se.ref_count = 0;
  29296. se.active = false;
  29297. }
  29298. }
  29299. inline void register_return_results(expression<T>& e)
  29300. {
  29301. e.register_return_results(results_context_);
  29302. results_context_ = 0;
  29303. }
  29304. inline void load_unary_operations_map(unary_op_map_t& m)
  29305. {
  29306. #define register_unary_op(Op,UnaryFunctor) \
  29307. m.insert(std::make_pair(Op,UnaryFunctor<T>::process)); \
  29308. register_unary_op(details:: e_abs, details:: abs_op)
  29309. register_unary_op(details:: e_acos, details:: acos_op)
  29310. register_unary_op(details::e_acosh, details::acosh_op)
  29311. register_unary_op(details:: e_asin, details:: asin_op)
  29312. register_unary_op(details::e_asinh, details::asinh_op)
  29313. register_unary_op(details::e_atanh, details::atanh_op)
  29314. register_unary_op(details:: e_ceil, details:: ceil_op)
  29315. register_unary_op(details:: e_cos, details:: cos_op)
  29316. register_unary_op(details:: e_cosh, details:: cosh_op)
  29317. register_unary_op(details:: e_exp, details:: exp_op)
  29318. register_unary_op(details::e_expm1, details::expm1_op)
  29319. register_unary_op(details::e_floor, details::floor_op)
  29320. register_unary_op(details:: e_log, details:: log_op)
  29321. register_unary_op(details::e_log10, details::log10_op)
  29322. register_unary_op(details:: e_log2, details:: log2_op)
  29323. register_unary_op(details::e_log1p, details::log1p_op)
  29324. register_unary_op(details:: e_neg, details:: neg_op)
  29325. register_unary_op(details:: e_pos, details:: pos_op)
  29326. register_unary_op(details::e_round, details::round_op)
  29327. register_unary_op(details:: e_sin, details:: sin_op)
  29328. register_unary_op(details:: e_sinc, details:: sinc_op)
  29329. register_unary_op(details:: e_sinh, details:: sinh_op)
  29330. register_unary_op(details:: e_sqrt, details:: sqrt_op)
  29331. register_unary_op(details:: e_tan, details:: tan_op)
  29332. register_unary_op(details:: e_tanh, details:: tanh_op)
  29333. register_unary_op(details:: e_cot, details:: cot_op)
  29334. register_unary_op(details:: e_sec, details:: sec_op)
  29335. register_unary_op(details:: e_csc, details:: csc_op)
  29336. register_unary_op(details:: e_r2d, details:: r2d_op)
  29337. register_unary_op(details:: e_d2r, details:: d2r_op)
  29338. register_unary_op(details:: e_d2g, details:: d2g_op)
  29339. register_unary_op(details:: e_g2d, details:: g2d_op)
  29340. register_unary_op(details:: e_notl, details:: notl_op)
  29341. register_unary_op(details:: e_sgn, details:: sgn_op)
  29342. register_unary_op(details:: e_erf, details:: erf_op)
  29343. register_unary_op(details:: e_erfc, details:: erfc_op)
  29344. register_unary_op(details:: e_ncdf, details:: ncdf_op)
  29345. register_unary_op(details:: e_frac, details:: frac_op)
  29346. register_unary_op(details::e_trunc, details::trunc_op)
  29347. #undef register_unary_op
  29348. }
  29349. inline void load_binary_operations_map(binary_op_map_t& m)
  29350. {
  29351. typedef typename binary_op_map_t::value_type value_type;
  29352. #define register_binary_op(Op,BinaryFunctor) \
  29353. m.insert(value_type(Op,BinaryFunctor<T>::process)); \
  29354. register_binary_op(details:: e_add, details:: add_op)
  29355. register_binary_op(details:: e_sub, details:: sub_op)
  29356. register_binary_op(details:: e_mul, details:: mul_op)
  29357. register_binary_op(details:: e_div, details:: div_op)
  29358. register_binary_op(details:: e_mod, details:: mod_op)
  29359. register_binary_op(details:: e_pow, details:: pow_op)
  29360. register_binary_op(details:: e_lt, details:: lt_op)
  29361. register_binary_op(details:: e_lte, details:: lte_op)
  29362. register_binary_op(details:: e_gt, details:: gt_op)
  29363. register_binary_op(details:: e_gte, details:: gte_op)
  29364. register_binary_op(details:: e_eq, details:: eq_op)
  29365. register_binary_op(details:: e_ne, details:: ne_op)
  29366. register_binary_op(details:: e_and, details:: and_op)
  29367. register_binary_op(details::e_nand, details::nand_op)
  29368. register_binary_op(details:: e_or, details:: or_op)
  29369. register_binary_op(details:: e_nor, details:: nor_op)
  29370. register_binary_op(details:: e_xor, details:: xor_op)
  29371. register_binary_op(details::e_xnor, details::xnor_op)
  29372. #undef register_binary_op
  29373. }
  29374. inline void load_inv_binary_operations_map(inv_binary_op_map_t& m)
  29375. {
  29376. typedef typename inv_binary_op_map_t::value_type value_type;
  29377. #define register_binary_op(Op,BinaryFunctor) \
  29378. m.insert(value_type(BinaryFunctor<T>::process,Op)); \
  29379. register_binary_op(details:: e_add, details:: add_op)
  29380. register_binary_op(details:: e_sub, details:: sub_op)
  29381. register_binary_op(details:: e_mul, details:: mul_op)
  29382. register_binary_op(details:: e_div, details:: div_op)
  29383. register_binary_op(details:: e_mod, details:: mod_op)
  29384. register_binary_op(details:: e_pow, details:: pow_op)
  29385. register_binary_op(details:: e_lt, details:: lt_op)
  29386. register_binary_op(details:: e_lte, details:: lte_op)
  29387. register_binary_op(details:: e_gt, details:: gt_op)
  29388. register_binary_op(details:: e_gte, details:: gte_op)
  29389. register_binary_op(details:: e_eq, details:: eq_op)
  29390. register_binary_op(details:: e_ne, details:: ne_op)
  29391. register_binary_op(details:: e_and, details:: and_op)
  29392. register_binary_op(details::e_nand, details::nand_op)
  29393. register_binary_op(details:: e_or, details:: or_op)
  29394. register_binary_op(details:: e_nor, details:: nor_op)
  29395. register_binary_op(details:: e_xor, details:: xor_op)
  29396. register_binary_op(details::e_xnor, details::xnor_op)
  29397. #undef register_binary_op
  29398. }
  29399. inline void load_sf3_map(sf3_map_t& sf3_map)
  29400. {
  29401. typedef std::pair<trinary_functor_t,details::operator_type> pair_t;
  29402. #define register_sf3(Op) \
  29403. sf3_map[details::sf##Op##_op<T>::id()] = pair_t(details::sf##Op##_op<T>::process,details::e_sf##Op); \
  29404. register_sf3(00) register_sf3(01) register_sf3(02) register_sf3(03)
  29405. register_sf3(04) register_sf3(05) register_sf3(06) register_sf3(07)
  29406. register_sf3(08) register_sf3(09) register_sf3(10) register_sf3(11)
  29407. register_sf3(12) register_sf3(13) register_sf3(14) register_sf3(15)
  29408. register_sf3(16) register_sf3(17) register_sf3(18) register_sf3(19)
  29409. register_sf3(20) register_sf3(21) register_sf3(22) register_sf3(23)
  29410. register_sf3(24) register_sf3(25) register_sf3(26) register_sf3(27)
  29411. register_sf3(28) register_sf3(29) register_sf3(30)
  29412. #undef register_sf3
  29413. #define register_sf3_extid(Id, Op) \
  29414. sf3_map[Id] = pair_t(details::sf##Op##_op<T>::process,details::e_sf##Op); \
  29415. register_sf3_extid("(t-t)-t",23) // (t-t)-t --> t-(t+t)
  29416. #undef register_sf3_extid
  29417. }
  29418. inline void load_sf4_map(sf4_map_t& sf4_map)
  29419. {
  29420. typedef std::pair<quaternary_functor_t,details::operator_type> pair_t;
  29421. #define register_sf4(Op) \
  29422. sf4_map[details::sf##Op##_op<T>::id()] = pair_t(details::sf##Op##_op<T>::process,details::e_sf##Op); \
  29423. register_sf4(48) register_sf4(49) register_sf4(50) register_sf4(51)
  29424. register_sf4(52) register_sf4(53) register_sf4(54) register_sf4(55)
  29425. register_sf4(56) register_sf4(57) register_sf4(58) register_sf4(59)
  29426. register_sf4(60) register_sf4(61) register_sf4(62) register_sf4(63)
  29427. register_sf4(64) register_sf4(65) register_sf4(66) register_sf4(67)
  29428. register_sf4(68) register_sf4(69) register_sf4(70) register_sf4(71)
  29429. register_sf4(72) register_sf4(73) register_sf4(74) register_sf4(75)
  29430. register_sf4(76) register_sf4(77) register_sf4(78) register_sf4(79)
  29431. register_sf4(80) register_sf4(81) register_sf4(82) register_sf4(83)
  29432. #undef register_sf4
  29433. #define register_sf4ext(Op) \
  29434. sf4_map[details::sfext##Op##_op<T>::id()] = pair_t(details::sfext##Op##_op<T>::process,details::e_sf4ext##Op); \
  29435. register_sf4ext(00) register_sf4ext(01) register_sf4ext(02) register_sf4ext(03)
  29436. register_sf4ext(04) register_sf4ext(05) register_sf4ext(06) register_sf4ext(07)
  29437. register_sf4ext(08) register_sf4ext(09) register_sf4ext(10) register_sf4ext(11)
  29438. register_sf4ext(12) register_sf4ext(13) register_sf4ext(14) register_sf4ext(15)
  29439. register_sf4ext(16) register_sf4ext(17) register_sf4ext(18) register_sf4ext(19)
  29440. register_sf4ext(20) register_sf4ext(21) register_sf4ext(22) register_sf4ext(23)
  29441. register_sf4ext(24) register_sf4ext(25) register_sf4ext(26) register_sf4ext(27)
  29442. register_sf4ext(28) register_sf4ext(29) register_sf4ext(30) register_sf4ext(31)
  29443. register_sf4ext(32) register_sf4ext(33) register_sf4ext(34) register_sf4ext(35)
  29444. register_sf4ext(36) register_sf4ext(36) register_sf4ext(38) register_sf4ext(39)
  29445. register_sf4ext(40) register_sf4ext(41) register_sf4ext(42) register_sf4ext(43)
  29446. register_sf4ext(44) register_sf4ext(45) register_sf4ext(46) register_sf4ext(47)
  29447. register_sf4ext(48) register_sf4ext(49) register_sf4ext(50) register_sf4ext(51)
  29448. register_sf4ext(52) register_sf4ext(53) register_sf4ext(54) register_sf4ext(55)
  29449. register_sf4ext(56) register_sf4ext(57) register_sf4ext(58) register_sf4ext(59)
  29450. register_sf4ext(60) register_sf4ext(61)
  29451. #undef register_sf4ext
  29452. }
  29453. inline results_context_t& results_ctx()
  29454. {
  29455. if (0 == results_context_)
  29456. {
  29457. results_context_ = new results_context_t();
  29458. }
  29459. return (*results_context_);
  29460. }
  29461. inline void return_cleanup()
  29462. {
  29463. #ifndef exprtk_disable_return_statement
  29464. if (results_context_)
  29465. {
  29466. delete results_context_;
  29467. results_context_ = 0;
  29468. }
  29469. state_.return_stmt_present = false;
  29470. #endif
  29471. }
  29472. private:
  29473. parser(const parser<T>&);
  29474. parser<T>& operator=(const parser<T>&);
  29475. settings_store settings_;
  29476. expression_generator<T> expression_generator_;
  29477. details::node_allocator node_allocator_;
  29478. symtab_store symtab_store_;
  29479. dependent_entity_collector dec_;
  29480. std::deque<parser_error::type> error_list_;
  29481. std::deque<bool> brkcnt_list_;
  29482. parser_state state_;
  29483. bool resolve_unknown_symbol_;
  29484. results_context_t* results_context_;
  29485. unknown_symbol_resolver* unknown_symbol_resolver_;
  29486. unknown_symbol_resolver default_usr_;
  29487. base_ops_map_t base_ops_map_;
  29488. unary_op_map_t unary_op_map_;
  29489. binary_op_map_t binary_op_map_;
  29490. inv_binary_op_map_t inv_binary_op_map_;
  29491. sf3_map_t sf3_map_;
  29492. sf4_map_t sf4_map_;
  29493. std::string synthesis_error_;
  29494. scope_element_manager sem_;
  29495. lexer::helper::helper_assembly helper_assembly_;
  29496. lexer::helper::commutative_inserter commutative_inserter_;
  29497. lexer::helper::operator_joiner operator_joiner_2_;
  29498. lexer::helper::operator_joiner operator_joiner_3_;
  29499. lexer::helper::symbol_replacer symbol_replacer_;
  29500. lexer::helper::bracket_checker bracket_checker_;
  29501. lexer::helper::numeric_checker numeric_checker_;
  29502. lexer::helper::sequence_validator sequence_validator_;
  29503. lexer::helper::sequence_validator_3tokens sequence_validator_3tkns_;
  29504. template <typename ParserType>
  29505. friend void details::disable_type_checking(ParserType& p);
  29506. };
  29507. namespace details
  29508. {
  29509. template <typename T>
  29510. struct collector_helper
  29511. {
  29512. typedef exprtk::symbol_table<T> symbol_table_t;
  29513. typedef exprtk::expression<T> expression_t;
  29514. typedef exprtk::parser<T> parser_t;
  29515. typedef typename parser_t::dependent_entity_collector::symbol_t symbol_t;
  29516. typedef typename parser_t::unknown_symbol_resolver usr_t;
  29517. struct resolve_as_vector : public parser_t::unknown_symbol_resolver
  29518. {
  29519. typedef exprtk::parser<T> parser_t;
  29520. resolve_as_vector()
  29521. : usr_t(usr_t::e_usrmode_extended)
  29522. {}
  29523. virtual bool process(const std::string& unknown_symbol,
  29524. symbol_table_t& symbol_table,
  29525. std::string&)
  29526. {
  29527. static T v[1];
  29528. symbol_table.add_vector(unknown_symbol,v);
  29529. return true;
  29530. }
  29531. };
  29532. static inline bool collection_pass(const std::string& expression_string,
  29533. std::set<std::string>& symbol_set,
  29534. const bool collect_variables,
  29535. const bool collect_functions,
  29536. const bool vector_pass,
  29537. symbol_table_t& ext_symbol_table)
  29538. {
  29539. symbol_table_t symbol_table;
  29540. expression_t expression;
  29541. parser_t parser;
  29542. resolve_as_vector vect_resolver;
  29543. expression.register_symbol_table(symbol_table );
  29544. expression.register_symbol_table(ext_symbol_table);
  29545. if (vector_pass)
  29546. parser.enable_unknown_symbol_resolver(&vect_resolver);
  29547. else
  29548. parser.enable_unknown_symbol_resolver();
  29549. if (collect_variables)
  29550. parser.dec().collect_variables() = true;
  29551. if (collect_functions)
  29552. parser.dec().collect_functions() = true;
  29553. bool pass_result = false;
  29554. details::disable_type_checking(parser);
  29555. if (parser.compile(expression_string, expression))
  29556. {
  29557. pass_result = true;
  29558. std::deque<symbol_t> symb_list;
  29559. parser.dec().symbols(symb_list);
  29560. for (std::size_t i = 0; i < symb_list.size(); ++i)
  29561. {
  29562. symbol_set.insert(symb_list[i].first);
  29563. }
  29564. }
  29565. return pass_result;
  29566. }
  29567. };
  29568. }
  29569. template <typename Allocator,
  29570. template <typename, typename> class Sequence>
  29571. inline bool collect_variables(const std::string& expression,
  29572. Sequence<std::string, Allocator>& symbol_list)
  29573. {
  29574. typedef double T;
  29575. typedef details::collector_helper<T> collect_t;
  29576. collect_t::symbol_table_t null_symbol_table;
  29577. std::set<std::string> symbol_set;
  29578. const bool variable_pass = collect_t::collection_pass
  29579. (expression, symbol_set, true, false, false, null_symbol_table);
  29580. const bool vector_pass = collect_t::collection_pass
  29581. (expression, symbol_set, true, false, true, null_symbol_table);
  29582. if (!variable_pass && !vector_pass)
  29583. return false;
  29584. std::set<std::string>::iterator itr = symbol_set.begin();
  29585. while (symbol_set.end() != itr)
  29586. {
  29587. symbol_list.push_back(*itr);
  29588. ++itr;
  29589. }
  29590. return true;
  29591. }
  29592. template <typename T,
  29593. typename Allocator,
  29594. template <typename, typename> class Sequence>
  29595. inline bool collect_variables(const std::string& expression,
  29596. exprtk::symbol_table<T>& extrnl_symbol_table,
  29597. Sequence<std::string, Allocator>& symbol_list)
  29598. {
  29599. typedef details::collector_helper<T> collect_t;
  29600. std::set<std::string> symbol_set;
  29601. const bool variable_pass = collect_t::collection_pass
  29602. (expression, symbol_set, true, false, false, extrnl_symbol_table);
  29603. const bool vector_pass = collect_t::collection_pass
  29604. (expression, symbol_set, true, false, true, extrnl_symbol_table);
  29605. if (!variable_pass && !vector_pass)
  29606. return false;
  29607. std::set<std::string>::iterator itr = symbol_set.begin();
  29608. while (symbol_set.end() != itr)
  29609. {
  29610. symbol_list.push_back(*itr);
  29611. ++itr;
  29612. }
  29613. return true;
  29614. }
  29615. template <typename Allocator,
  29616. template <typename, typename> class Sequence>
  29617. inline bool collect_functions(const std::string& expression,
  29618. Sequence<std::string, Allocator>& symbol_list)
  29619. {
  29620. typedef double T;
  29621. typedef details::collector_helper<T> collect_t;
  29622. collect_t::symbol_table_t null_symbol_table;
  29623. std::set<std::string> symbol_set;
  29624. const bool variable_pass = collect_t::collection_pass
  29625. (expression, symbol_set, false, true, false, null_symbol_table);
  29626. const bool vector_pass = collect_t::collection_pass
  29627. (expression, symbol_set, false, true, true, null_symbol_table);
  29628. if (!variable_pass && !vector_pass)
  29629. return false;
  29630. std::set<std::string>::iterator itr = symbol_set.begin();
  29631. while (symbol_set.end() != itr)
  29632. {
  29633. symbol_list.push_back(*itr);
  29634. ++itr;
  29635. }
  29636. return true;
  29637. }
  29638. template <typename T,
  29639. typename Allocator,
  29640. template <typename, typename> class Sequence>
  29641. inline bool collect_functions(const std::string& expression,
  29642. exprtk::symbol_table<T>& extrnl_symbol_table,
  29643. Sequence<std::string, Allocator>& symbol_list)
  29644. {
  29645. typedef details::collector_helper<T> collect_t;
  29646. std::set<std::string> symbol_set;
  29647. const bool variable_pass = collect_t::collection_pass
  29648. (expression, symbol_set, false, true, false, extrnl_symbol_table);
  29649. const bool vector_pass = collect_t::collection_pass
  29650. (expression, symbol_set, false, true, true, extrnl_symbol_table);
  29651. if (!variable_pass && !vector_pass)
  29652. return false;
  29653. std::set<std::string>::iterator itr = symbol_set.begin();
  29654. while (symbol_set.end() != itr)
  29655. {
  29656. symbol_list.push_back(*itr);
  29657. ++itr;
  29658. }
  29659. return true;
  29660. }
  29661. template <typename T>
  29662. inline T integrate(const expression<T>& e,
  29663. T& x,
  29664. const T& r0, const T& r1,
  29665. const std::size_t number_of_intervals = 1000000)
  29666. {
  29667. if (r0 > r1)
  29668. return T(0);
  29669. const T h = (r1 - r0) / (T(2) * number_of_intervals);
  29670. T total_area = T(0);
  29671. for (std::size_t i = 0; i < number_of_intervals; ++i)
  29672. {
  29673. x = r0 + T(2) * i * h;
  29674. const T y0 = e.value(); x += h;
  29675. const T y1 = e.value(); x += h;
  29676. const T y2 = e.value(); x += h;
  29677. total_area += h * (y0 + T(4) * y1 + y2) / T(3);
  29678. }
  29679. return total_area;
  29680. }
  29681. template <typename T>
  29682. inline T integrate(const expression<T>& e,
  29683. const std::string& variable_name,
  29684. const T& r0, const T& r1,
  29685. const std::size_t number_of_intervals = 1000000)
  29686. {
  29687. const symbol_table<T>& sym_table = e.get_symbol_table();
  29688. if (!sym_table.valid())
  29689. return std::numeric_limits<T>::quiet_NaN();
  29690. details::variable_node<T>* var = sym_table.get_variable(variable_name);
  29691. if (var)
  29692. {
  29693. T& x = var->ref();
  29694. T x_original = x;
  29695. T result = integrate(e, x, r0, r1, number_of_intervals);
  29696. x = x_original;
  29697. return result;
  29698. }
  29699. else
  29700. return std::numeric_limits<T>::quiet_NaN();
  29701. }
  29702. template <typename T>
  29703. inline T derivative(const expression<T>& e,
  29704. T& x,
  29705. const T& h = T(0.00000001))
  29706. {
  29707. const T x_init = x;
  29708. const T _2h = T(2) * h;
  29709. x = x_init + _2h;
  29710. const T y0 = e.value();
  29711. x = x_init + h;
  29712. const T y1 = e.value();
  29713. x = x_init - h;
  29714. const T y2 = e.value();
  29715. x = x_init - _2h;
  29716. const T y3 = e.value();
  29717. x = x_init;
  29718. return (-y0 + T(8) * (y1 - y2) + y3) / (T(12) * h);
  29719. }
  29720. template <typename T>
  29721. inline T second_derivative(const expression<T>& e,
  29722. T& x,
  29723. const T& h = T(0.00001))
  29724. {
  29725. const T x_init = x;
  29726. const T _2h = T(2) * h;
  29727. const T y = e.value();
  29728. x = x_init + _2h;
  29729. const T y0 = e.value();
  29730. x = x_init + h;
  29731. const T y1 = e.value();
  29732. x = x_init - h;
  29733. const T y2 = e.value();
  29734. x = x_init - _2h;
  29735. const T y3 = e.value();
  29736. x = x_init;
  29737. return (-y0 + T(16) * (y1 + y2) - T(30) * y - y3) / (T(12) * h * h);
  29738. }
  29739. template <typename T>
  29740. inline T third_derivative(const expression<T>& e,
  29741. T& x,
  29742. const T& h = T(0.0001))
  29743. {
  29744. const T x_init = x;
  29745. const T _2h = T(2) * h;
  29746. x = x_init + _2h;
  29747. const T y0 = e.value();
  29748. x = x_init + h;
  29749. const T y1 = e.value();
  29750. x = x_init - h;
  29751. const T y2 = e.value();
  29752. x = x_init - _2h;
  29753. const T y3 = e.value();
  29754. x = x_init;
  29755. return (y0 + T(2) * (y2 - y1) - y3) / (T(2) * h * h * h);
  29756. }
  29757. template <typename T>
  29758. inline T derivative(const expression<T>& e,
  29759. const std::string& variable_name,
  29760. const T& h = T(0.00000001))
  29761. {
  29762. const symbol_table<T>& sym_table = e.get_symbol_table();
  29763. if (!sym_table.valid())
  29764. {
  29765. return std::numeric_limits<T>::quiet_NaN();
  29766. }
  29767. details::variable_node<T>* var = sym_table.get_variable(variable_name);
  29768. if (var)
  29769. {
  29770. T& x = var->ref();
  29771. T x_original = x;
  29772. T result = derivative(e, x, h);
  29773. x = x_original;
  29774. return result;
  29775. }
  29776. else
  29777. return std::numeric_limits<T>::quiet_NaN();
  29778. }
  29779. template <typename T>
  29780. inline T second_derivative(const expression<T>& e,
  29781. const std::string& variable_name,
  29782. const T& h = T(0.00001))
  29783. {
  29784. const symbol_table<T>& sym_table = e.get_symbol_table();
  29785. if (!sym_table.valid())
  29786. {
  29787. return std::numeric_limits<T>::quiet_NaN();
  29788. }
  29789. details::variable_node<T>* var = sym_table.get_variable(variable_name);
  29790. if (var)
  29791. {
  29792. T& x = var->ref();
  29793. const T x_original = x;
  29794. const T result = second_derivative(e, x, h);
  29795. x = x_original;
  29796. return result;
  29797. }
  29798. else
  29799. return std::numeric_limits<T>::quiet_NaN();
  29800. }
  29801. template <typename T>
  29802. inline T third_derivative(const expression<T>& e,
  29803. const std::string& variable_name,
  29804. const T& h = T(0.0001))
  29805. {
  29806. const symbol_table<T>& sym_table = e.get_symbol_table();
  29807. if (!sym_table.valid())
  29808. {
  29809. return std::numeric_limits<T>::quiet_NaN();
  29810. }
  29811. details::variable_node<T>* var = sym_table.get_variable(variable_name);
  29812. if (var)
  29813. {
  29814. T& x = var->ref();
  29815. const T x_original = x;
  29816. const T result = third_derivative(e, x, h);
  29817. x = x_original;
  29818. return result;
  29819. }
  29820. else
  29821. return std::numeric_limits<T>::quiet_NaN();
  29822. }
  29823. /*
  29824. Note: The following 'compute' routines are simple helpers,
  29825. for quickly setting up the required pieces of code in order
  29826. to evaluate an expression. By virtue of how they operate
  29827. there will be an overhead with regards to their setup and
  29828. teardown and hence should not be used in time critical
  29829. sections of code.
  29830. Furthermore they only assume a small sub set of variables,
  29831. no string variables or user defined functions.
  29832. */
  29833. template <typename T>
  29834. inline bool compute(const std::string& expression_string, T& result)
  29835. {
  29836. // No variables
  29837. symbol_table<T> symbol_table;
  29838. symbol_table.add_constants();
  29839. expression<T> expression;
  29840. expression.register_symbol_table(symbol_table);
  29841. parser<T> parser;
  29842. if (parser.compile(expression_string,expression))
  29843. {
  29844. result = expression.value();
  29845. return true;
  29846. }
  29847. else
  29848. return false;
  29849. }
  29850. template <typename T>
  29851. inline bool compute(const std::string& expression_string,
  29852. const T& x,
  29853. T& result)
  29854. {
  29855. // Only 'x'
  29856. static const std::string x_var("x");
  29857. symbol_table<T> symbol_table;
  29858. symbol_table.add_constants();
  29859. symbol_table.add_constant(x_var,x);
  29860. expression<T> expression;
  29861. expression.register_symbol_table(symbol_table);
  29862. parser<T> parser;
  29863. if (parser.compile(expression_string,expression))
  29864. {
  29865. result = expression.value();
  29866. return true;
  29867. }
  29868. else
  29869. return false;
  29870. }
  29871. template <typename T>
  29872. inline bool compute(const std::string& expression_string,
  29873. const T&x, const T& y,
  29874. T& result)
  29875. {
  29876. // Only 'x' and 'y'
  29877. static const std::string x_var("x");
  29878. static const std::string y_var("y");
  29879. symbol_table<T> symbol_table;
  29880. symbol_table.add_constants();
  29881. symbol_table.add_constant(x_var,x);
  29882. symbol_table.add_constant(y_var,y);
  29883. expression<T> expression;
  29884. expression.register_symbol_table(symbol_table);
  29885. parser<T> parser;
  29886. if (parser.compile(expression_string,expression))
  29887. {
  29888. result = expression.value();
  29889. return true;
  29890. }
  29891. else
  29892. return false;
  29893. }
  29894. template <typename T>
  29895. inline bool compute(const std::string& expression_string,
  29896. const T& x, const T& y, const T& z,
  29897. T& result)
  29898. {
  29899. // Only 'x', 'y' or 'z'
  29900. static const std::string x_var("x");
  29901. static const std::string y_var("y");
  29902. static const std::string z_var("z");
  29903. symbol_table<T> symbol_table;
  29904. symbol_table.add_constants();
  29905. symbol_table.add_constant(x_var,x);
  29906. symbol_table.add_constant(y_var,y);
  29907. symbol_table.add_constant(z_var,z);
  29908. expression<T> expression;
  29909. expression.register_symbol_table(symbol_table);
  29910. parser<T> parser;
  29911. if (parser.compile(expression_string,expression))
  29912. {
  29913. result = expression.value();
  29914. return true;
  29915. }
  29916. else
  29917. return false;
  29918. }
  29919. template <typename T, std::size_t N>
  29920. class polynomial : public ifunction<T>
  29921. {
  29922. private:
  29923. template <typename Type, std::size_t NumberOfCoefficients>
  29924. struct poly_impl { };
  29925. template <typename Type>
  29926. struct poly_impl <Type,12>
  29927. {
  29928. static inline T evaluate(const Type x,
  29929. const Type c12, const Type c11, const Type c10, const Type c9, const Type c8,
  29930. const Type c7, const Type c6, const Type c5, const Type c4, const Type c3,
  29931. const Type c2, const Type c1, const Type c0)
  29932. {
  29933. // p(x) = c_12x^12 + c_11x^11 + c_10x^10 + c_9x^9 + c_8x^8 + c_7x^7 + c_6x^6 + c_5x^5 + c_4x^4 + c_3x^3 + c_2x^2 + c_1x^1 + c_0x^0
  29934. return ((((((((((((c12 * x + c11) * x + c10) * x + c9) * x + c8) * x + c7) * x + c6) * x + c5) * x + c4) * x + c3) * x + c2) * x + c1) * x + c0);
  29935. }
  29936. };
  29937. template <typename Type>
  29938. struct poly_impl <Type,11>
  29939. {
  29940. static inline T evaluate(const Type x,
  29941. const Type c11, const Type c10, const Type c9, const Type c8, const Type c7,
  29942. const Type c6, const Type c5, const Type c4, const Type c3, const Type c2,
  29943. const Type c1, const Type c0)
  29944. {
  29945. // p(x) = c_11x^11 + c_10x^10 + c_9x^9 + c_8x^8 + c_7x^7 + c_6x^6 + c_5x^5 + c_4x^4 + c_3x^3 + c_2x^2 + c_1x^1 + c_0x^0
  29946. return (((((((((((c11 * x + c10) * x + c9) * x + c8) * x + c7) * x + c6) * x + c5) * x + c4) * x + c3) * x + c2) * x + c1) * x + c0);
  29947. }
  29948. };
  29949. template <typename Type>
  29950. struct poly_impl <Type,10>
  29951. {
  29952. static inline T evaluate(const Type x,
  29953. const Type c10, const Type c9, const Type c8, const Type c7, const Type c6,
  29954. const Type c5, const Type c4, const Type c3, const Type c2, const Type c1,
  29955. const Type c0)
  29956. {
  29957. // p(x) = c_10x^10 + c_9x^9 + c_8x^8 + c_7x^7 + c_6x^6 + c_5x^5 + c_4x^4 + c_3x^3 + c_2x^2 + c_1x^1 + c_0x^0
  29958. return ((((((((((c10 * x + c9) * x + c8) * x + c7) * x + c6) * x + c5) * x + c4) * x + c3) * x + c2) * x + c1) * x + c0);
  29959. }
  29960. };
  29961. template <typename Type>
  29962. struct poly_impl <Type,9>
  29963. {
  29964. static inline T evaluate(const Type x,
  29965. const Type c9, const Type c8, const Type c7, const Type c6, const Type c5,
  29966. const Type c4, const Type c3, const Type c2, const Type c1, const Type c0)
  29967. {
  29968. // p(x) = c_9x^9 + c_8x^8 + c_7x^7 + c_6x^6 + c_5x^5 + c_4x^4 + c_3x^3 + c_2x^2 + c_1x^1 + c_0x^0
  29969. return (((((((((c9 * x + c8) * x + c7) * x + c6) * x + c5) * x + c4) * x + c3) * x + c2) * x + c1) * x + c0);
  29970. }
  29971. };
  29972. template <typename Type>
  29973. struct poly_impl <Type,8>
  29974. {
  29975. static inline T evaluate(const Type x,
  29976. const Type c8, const Type c7, const Type c6, const Type c5, const Type c4,
  29977. const Type c3, const Type c2, const Type c1, const Type c0)
  29978. {
  29979. // p(x) = c_8x^8 + c_7x^7 + c_6x^6 + c_5x^5 + c_4x^4 + c_3x^3 + c_2x^2 + c_1x^1 + c_0x^0
  29980. return ((((((((c8 * x + c7) * x + c6) * x + c5) * x + c4) * x + c3) * x + c2) * x + c1) * x + c0);
  29981. }
  29982. };
  29983. template <typename Type>
  29984. struct poly_impl <Type,7>
  29985. {
  29986. static inline T evaluate(const Type x,
  29987. const Type c7, const Type c6, const Type c5, const Type c4, const Type c3,
  29988. const Type c2, const Type c1, const Type c0)
  29989. {
  29990. // p(x) = c_7x^7 + c_6x^6 + c_5x^5 + c_4x^4 + c_3x^3 + c_2x^2 + c_1x^1 + c_0x^0
  29991. return (((((((c7 * x + c6) * x + c5) * x + c4) * x + c3) * x + c2) * x + c1) * x + c0);
  29992. }
  29993. };
  29994. template <typename Type>
  29995. struct poly_impl <Type,6>
  29996. {
  29997. static inline T evaluate(const Type x,
  29998. const Type c6, const Type c5, const Type c4, const Type c3, const Type c2,
  29999. const Type c1, const Type c0)
  30000. {
  30001. // p(x) = c_6x^6 + c_5x^5 + c_4x^4 + c_3x^3 + c_2x^2 + c_1x^1 + c_0x^0
  30002. return ((((((c6 * x + c5) * x + c4) * x + c3) * x + c2) * x + c1) * x + c0);
  30003. }
  30004. };
  30005. template <typename Type>
  30006. struct poly_impl <Type,5>
  30007. {
  30008. static inline T evaluate(const Type x,
  30009. const Type c5, const Type c4, const Type c3, const Type c2,
  30010. const Type c1, const Type c0)
  30011. {
  30012. // p(x) = c_5x^5 + c_4x^4 + c_3x^3 + c_2x^2 + c_1x^1 + c_0x^0
  30013. return (((((c5 * x + c4) * x + c3) * x + c2) * x + c1) * x + c0);
  30014. }
  30015. };
  30016. template <typename Type>
  30017. struct poly_impl <Type,4>
  30018. {
  30019. static inline T evaluate(const Type x, const Type c4, const Type c3, const Type c2, const Type c1, const Type c0)
  30020. {
  30021. // p(x) = c_4x^4 + c_3x^3 + c_2x^2 + c_1x^1 + c_0x^0
  30022. return ((((c4 * x + c3) * x + c2) * x + c1) * x + c0);
  30023. }
  30024. };
  30025. template <typename Type>
  30026. struct poly_impl <Type,3>
  30027. {
  30028. static inline T evaluate(const Type x, const Type c3, const Type c2, const Type c1, const Type c0)
  30029. {
  30030. // p(x) = c_3x^3 + c_2x^2 + c_1x^1 + c_0x^0
  30031. return (((c3 * x + c2) * x + c1) * x + c0);
  30032. }
  30033. };
  30034. template <typename Type>
  30035. struct poly_impl <Type,2>
  30036. {
  30037. static inline T evaluate(const Type x, const Type c2, const Type c1, const Type c0)
  30038. {
  30039. // p(x) = c_2x^2 + c_1x^1 + c_0x^0
  30040. return ((c2 * x + c1) * x + c0);
  30041. }
  30042. };
  30043. template <typename Type>
  30044. struct poly_impl <Type,1>
  30045. {
  30046. static inline T evaluate(const Type x, const Type c1, const Type c0)
  30047. {
  30048. // p(x) = c_1x^1 + c_0x^0
  30049. return (c1 * x + c0);
  30050. }
  30051. };
  30052. public:
  30053. using ifunction<T>::operator();
  30054. polynomial()
  30055. : ifunction<T>((N+2 <= 20) ? (N + 2) : std::numeric_limits<std::size_t>::max())
  30056. {
  30057. disable_has_side_effects(*this);
  30058. }
  30059. virtual ~polynomial()
  30060. {}
  30061. #define poly_rtrn(NN) \
  30062. return (NN != N) ? std::numeric_limits<T>::quiet_NaN() :
  30063. inline virtual T operator() (const T& x, const T& c1, const T& c0)
  30064. {
  30065. poly_rtrn(1) poly_impl<T,1>::evaluate(x, c1, c0);
  30066. }
  30067. inline virtual T operator() (const T& x, const T& c2, const T& c1, const T& c0)
  30068. {
  30069. poly_rtrn(2) poly_impl<T,2>::evaluate(x, c2, c1, c0);
  30070. }
  30071. inline virtual T operator() (const T& x, const T& c3, const T& c2, const T& c1, const T& c0)
  30072. {
  30073. poly_rtrn(3) poly_impl<T,3>::evaluate(x, c3, c2, c1, c0);
  30074. }
  30075. inline virtual T operator() (const T& x, const T& c4, const T& c3, const T& c2, const T& c1, const T& c0)
  30076. {
  30077. poly_rtrn(4) poly_impl<T,4>::evaluate(x, c4, c3, c2, c1, c0);
  30078. }
  30079. inline virtual T operator() (const T& x, const T& c5, const T& c4, const T& c3, const T& c2, const T& c1, const T& c0)
  30080. {
  30081. poly_rtrn(5) poly_impl<T,5>::evaluate(x, c5, c4, c3, c2, c1, c0);
  30082. }
  30083. inline virtual T operator() (const T& x, const T& c6, const T& c5, const T& c4, const T& c3, const T& c2, const T& c1, const T& c0)
  30084. {
  30085. poly_rtrn(6) poly_impl<T,6>::evaluate(x, c6, c5, c4, c3, c2, c1, c0);
  30086. }
  30087. inline virtual T operator() (const T& x, const T& c7, const T& c6, const T& c5, const T& c4, const T& c3, const T& c2, const T& c1, const T& c0)
  30088. {
  30089. poly_rtrn(7) poly_impl<T,7>::evaluate(x, c7, c6, c5, c4, c3, c2, c1, c0);
  30090. }
  30091. inline virtual T operator() (const T& x, const T& c8, const T& c7, const T& c6, const T& c5, const T& c4, const T& c3, const T& c2, const T& c1, const T& c0)
  30092. {
  30093. poly_rtrn(8) poly_impl<T,8>::evaluate(x, c8, c7, c6, c5, c4, c3, c2, c1, c0);
  30094. }
  30095. inline virtual T operator() (const T& x, const T& c9, const T& c8, const T& c7, const T& c6, const T& c5, const T& c4, const T& c3, const T& c2, const T& c1, const T& c0)
  30096. {
  30097. poly_rtrn(9) poly_impl<T,9>::evaluate(x, c9, c8, c7, c6, c5, c4, c3, c2, c1, c0);
  30098. }
  30099. inline virtual T operator() (const T& x, const T& c10, const T& c9, const T& c8, const T& c7, const T& c6, const T& c5, const T& c4, const T& c3, const T& c2, const T& c1, const T& c0)
  30100. {
  30101. poly_rtrn(10) poly_impl<T,10>::evaluate(x, c10, c9, c8, c7, c6, c5, c4, c3, c2, c1, c0);
  30102. }
  30103. inline virtual T operator() (const T& x, const T& c11, const T& c10, const T& c9, const T& c8, const T& c7, const T& c6, const T& c5, const T& c4, const T& c3, const T& c2, const T& c1, const T& c0)
  30104. {
  30105. poly_rtrn(11) poly_impl<T,11>::evaluate(x, c11, c10, c9, c8, c7, c6, c5, c4, c3, c2, c1, c0);
  30106. }
  30107. inline virtual T operator() (const T& x, const T& c12, const T& c11, const T& c10, const T& c9, const T& c8, const T& c7, const T& c6, const T& c5, const T& c4, const T& c3, const T& c2, const T& c1, const T& c0)
  30108. {
  30109. poly_rtrn(12) poly_impl<T,12>::evaluate(x, c12, c11, c10, c9, c8, c7, c6, c5, c4, c3, c2, c1, c0);
  30110. }
  30111. #undef poly_rtrn
  30112. inline virtual T operator() ()
  30113. {
  30114. return std::numeric_limits<T>::quiet_NaN();
  30115. }
  30116. inline virtual T operator() (const T&)
  30117. {
  30118. return std::numeric_limits<T>::quiet_NaN();
  30119. }
  30120. inline virtual T operator() (const T&, const T&)
  30121. {
  30122. return std::numeric_limits<T>::quiet_NaN();
  30123. }
  30124. };
  30125. template <typename T>
  30126. class function_compositor
  30127. {
  30128. public:
  30129. typedef exprtk::expression<T> expression_t;
  30130. typedef exprtk::symbol_table<T> symbol_table_t;
  30131. typedef exprtk::parser<T> parser_t;
  30132. typedef typename parser_t::settings_store settings_t;
  30133. struct function
  30134. {
  30135. function()
  30136. {}
  30137. function(const std::string& n)
  30138. : name_(n)
  30139. {}
  30140. function(const std::string& name,
  30141. const std::string& expression)
  30142. : name_(name),
  30143. expression_(expression)
  30144. {}
  30145. function(const std::string& name,
  30146. const std::string& expression,
  30147. const std::string& v0)
  30148. : name_(name),
  30149. expression_(expression)
  30150. {
  30151. v_.push_back(v0);
  30152. }
  30153. function(const std::string& name,
  30154. const std::string& expression,
  30155. const std::string& v0, const std::string& v1)
  30156. : name_(name),
  30157. expression_(expression)
  30158. {
  30159. v_.push_back(v0); v_.push_back(v1);
  30160. }
  30161. function(const std::string& name,
  30162. const std::string& expression,
  30163. const std::string& v0, const std::string& v1,
  30164. const std::string& v2)
  30165. : name_(name),
  30166. expression_(expression)
  30167. {
  30168. v_.push_back(v0); v_.push_back(v1);
  30169. v_.push_back(v2);
  30170. }
  30171. function(const std::string& name,
  30172. const std::string& expression,
  30173. const std::string& v0, const std::string& v1,
  30174. const std::string& v2, const std::string& v3)
  30175. : name_(name),
  30176. expression_(expression)
  30177. {
  30178. v_.push_back(v0); v_.push_back(v1);
  30179. v_.push_back(v2); v_.push_back(v3);
  30180. }
  30181. function(const std::string& name,
  30182. const std::string& expression,
  30183. const std::string& v0, const std::string& v1,
  30184. const std::string& v2, const std::string& v3,
  30185. const std::string& v4)
  30186. : name_(name),
  30187. expression_(expression)
  30188. {
  30189. v_.push_back(v0); v_.push_back(v1);
  30190. v_.push_back(v2); v_.push_back(v3);
  30191. v_.push_back(v4);
  30192. }
  30193. inline function& name(const std::string& n)
  30194. {
  30195. name_ = n;
  30196. return (*this);
  30197. }
  30198. inline function& expression(const std::string& e)
  30199. {
  30200. expression_ = e;
  30201. return (*this);
  30202. }
  30203. inline function& var(const std::string& v)
  30204. {
  30205. v_.push_back(v);
  30206. return (*this);
  30207. }
  30208. std::string name_;
  30209. std::string expression_;
  30210. std::deque<std::string> v_;
  30211. };
  30212. private:
  30213. struct base_func : public exprtk::ifunction<T>
  30214. {
  30215. typedef const T& type;
  30216. typedef exprtk::ifunction<T> function_t;
  30217. typedef std::vector<T*> varref_t;
  30218. typedef std::vector<T> var_t;
  30219. typedef std::pair<T*,std::size_t> lvarref_t;
  30220. typedef std::vector<lvarref_t> lvr_vec_t;
  30221. using exprtk::ifunction<T>::operator();
  30222. base_func(const std::size_t& pc = 0)
  30223. : exprtk::ifunction<T>(pc),
  30224. local_var_stack_size(0),
  30225. stack_depth(0)
  30226. {
  30227. v.resize(pc);
  30228. }
  30229. virtual ~base_func()
  30230. {}
  30231. inline void update(const T& v0)
  30232. {
  30233. (*v[0]) = v0;
  30234. }
  30235. inline void update(const T& v0, const T& v1)
  30236. {
  30237. (*v[0]) = v0; (*v[1]) = v1;
  30238. }
  30239. inline void update(const T& v0, const T& v1, const T& v2)
  30240. {
  30241. (*v[0]) = v0; (*v[1]) = v1;
  30242. (*v[2]) = v2;
  30243. }
  30244. inline void update(const T& v0, const T& v1, const T& v2, const T& v3)
  30245. {
  30246. (*v[0]) = v0; (*v[1]) = v1;
  30247. (*v[2]) = v2; (*v[3]) = v3;
  30248. }
  30249. inline void update(const T& v0, const T& v1, const T& v2, const T& v3, const T& v4)
  30250. {
  30251. (*v[0]) = v0; (*v[1]) = v1;
  30252. (*v[2]) = v2; (*v[3]) = v3;
  30253. (*v[4]) = v4;
  30254. }
  30255. inline void update(const T& v0, const T& v1, const T& v2, const T& v3, const T& v4, const T& v5)
  30256. {
  30257. (*v[0]) = v0; (*v[1]) = v1;
  30258. (*v[2]) = v2; (*v[3]) = v3;
  30259. (*v[4]) = v4; (*v[5]) = v5;
  30260. }
  30261. inline function_t& setup(expression_t& expr)
  30262. {
  30263. expression = expr;
  30264. typedef typename expression_t::control_block::local_data_list_t ldl_t;
  30265. ldl_t ldl = expr.local_data_list();
  30266. std::vector<std::size_t> index_list;
  30267. for (std::size_t i = 0; i < ldl.size(); ++i)
  30268. {
  30269. if (ldl[i].size)
  30270. {
  30271. index_list.push_back(i);
  30272. }
  30273. }
  30274. std::size_t input_param_count = 0;
  30275. for (std::size_t i = 0; i < index_list.size(); ++i)
  30276. {
  30277. const std::size_t index = index_list[i];
  30278. if (i < (index_list.size() - v.size()))
  30279. {
  30280. lv.push_back(
  30281. std::make_pair(
  30282. reinterpret_cast<T*>(ldl[index].pointer),
  30283. ldl[index].size));
  30284. local_var_stack_size += ldl[index].size;
  30285. }
  30286. else
  30287. v[input_param_count++] = reinterpret_cast<T*>(ldl[index].pointer);
  30288. }
  30289. clear_stack();
  30290. return (*this);
  30291. }
  30292. inline void pre()
  30293. {
  30294. if (stack_depth++)
  30295. {
  30296. if (!v.empty())
  30297. {
  30298. var_t var_stack(v.size(),T(0));
  30299. copy(v,var_stack);
  30300. param_stack.push_back(var_stack);
  30301. }
  30302. if (!lv.empty())
  30303. {
  30304. var_t local_var_stack(local_var_stack_size,T(0));
  30305. copy(lv,local_var_stack);
  30306. local_stack.push_back(local_var_stack);
  30307. }
  30308. }
  30309. }
  30310. inline void post()
  30311. {
  30312. if (--stack_depth)
  30313. {
  30314. if (!v.empty())
  30315. {
  30316. copy(param_stack.back(),v);
  30317. param_stack.pop_back();
  30318. }
  30319. if (!lv.empty())
  30320. {
  30321. copy(local_stack.back(),lv);
  30322. local_stack.pop_back();
  30323. }
  30324. }
  30325. }
  30326. void copy(const varref_t& src_v, var_t& dest_v)
  30327. {
  30328. for (std::size_t i = 0; i < src_v.size(); ++i)
  30329. {
  30330. dest_v[i] = (*src_v[i]);
  30331. }
  30332. }
  30333. void copy(const var_t& src_v, varref_t& dest_v)
  30334. {
  30335. for (std::size_t i = 0; i < src_v.size(); ++i)
  30336. {
  30337. (*dest_v[i]) = src_v[i];
  30338. }
  30339. }
  30340. void copy(const lvr_vec_t& src_v, var_t& dest_v)
  30341. {
  30342. typename var_t::iterator itr = dest_v.begin();
  30343. typedef typename std::iterator_traits<typename var_t::iterator>::difference_type diff_t;
  30344. for (std::size_t i = 0; i < src_v.size(); ++i)
  30345. {
  30346. lvarref_t vr = src_v[i];
  30347. if (1 == vr.second)
  30348. *itr++ = (*vr.first);
  30349. else
  30350. {
  30351. std::copy(vr.first, vr.first + vr.second, itr);
  30352. itr += static_cast<diff_t>(vr.second);
  30353. }
  30354. }
  30355. }
  30356. void copy(const var_t& src_v, lvr_vec_t& dest_v)
  30357. {
  30358. typename var_t::const_iterator itr = src_v.begin();
  30359. typedef typename std::iterator_traits<typename var_t::iterator>::difference_type diff_t;
  30360. for (std::size_t i = 0; i < src_v.size(); ++i)
  30361. {
  30362. lvarref_t vr = dest_v[i];
  30363. if (1 == vr.second)
  30364. (*vr.first) = *itr++;
  30365. else
  30366. {
  30367. std::copy(itr, itr + static_cast<diff_t>(vr.second), vr.first);
  30368. itr += static_cast<diff_t>(vr.second);
  30369. }
  30370. }
  30371. }
  30372. inline void clear_stack()
  30373. {
  30374. for (std::size_t i = 0; i < v.size(); ++i)
  30375. {
  30376. (*v[i]) = 0;
  30377. }
  30378. }
  30379. inline virtual T value(expression_t& e)
  30380. {
  30381. return e.value();
  30382. }
  30383. expression_t expression;
  30384. varref_t v;
  30385. lvr_vec_t lv;
  30386. std::size_t local_var_stack_size;
  30387. std::size_t stack_depth;
  30388. std::deque<var_t> param_stack;
  30389. std::deque<var_t> local_stack;
  30390. };
  30391. typedef std::map<std::string,base_func*> funcparam_t;
  30392. struct func_0param : public base_func
  30393. {
  30394. using exprtk::ifunction<T>::operator();
  30395. func_0param() : base_func(0) {}
  30396. inline T operator() ()
  30397. {
  30398. return this->value(base_func::expression);
  30399. }
  30400. };
  30401. typedef const T& type;
  30402. template <typename BaseFuncType>
  30403. struct scoped_bft
  30404. {
  30405. scoped_bft(BaseFuncType& bft) : bft_(bft) { bft_.pre (); }
  30406. ~scoped_bft() { bft_.post(); }
  30407. BaseFuncType& bft_;
  30408. private:
  30409. scoped_bft(scoped_bft&);
  30410. scoped_bft& operator=(scoped_bft&);
  30411. };
  30412. struct func_1param : public base_func
  30413. {
  30414. using exprtk::ifunction<T>::operator();
  30415. func_1param() : base_func(1) {}
  30416. inline T operator() (type v0)
  30417. {
  30418. scoped_bft<func_1param> sb(*this);
  30419. base_func::update(v0);
  30420. return this->value(base_func::expression);
  30421. }
  30422. };
  30423. struct func_2param : public base_func
  30424. {
  30425. using exprtk::ifunction<T>::operator();
  30426. func_2param() : base_func(2) {}
  30427. inline T operator() (type v0, type v1)
  30428. {
  30429. scoped_bft<func_2param> sb(*this);
  30430. base_func::update(v0, v1);
  30431. return this->value(base_func::expression);
  30432. }
  30433. };
  30434. struct func_3param : public base_func
  30435. {
  30436. using exprtk::ifunction<T>::operator();
  30437. func_3param() : base_func(3) {}
  30438. inline T operator() (type v0, type v1, type v2)
  30439. {
  30440. scoped_bft<func_3param> sb(*this);
  30441. base_func::update(v0, v1, v2);
  30442. return this->value(base_func::expression);
  30443. }
  30444. };
  30445. struct func_4param : public base_func
  30446. {
  30447. using exprtk::ifunction<T>::operator();
  30448. func_4param() : base_func(4) {}
  30449. inline T operator() (type v0, type v1, type v2, type v3)
  30450. {
  30451. scoped_bft<func_4param> sb(*this);
  30452. base_func::update(v0, v1, v2, v3);
  30453. return this->value(base_func::expression);
  30454. }
  30455. };
  30456. struct func_5param : public base_func
  30457. {
  30458. using exprtk::ifunction<T>::operator();
  30459. func_5param() : base_func(5) {}
  30460. inline T operator() (type v0, type v1, type v2, type v3, type v4)
  30461. {
  30462. scoped_bft<func_5param> sb(*this);
  30463. base_func::update(v0, v1, v2, v3, v4);
  30464. return this->value(base_func::expression);
  30465. }
  30466. };
  30467. struct func_6param : public base_func
  30468. {
  30469. using exprtk::ifunction<T>::operator();
  30470. func_6param() : base_func(6) {}
  30471. inline T operator() (type v0, type v1, type v2, type v3, type v4, type v5)
  30472. {
  30473. scoped_bft<func_6param> sb(*this);
  30474. base_func::update(v0, v1, v2, v3, v4, v5);
  30475. return this->value(base_func::expression);
  30476. }
  30477. };
  30478. static T return_value(expression_t& e)
  30479. {
  30480. typedef exprtk::results_context<T> results_context_t;
  30481. typedef typename results_context_t::type_store_t type_t;
  30482. typedef typename type_t::scalar_view scalar_t;
  30483. T result = e.value();
  30484. if (e.return_invoked())
  30485. {
  30486. // Due to the post compilation checks, it can be safely
  30487. // assumed that there will be at least one parameter
  30488. // and that the first parameter will always be scalar.
  30489. return scalar_t(e.results()[0])();
  30490. }
  30491. return result;
  30492. }
  30493. #define def_fp_retval(N) \
  30494. struct func_##N##param_retval : public func_##N##param \
  30495. { \
  30496. inline T value(expression_t& e) \
  30497. { \
  30498. return return_value(e); \
  30499. } \
  30500. }; \
  30501. def_fp_retval(0)
  30502. def_fp_retval(1)
  30503. def_fp_retval(2)
  30504. def_fp_retval(3)
  30505. def_fp_retval(4)
  30506. def_fp_retval(5)
  30507. def_fp_retval(6)
  30508. template <typename Allocator,
  30509. template <typename, typename> class Sequence>
  30510. inline bool add(const std::string& name,
  30511. const std::string& expression,
  30512. const Sequence<std::string,Allocator>& var_list,
  30513. const bool override = false)
  30514. {
  30515. const typename std::map<std::string,expression_t>::iterator itr = expr_map_.find(name);
  30516. if (expr_map_.end() != itr)
  30517. {
  30518. if (!override)
  30519. {
  30520. exprtk_debug(("Compositor error(add): function '%s' already defined\n",
  30521. name.c_str()));
  30522. return false;
  30523. }
  30524. remove(name, var_list.size());
  30525. }
  30526. if (compile_expression(name,expression,var_list))
  30527. {
  30528. const std::size_t n = var_list.size();
  30529. fp_map_[n][name]->setup(expr_map_[name]);
  30530. return true;
  30531. }
  30532. else
  30533. {
  30534. exprtk_debug(("Compositor error(add): Failed to compile function '%s'\n",
  30535. name.c_str()));
  30536. return false;
  30537. }
  30538. }
  30539. public:
  30540. function_compositor()
  30541. : parser_(settings_t::compile_all_opts +
  30542. settings_t::e_disable_zero_return),
  30543. fp_map_(7)
  30544. {}
  30545. function_compositor(const symbol_table_t& st)
  30546. : symbol_table_(st),
  30547. parser_(settings_t::compile_all_opts +
  30548. settings_t::e_disable_zero_return),
  30549. fp_map_(7)
  30550. {}
  30551. ~function_compositor()
  30552. {
  30553. clear();
  30554. }
  30555. inline symbol_table_t& symbol_table()
  30556. {
  30557. return symbol_table_;
  30558. }
  30559. inline void add_auxiliary_symtab(symbol_table_t& symtab)
  30560. {
  30561. auxiliary_symtab_list_.push_back(&symtab);
  30562. }
  30563. void clear()
  30564. {
  30565. symbol_table_.clear();
  30566. expr_map_ .clear();
  30567. for (std::size_t i = 0; i < fp_map_.size(); ++i)
  30568. {
  30569. typename funcparam_t::iterator itr = fp_map_[i].begin();
  30570. typename funcparam_t::iterator end = fp_map_[i].end ();
  30571. while (itr != end)
  30572. {
  30573. delete itr->second;
  30574. ++itr;
  30575. }
  30576. fp_map_[i].clear();
  30577. }
  30578. }
  30579. inline bool add(const function& f, const bool override = false)
  30580. {
  30581. return add(f.name_, f.expression_, f.v_,override);
  30582. }
  30583. private:
  30584. template <typename Allocator,
  30585. template <typename, typename> class Sequence>
  30586. bool compile_expression(const std::string& name,
  30587. const std::string& expression,
  30588. const Sequence<std::string,Allocator>& input_var_list,
  30589. bool return_present = false)
  30590. {
  30591. expression_t compiled_expression;
  30592. symbol_table_t local_symbol_table;
  30593. local_symbol_table.load_from(symbol_table_);
  30594. local_symbol_table.add_constants();
  30595. if (!valid(name,input_var_list.size()))
  30596. return false;
  30597. if (!forward(name,
  30598. input_var_list.size(),
  30599. local_symbol_table,
  30600. return_present))
  30601. return false;
  30602. compiled_expression.register_symbol_table(local_symbol_table);
  30603. for (std::size_t i = 0; i < auxiliary_symtab_list_.size(); ++i)
  30604. {
  30605. compiled_expression.register_symbol_table((*auxiliary_symtab_list_[i]));
  30606. }
  30607. std::string mod_expression;
  30608. for (std::size_t i = 0; i < input_var_list.size(); ++i)
  30609. {
  30610. mod_expression += " var " + input_var_list[i] + "{};\n";
  30611. }
  30612. if (
  30613. ('{' == details::front(expression)) &&
  30614. ('}' == details::back (expression))
  30615. )
  30616. mod_expression += "~" + expression + ";";
  30617. else
  30618. mod_expression += "~{" + expression + "};";
  30619. if (!parser_.compile(mod_expression,compiled_expression))
  30620. {
  30621. exprtk_debug(("Compositor Error: %s\n",parser_.error().c_str()));
  30622. exprtk_debug(("Compositor modified expression: \n%s\n",mod_expression.c_str()));
  30623. remove(name,input_var_list.size());
  30624. return false;
  30625. }
  30626. if (!return_present && parser_.dec().return_present())
  30627. {
  30628. remove(name,input_var_list.size());
  30629. return compile_expression(name, expression, input_var_list, true);
  30630. }
  30631. // Make sure every return point has a scalar as its first parameter
  30632. if (parser_.dec().return_present())
  30633. {
  30634. typedef std::vector<std::string> str_list_t;
  30635. str_list_t ret_param_list = parser_.dec().return_param_type_list();
  30636. for (std::size_t i = 0; i < ret_param_list.size(); ++i)
  30637. {
  30638. const std::string& params = ret_param_list[i];
  30639. if (params.empty() || ('T' != params[0]))
  30640. {
  30641. exprtk_debug(("Compositor Error: Return statement in function '%s' is invalid\n",
  30642. name.c_str()));
  30643. remove(name,input_var_list.size());
  30644. return false;
  30645. }
  30646. }
  30647. }
  30648. expr_map_[name] = compiled_expression;
  30649. exprtk::ifunction<T>& ifunc = (*(fp_map_[input_var_list.size()])[name]);
  30650. if (symbol_table_.add_function(name,ifunc))
  30651. return true;
  30652. else
  30653. {
  30654. exprtk_debug(("Compositor Error: Failed to add function '%s' to symbol table\n",
  30655. name.c_str()));
  30656. return false;
  30657. }
  30658. }
  30659. inline bool symbol_used(const std::string& symbol) const
  30660. {
  30661. return (
  30662. symbol_table_.is_variable (symbol) ||
  30663. symbol_table_.is_stringvar (symbol) ||
  30664. symbol_table_.is_function (symbol) ||
  30665. symbol_table_.is_vector (symbol) ||
  30666. symbol_table_.is_vararg_function(symbol)
  30667. );
  30668. }
  30669. inline bool valid(const std::string& name,
  30670. const std::size_t& arg_count) const
  30671. {
  30672. if (arg_count > 6)
  30673. return false;
  30674. else if (symbol_used(name))
  30675. return false;
  30676. else if (fp_map_[arg_count].end() != fp_map_[arg_count].find(name))
  30677. return false;
  30678. else
  30679. return true;
  30680. }
  30681. inline bool forward(const std::string& name,
  30682. const std::size_t& arg_count,
  30683. symbol_table_t& sym_table,
  30684. const bool ret_present = false)
  30685. {
  30686. switch (arg_count)
  30687. {
  30688. #define case_stmt(N) \
  30689. case N : (fp_map_[arg_count])[name] = \
  30690. (!ret_present) ? static_cast<base_func*> \
  30691. (new func_##N##param) : \
  30692. static_cast<base_func*> \
  30693. (new func_##N##param_retval) ; \
  30694. break; \
  30695. case_stmt(0) case_stmt(1) case_stmt(2)
  30696. case_stmt(3) case_stmt(4) case_stmt(5)
  30697. case_stmt(6)
  30698. #undef case_stmt
  30699. }
  30700. exprtk::ifunction<T>& ifunc = (*(fp_map_[arg_count])[name]);
  30701. return sym_table.add_function(name,ifunc);
  30702. }
  30703. inline void remove(const std::string& name, const std::size_t& arg_count)
  30704. {
  30705. if (arg_count > 6)
  30706. return;
  30707. const typename std::map<std::string,expression_t>::iterator em_itr = expr_map_.find(name);
  30708. if (expr_map_.end() != em_itr)
  30709. {
  30710. expr_map_.erase(em_itr);
  30711. }
  30712. const typename funcparam_t::iterator fp_itr = fp_map_[arg_count].find(name);
  30713. if (fp_map_[arg_count].end() != fp_itr)
  30714. {
  30715. delete fp_itr->second;
  30716. fp_map_[arg_count].erase(fp_itr);
  30717. }
  30718. symbol_table_.remove_function(name);
  30719. }
  30720. private:
  30721. symbol_table_t symbol_table_;
  30722. parser_t parser_;
  30723. std::map<std::string,expression_t> expr_map_;
  30724. std::vector<funcparam_t> fp_map_;
  30725. std::vector<symbol_table_t*> auxiliary_symtab_list_;
  30726. };
  30727. template <typename T>
  30728. inline bool pgo_primer()
  30729. {
  30730. static const std::string expression_list[] =
  30731. {
  30732. "(y + x)",
  30733. "2 * (y + x)",
  30734. "(2 * y + 2 * x)",
  30735. "(y + x / y) * (x - y / x)",
  30736. "x / ((x + y) * (x - y)) / y",
  30737. "1 - ((x * y) + (y / x)) - 3",
  30738. "sin(2 * x) + cos(pi / y)",
  30739. "1 - sin(2 * x) + cos(pi / y)",
  30740. "sqrt(1 - sin(2 * x) + cos(pi / y) / 3)",
  30741. "(x^2 / sin(2 * pi / y)) -x / 2",
  30742. "x + (cos(y - sin(2 / x * pi)) - sin(x - cos(2 * y / pi))) - y",
  30743. "clamp(-1.0, sin(2 * pi * x) + cos(y / 2 * pi), +1.0)",
  30744. "iclamp(-1.0, sin(2 * pi * x) + cos(y / 2 * pi), +1.0)",
  30745. "max(3.33, min(sqrt(1 - sin(2 * x) + cos(pi / y) / 3), 1.11))",
  30746. "if(avg(x,y) <= x + y, x - y, x * y) + 2 * pi / x",
  30747. "1.1x^1 + 2.2y^2 - 3.3x^3 + 4.4y^4 - 5.5x^5 + 6.6y^6 - 7.7x^27 + 8.8y^55",
  30748. "(yy + xx)",
  30749. "2 * (yy + xx)",
  30750. "(2 * yy + 2 * xx)",
  30751. "(yy + xx / yy) * (xx - yy / xx)",
  30752. "xx / ((xx + yy) * (xx - yy)) / yy",
  30753. "1 - ((xx * yy) + (yy / xx)) - 3",
  30754. "sin(2 * xx) + cos(pi / yy)",
  30755. "1 - sin(2 * xx) + cos(pi / yy)",
  30756. "sqrt(1 - sin(2 * xx) + cos(pi / yy) / 3)",
  30757. "(xx^2 / sin(2 * pi / yy)) -xx / 2",
  30758. "xx + (cos(yy - sin(2 / xx * pi)) - sin(xx - cos(2 * yy / pi))) - yy",
  30759. "clamp(-1.0, sin(2 * pi * xx) + cos(yy / 2 * pi), +1.0)",
  30760. "max(3.33, min(sqrt(1 - sin(2 * xx) + cos(pi / yy) / 3), 1.11))",
  30761. "if(avg(xx,yy) <= xx + yy, xx - yy, xx * yy) + 2 * pi / xx",
  30762. "1.1xx^1 + 2.2yy^2 - 3.3xx^3 + 4.4yy^4 - 5.5xx^5 + 6.6yy^6 - 7.7xx^27 + 8.8yy^55",
  30763. "(1.1*(2.2*(3.3*(4.4*(5.5*(6.6*(7.7*(8.8*(9.9+x)))))))))",
  30764. "(((((((((x+9.9)*8.8)*7.7)*6.6)*5.5)*4.4)*3.3)*2.2)*1.1)",
  30765. "(x + y) * z", "x + (y * z)", "(x + y) * 7", "x + (y * 7)",
  30766. "(x + 7) * y", "x + (7 * y)", "(7 + x) * y", "7 + (x * y)",
  30767. "(2 + x) * 3", "2 + (x * 3)", "(2 + 3) * x", "2 + (3 * x)",
  30768. "(x + 2) * 3", "x + (2 * 3)",
  30769. "(x + y) * (z / w)", "(x + y) * (z / 7)", "(x + y) * (7 / z)", "(x + 7) * (y / z)",
  30770. "(7 + x) * (y / z)", "(2 + x) * (y / z)", "(x + 2) * (y / 3)", "(2 + x) * (y / 3)",
  30771. "(x + 2) * (3 / y)", "x + (y * (z / w))", "x + (y * (z / 7))", "x + (y * (7 / z))",
  30772. "x + (7 * (y / z))", "7 + (x * (y / z))", "2 + (x * (3 / y))", "x + (2 * (y / 4))",
  30773. "2 + (x * (y / 3))", "x + (2 * (3 / y))",
  30774. "x + ((y * z) / w)", "x + ((y * z) / 7)", "x + ((y * 7) / z)", "x + ((7 * y) / z)",
  30775. "7 + ((y * z) / w)", "2 + ((x * 3) / y)", "x + ((2 * y) / 3)", "2 + ((x * y) / 3)",
  30776. "x + ((2 * 3) / y)", "(((x + y) * z) / w)",
  30777. "(((x + y) * z) / 7)", "(((x + y) * 7) / z)", "(((x + 7) * y) / z)", "(((7 + x) * y) / z)",
  30778. "(((2 + x) * 3) / y)", "(((x + 2) * y) / 3)", "(((2 + x) * y) / 3)", "(((x + 2) * 3) / y)",
  30779. "((x + (y * z)) / w)", "((x + (y * z)) / 7)", "((x + (y * 7)) / y)", "((x + (7 * y)) / z)",
  30780. "((7 + (x * y)) / z)", "((2 + (x * 3)) / y)", "((x + (2 * y)) / 3)", "((2 + (x * y)) / 3)",
  30781. "((x + (2 * 3)) / y)",
  30782. "(xx + yy) * zz", "xx + (yy * zz)",
  30783. "(xx + yy) * 7", "xx + (yy * 7)",
  30784. "(xx + 7) * yy", "xx + (7 * yy)",
  30785. "(7 + xx) * yy", "7 + (xx * yy)",
  30786. "(2 + x) * 3", "2 + (x * 3)",
  30787. "(2 + 3) * x", "2 + (3 * x)",
  30788. "(x + 2) * 3", "x + (2 * 3)",
  30789. "(xx + yy) * (zz / ww)", "(xx + yy) * (zz / 7)",
  30790. "(xx + yy) * (7 / zz)", "(xx + 7) * (yy / zz)",
  30791. "(7 + xx) * (yy / zz)", "(2 + xx) * (yy / zz)",
  30792. "(xx + 2) * (yy / 3)", "(2 + xx) * (yy / 3)",
  30793. "(xx + 2) * (3 / yy)", "xx + (yy * (zz / ww))",
  30794. "xx + (yy * (zz / 7))", "xx + (yy * (7 / zz))",
  30795. "xx + (7 * (yy / zz))", "7 + (xx * (yy / zz))",
  30796. "2 + (xx * (3 / yy))", "xx + (2 * (yy / 4))",
  30797. "2 + (xx * (yy / 3))", "xx + (2 * (3 / yy))",
  30798. "xx + ((yy * zz) / ww)", "xx + ((yy * zz) / 7)",
  30799. "xx + ((yy * 7) / zz)", "xx + ((7 * yy) / zz)",
  30800. "7 + ((yy * zz) / ww)", "2 + ((xx * 3) / yy)",
  30801. "xx + ((2 * yy) / 3)", "2 + ((xx * yy) / 3)",
  30802. "xx + ((2 * 3) / yy)", "(((xx + yy) * zz) / ww)",
  30803. "(((xx + yy) * zz) / 7)", "(((xx + yy) * 7) / zz)",
  30804. "(((xx + 7) * yy) / zz)", "(((7 + xx) * yy) / zz)",
  30805. "(((2 + xx) * 3) / yy)", "(((xx + 2) * yy) / 3)",
  30806. "(((2 + xx) * yy) / 3)", "(((xx + 2) * 3) / yy)",
  30807. "((xx + (yy * zz)) / ww)", "((xx + (yy * zz)) / 7)",
  30808. "((xx + (yy * 7)) / yy)", "((xx + (7 * yy)) / zz)",
  30809. "((7 + (xx * yy)) / zz)", "((2 + (xx * 3)) / yy)",
  30810. "((xx + (2 * yy)) / 3)", "((2 + (xx * yy)) / 3)",
  30811. "((xx + (2 * 3)) / yy)"
  30812. };
  30813. static const std::size_t expression_list_size = sizeof(expression_list) / sizeof(std::string);
  30814. T x = T(0);
  30815. T y = T(0);
  30816. T z = T(0);
  30817. T w = T(0);
  30818. T xx = T(0);
  30819. T yy = T(0);
  30820. T zz = T(0);
  30821. T ww = T(0);
  30822. exprtk::symbol_table<T> symbol_table;
  30823. symbol_table.add_constants();
  30824. symbol_table.add_variable( "x", x);
  30825. symbol_table.add_variable( "y", y);
  30826. symbol_table.add_variable( "z", z);
  30827. symbol_table.add_variable( "w", w);
  30828. symbol_table.add_variable("xx",xx);
  30829. symbol_table.add_variable("yy",yy);
  30830. symbol_table.add_variable("zz",zz);
  30831. symbol_table.add_variable("ww",ww);
  30832. typedef typename std::deque<exprtk::expression<T> > expr_list_t;
  30833. expr_list_t expr_list;
  30834. const std::size_t rounds = 50;
  30835. {
  30836. for (std::size_t r = 0; r < rounds; ++r)
  30837. {
  30838. expr_list.clear();
  30839. exprtk::parser<T> parser;
  30840. for (std::size_t i = 0; i < expression_list_size; ++i)
  30841. {
  30842. exprtk::expression<T> expression;
  30843. expression.register_symbol_table(symbol_table);
  30844. if (!parser.compile(expression_list[i],expression))
  30845. {
  30846. return false;
  30847. }
  30848. expr_list.push_back(expression);
  30849. }
  30850. }
  30851. }
  30852. struct execute
  30853. {
  30854. static inline T process(T& x, T& y, expression<T>& expression)
  30855. {
  30856. static const T lower_bound = T(-20);
  30857. static const T upper_bound = T(+20);
  30858. static const T delta = T(0.1);
  30859. T total = T(0);
  30860. for (x = lower_bound; x <= upper_bound; x += delta)
  30861. {
  30862. for (y = lower_bound; y <= upper_bound; y += delta)
  30863. {
  30864. total += expression.value();
  30865. }
  30866. }
  30867. return total;
  30868. }
  30869. };
  30870. for (std::size_t i = 0; i < expr_list.size(); ++i)
  30871. {
  30872. execute::process( x, y, expr_list[i]);
  30873. execute::process(xx, yy, expr_list[i]);
  30874. }
  30875. {
  30876. for (std::size_t i = 0; i < 10000; ++i)
  30877. {
  30878. const T v = T(123.456 + i);
  30879. if (details::is_true(details::numeric::nequal(details::numeric::fast_exp<T, 1>::result(v),details::numeric::pow(v,T( 1)))))
  30880. return false;
  30881. #define else_stmt(N) \
  30882. else if (details::is_true(details::numeric::nequal(details::numeric::fast_exp<T,N>::result(v),details::numeric::pow(v,T(N))))) \
  30883. return false; \
  30884. else_stmt( 2) else_stmt( 3) else_stmt( 4) else_stmt( 5)
  30885. else_stmt( 6) else_stmt( 7) else_stmt( 8) else_stmt( 9)
  30886. else_stmt(10) else_stmt(11) else_stmt(12) else_stmt(13)
  30887. else_stmt(14) else_stmt(15) else_stmt(16) else_stmt(17)
  30888. else_stmt(18) else_stmt(19) else_stmt(20) else_stmt(21)
  30889. else_stmt(22) else_stmt(23) else_stmt(24) else_stmt(25)
  30890. else_stmt(26) else_stmt(27) else_stmt(28) else_stmt(29)
  30891. else_stmt(30) else_stmt(31) else_stmt(32) else_stmt(33)
  30892. else_stmt(34) else_stmt(35) else_stmt(36) else_stmt(37)
  30893. else_stmt(38) else_stmt(39) else_stmt(40) else_stmt(41)
  30894. else_stmt(42) else_stmt(43) else_stmt(44) else_stmt(45)
  30895. else_stmt(46) else_stmt(47) else_stmt(48) else_stmt(49)
  30896. else_stmt(50) else_stmt(51) else_stmt(52) else_stmt(53)
  30897. else_stmt(54) else_stmt(55) else_stmt(56) else_stmt(57)
  30898. else_stmt(58) else_stmt(59) else_stmt(60) else_stmt(61)
  30899. }
  30900. }
  30901. return true;
  30902. }
  30903. }
  30904. #if defined(_WIN32) || defined(__WIN32__) || defined(WIN32)
  30905. # ifndef NOMINMAX
  30906. # define NOMINMAX
  30907. # endif
  30908. # ifndef WIN32_LEAN_AND_MEAN
  30909. # define WIN32_LEAN_AND_MEAN
  30910. # endif
  30911. # include <windows.h>
  30912. # include <ctime>
  30913. #else
  30914. # include <ctime>
  30915. # include <sys/time.h>
  30916. # include <sys/types.h>
  30917. #endif
  30918. namespace exprtk
  30919. {
  30920. class timer
  30921. {
  30922. public:
  30923. #if defined(_WIN32) || defined(__WIN32__) || defined(WIN32)
  30924. timer()
  30925. : in_use_(false)
  30926. {
  30927. QueryPerformanceFrequency(&clock_frequency_);
  30928. }
  30929. inline void start()
  30930. {
  30931. in_use_ = true;
  30932. QueryPerformanceCounter(&start_time_);
  30933. }
  30934. inline void stop()
  30935. {
  30936. QueryPerformanceCounter(&stop_time_);
  30937. in_use_ = false;
  30938. }
  30939. inline double time() const
  30940. {
  30941. return (1.0 * (stop_time_.QuadPart - start_time_.QuadPart)) / (1.0 * clock_frequency_.QuadPart);
  30942. }
  30943. #else
  30944. timer()
  30945. : in_use_(false)
  30946. {
  30947. start_time_.tv_sec = 0;
  30948. start_time_.tv_usec = 0;
  30949. stop_time_.tv_sec = 0;
  30950. stop_time_.tv_usec = 0;
  30951. }
  30952. inline void start()
  30953. {
  30954. in_use_ = true;
  30955. gettimeofday(&start_time_,0);
  30956. }
  30957. inline void stop()
  30958. {
  30959. gettimeofday(&stop_time_, 0);
  30960. in_use_ = false;
  30961. }
  30962. inline unsigned long long int usec_time() const
  30963. {
  30964. if (!in_use_)
  30965. {
  30966. if (stop_time_.tv_sec >= start_time_.tv_sec)
  30967. {
  30968. return 1000000LLU * static_cast<details::_uint64_t>(stop_time_.tv_sec - start_time_.tv_sec ) +
  30969. static_cast<details::_uint64_t>(stop_time_.tv_usec - start_time_.tv_usec) ;
  30970. }
  30971. else
  30972. return std::numeric_limits<details::_uint64_t>::max();
  30973. }
  30974. else
  30975. return std::numeric_limits<details::_uint64_t>::max();
  30976. }
  30977. inline double time() const
  30978. {
  30979. return usec_time() * 0.000001;
  30980. }
  30981. #endif
  30982. inline bool in_use() const
  30983. {
  30984. return in_use_;
  30985. }
  30986. private:
  30987. bool in_use_;
  30988. #if defined(_WIN32) || defined(__WIN32__) || defined(WIN32)
  30989. LARGE_INTEGER start_time_;
  30990. LARGE_INTEGER stop_time_;
  30991. LARGE_INTEGER clock_frequency_;
  30992. #else
  30993. struct timeval start_time_;
  30994. struct timeval stop_time_;
  30995. #endif
  30996. };
  30997. } // namespace exprtk
  30998. #ifndef exprtk_disable_rtl_io
  30999. namespace exprtk
  31000. {
  31001. namespace rtl { namespace io { namespace details
  31002. {
  31003. template <typename T>
  31004. inline void print_type(const std::string& fmt,
  31005. const T v,
  31006. exprtk::details::numeric::details::real_type_tag)
  31007. {
  31008. printf(fmt.c_str(),v);
  31009. }
  31010. template <typename T>
  31011. struct print_impl
  31012. {
  31013. typedef typename igeneric_function<T>::generic_type generic_type;
  31014. typedef typename igeneric_function<T>::parameter_list_t parameter_list_t;
  31015. typedef typename generic_type::scalar_view scalar_t;
  31016. typedef typename generic_type::vector_view vector_t;
  31017. typedef typename generic_type::string_view string_t;
  31018. typedef typename exprtk::details::numeric::details::number_type<T>::type num_type;
  31019. static void process(const std::string& scalar_format, parameter_list_t parameters)
  31020. {
  31021. for (std::size_t i = 0; i < parameters.size(); ++i)
  31022. {
  31023. generic_type& gt = parameters[i];
  31024. switch (gt.type)
  31025. {
  31026. case generic_type::e_scalar : print(scalar_format,scalar_t(gt));
  31027. break;
  31028. case generic_type::e_vector : print(scalar_format,vector_t(gt));
  31029. break;
  31030. case generic_type::e_string : print(string_t(gt));
  31031. break;
  31032. default : continue;
  31033. }
  31034. }
  31035. }
  31036. static inline void print(const std::string& scalar_format, const scalar_t& s)
  31037. {
  31038. print_type(scalar_format,s(),num_type());
  31039. }
  31040. static inline void print(const std::string& scalar_format, const vector_t& v)
  31041. {
  31042. for (std::size_t i = 0; i < v.size(); ++i)
  31043. {
  31044. print_type(scalar_format,v[i],num_type());
  31045. if ((i + 1) < v.size())
  31046. printf(" ");
  31047. }
  31048. }
  31049. static inline void print(const string_t& s)
  31050. {
  31051. printf("%s",to_str(s).c_str());
  31052. }
  31053. };
  31054. } // namespace exprtk::rtl::io::details
  31055. template <typename T>
  31056. struct print : public exprtk::igeneric_function<T>
  31057. {
  31058. typedef typename igeneric_function<T>::parameter_list_t parameter_list_t;
  31059. using exprtk::igeneric_function<T>::operator();
  31060. print(const std::string& scalar_format = "%10.5f")
  31061. : scalar_format_(scalar_format)
  31062. {
  31063. exprtk::enable_zero_parameters(*this);
  31064. }
  31065. inline T operator() (parameter_list_t parameters)
  31066. {
  31067. details::print_impl<T>::process(scalar_format_,parameters);
  31068. return T(0);
  31069. }
  31070. std::string scalar_format_;
  31071. };
  31072. template <typename T>
  31073. struct println : public exprtk::igeneric_function<T>
  31074. {
  31075. typedef typename igeneric_function<T>::parameter_list_t parameter_list_t;
  31076. using exprtk::igeneric_function<T>::operator();
  31077. println(const std::string& scalar_format = "%10.5f")
  31078. : scalar_format_(scalar_format)
  31079. {
  31080. exprtk::enable_zero_parameters(*this);
  31081. }
  31082. inline T operator() (parameter_list_t parameters)
  31083. {
  31084. details::print_impl<T>::process(scalar_format_,parameters);
  31085. printf("\n");
  31086. return T(0);
  31087. }
  31088. std::string scalar_format_;
  31089. };
  31090. template <typename T>
  31091. struct package
  31092. {
  31093. print <T> p;
  31094. println<T> pl;
  31095. bool register_package(exprtk::symbol_table<T>& symtab)
  31096. {
  31097. #define exprtk_register_function(FunctionName,FunctionType) \
  31098. if (!symtab.add_function(FunctionName,FunctionType)) \
  31099. { \
  31100. exprtk_debug(( \
  31101. "exprtk::rtl::io::register_package - Failed to add function: %s\n", \
  31102. FunctionName)); \
  31103. return false; \
  31104. } \
  31105. exprtk_register_function("print" , p)
  31106. exprtk_register_function("println", pl)
  31107. #undef exprtk_register_function
  31108. return true;
  31109. }
  31110. };
  31111. } // namespace exprtk::rtl::io
  31112. } // namespace exprtk::rtl
  31113. } // namespace exprtk
  31114. #endif
  31115. #ifndef exprtk_disable_rtl_io_file
  31116. #include <fstream>
  31117. namespace exprtk
  31118. {
  31119. namespace rtl { namespace io { namespace file { namespace details
  31120. {
  31121. enum file_mode
  31122. {
  31123. e_error = 0,
  31124. e_read = 1,
  31125. e_write = 2,
  31126. e_rdwrt = 4
  31127. };
  31128. struct file_descriptor
  31129. {
  31130. file_descriptor(const std::string& fname, const std::string& access)
  31131. : stream_ptr(0),
  31132. mode(get_file_mode(access)),
  31133. file_name(fname)
  31134. {}
  31135. void* stream_ptr;
  31136. file_mode mode;
  31137. std::string file_name;
  31138. bool open()
  31139. {
  31140. if (e_read == mode)
  31141. {
  31142. std::ifstream* stream = new std::ifstream(file_name.c_str(),std::ios::binary);
  31143. if (!(*stream))
  31144. {
  31145. file_name.clear();
  31146. delete stream;
  31147. return false;
  31148. }
  31149. else
  31150. stream_ptr = stream;
  31151. return true;
  31152. }
  31153. else if (e_write == mode)
  31154. {
  31155. std::ofstream* stream = new std::ofstream(file_name.c_str(),std::ios::binary);
  31156. if (!(*stream))
  31157. {
  31158. file_name.clear();
  31159. delete stream;
  31160. return false;
  31161. }
  31162. else
  31163. stream_ptr = stream;
  31164. return true;
  31165. }
  31166. else if (e_rdwrt == mode)
  31167. {
  31168. std::fstream* stream = new std::fstream(file_name.c_str(),std::ios::binary);
  31169. if (!(*stream))
  31170. {
  31171. file_name.clear();
  31172. delete stream;
  31173. return false;
  31174. }
  31175. else
  31176. stream_ptr = stream;
  31177. return true;
  31178. }
  31179. else
  31180. return false;
  31181. }
  31182. template <typename Stream, typename Ptr>
  31183. void close(Ptr& p)
  31184. {
  31185. Stream* stream = reinterpret_cast<Stream*>(p);
  31186. stream->close();
  31187. delete stream;
  31188. p = reinterpret_cast<Ptr>(0);
  31189. }
  31190. bool close()
  31191. {
  31192. switch (mode)
  31193. {
  31194. case e_read : close<std::ifstream>(stream_ptr);
  31195. break;
  31196. case e_write : close<std::ofstream>(stream_ptr);
  31197. break;
  31198. case e_rdwrt : close<std::fstream> (stream_ptr);
  31199. break;
  31200. default : return false;
  31201. }
  31202. return true;
  31203. }
  31204. template <typename View>
  31205. bool write(const View& view, const std::size_t amount, const std::size_t offset = 0)
  31206. {
  31207. switch (mode)
  31208. {
  31209. case e_write : reinterpret_cast<std::ofstream*>(stream_ptr)->
  31210. write(reinterpret_cast<const char*>(view.begin() + offset), amount * sizeof(typename View::value_t));
  31211. break;
  31212. case e_rdwrt : reinterpret_cast<std::fstream*>(stream_ptr)->
  31213. write(reinterpret_cast<const char*>(view.begin() + offset) , amount * sizeof(typename View::value_t));
  31214. break;
  31215. default : return false;
  31216. }
  31217. return true;
  31218. }
  31219. template <typename View>
  31220. bool read(View& view, const std::size_t amount, const std::size_t offset = 0)
  31221. {
  31222. switch (mode)
  31223. {
  31224. case e_read : reinterpret_cast<std::ifstream*>(stream_ptr)->
  31225. read(reinterpret_cast<char*>(view.begin() + offset), amount * sizeof(typename View::value_t));
  31226. break;
  31227. case e_rdwrt : reinterpret_cast<std::fstream*>(stream_ptr)->
  31228. read(reinterpret_cast<char*>(view.begin() + offset) , amount * sizeof(typename View::value_t));
  31229. break;
  31230. default : return false;
  31231. }
  31232. return true;
  31233. }
  31234. bool getline(std::string& s)
  31235. {
  31236. switch (mode)
  31237. {
  31238. case e_read : return (!!std::getline(*reinterpret_cast<std::ifstream*>(stream_ptr),s));
  31239. case e_rdwrt : return (!!std::getline(*reinterpret_cast<std::fstream* >(stream_ptr),s));
  31240. default : return false;
  31241. }
  31242. }
  31243. bool eof() const
  31244. {
  31245. switch (mode)
  31246. {
  31247. case e_read : return reinterpret_cast<std::ifstream*>(stream_ptr)->eof();
  31248. case e_write : return reinterpret_cast<std::ofstream*>(stream_ptr)->eof();
  31249. case e_rdwrt : return reinterpret_cast<std::fstream* >(stream_ptr)->eof();
  31250. default : return true;
  31251. }
  31252. }
  31253. file_mode get_file_mode(const std::string& access) const
  31254. {
  31255. if (access.empty() || access.size() > 2)
  31256. return e_error;
  31257. std::size_t w_cnt = 0;
  31258. std::size_t r_cnt = 0;
  31259. for (std::size_t i = 0; i < access.size(); ++i)
  31260. {
  31261. switch (std::tolower(access[i]))
  31262. {
  31263. case 'r' : r_cnt++; break;
  31264. case 'w' : w_cnt++; break;
  31265. default : return e_error;
  31266. }
  31267. }
  31268. if ((0 == r_cnt) && (0 == w_cnt))
  31269. return e_error;
  31270. else if ((r_cnt > 1) || (w_cnt > 1))
  31271. return e_error;
  31272. else if ((1 == r_cnt) && (1 == w_cnt))
  31273. return e_rdwrt;
  31274. else if (1 == r_cnt)
  31275. return e_read;
  31276. else
  31277. return e_write;
  31278. }
  31279. };
  31280. template <typename T>
  31281. file_descriptor* make_handle(T v)
  31282. {
  31283. file_descriptor* fd = reinterpret_cast<file_descriptor*>(0);
  31284. std::memcpy(reinterpret_cast<char*>(&fd),
  31285. reinterpret_cast<const char*>(&v),
  31286. sizeof(fd));
  31287. return fd;
  31288. }
  31289. template <typename T>
  31290. void perform_check()
  31291. {
  31292. #ifdef _MSC_VER
  31293. #pragma warning(push)
  31294. #pragma warning(disable: 4127)
  31295. #endif
  31296. if (sizeof(T) < sizeof(void*))
  31297. {
  31298. throw std::runtime_error("exprtk::rtl::io::file - Error - pointer size larger than holder.");
  31299. }
  31300. #ifdef _MSC_VER
  31301. #pragma warning(pop)
  31302. #endif
  31303. }
  31304. } // namespace exprtk::rtl::io::file::details
  31305. template <typename T>
  31306. class open : public exprtk::igeneric_function<T>
  31307. {
  31308. public:
  31309. typedef typename exprtk::igeneric_function<T> igfun_t;
  31310. typedef typename igfun_t::parameter_list_t parameter_list_t;
  31311. typedef typename igfun_t::generic_type generic_type;
  31312. typedef typename generic_type::string_view string_t;
  31313. using exprtk::igeneric_function<T>::operator();
  31314. open()
  31315. : exprtk::igeneric_function<T>("S|SS")
  31316. { details::perform_check<T>(); }
  31317. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  31318. {
  31319. std::string file_name = to_str(string_t(parameters[0]));
  31320. std::string access;
  31321. if (file_name.empty())
  31322. return T(0);
  31323. if (0 == ps_index)
  31324. access = "r";
  31325. else if (0 == string_t(parameters[1]).size())
  31326. return T(0);
  31327. else
  31328. access = to_str(string_t(parameters[1]));
  31329. details::file_descriptor* fd = new details::file_descriptor(file_name,access);
  31330. if (fd->open())
  31331. {
  31332. T t = T(0);
  31333. std::memcpy(reinterpret_cast<char*>(&t ),
  31334. reinterpret_cast<char*>(&fd),
  31335. sizeof(fd));
  31336. return t;
  31337. }
  31338. else
  31339. {
  31340. delete fd;
  31341. return T(0);
  31342. }
  31343. }
  31344. };
  31345. template <typename T>
  31346. struct close : public exprtk::ifunction<T>
  31347. {
  31348. using exprtk::ifunction<T>::operator();
  31349. close()
  31350. : exprtk::ifunction<T>(1)
  31351. { details::perform_check<T>(); }
  31352. inline T operator() (const T& v)
  31353. {
  31354. details::file_descriptor* fd = details::make_handle(v);
  31355. if (!fd->close())
  31356. return T(0);
  31357. delete fd;
  31358. return T(1);
  31359. }
  31360. };
  31361. template <typename T>
  31362. class write : public exprtk::igeneric_function<T>
  31363. {
  31364. public:
  31365. typedef typename exprtk::igeneric_function<T> igfun_t;
  31366. typedef typename igfun_t::parameter_list_t parameter_list_t;
  31367. typedef typename igfun_t::generic_type generic_type;
  31368. typedef typename generic_type::string_view string_t;
  31369. typedef typename generic_type::scalar_view scalar_t;
  31370. typedef typename generic_type::vector_view vector_t;
  31371. using exprtk::igeneric_function<T>::operator();
  31372. write()
  31373. : igfun_t("TS|TST|TV|TVT")
  31374. { details::perform_check<T>(); }
  31375. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  31376. {
  31377. details::file_descriptor* fd = details::make_handle(scalar_t(parameters[0])());
  31378. std::size_t amount = 0;
  31379. switch (ps_index)
  31380. {
  31381. case 0 : {
  31382. const string_t buffer(parameters[1]);
  31383. amount = buffer.size();
  31384. return T(fd->write(buffer, amount) ? 1 : 0);
  31385. }
  31386. case 1 : {
  31387. const string_t buffer(parameters[1]);
  31388. amount = std::min(buffer.size(),
  31389. static_cast<std::size_t>(scalar_t(parameters[2])()));
  31390. return T(fd->write(buffer, amount) ? 1 : 0);
  31391. }
  31392. case 2 : {
  31393. const vector_t vec(parameters[1]);
  31394. amount = vec.size();
  31395. return T(fd->write(vec, amount) ? 1 : 0);
  31396. }
  31397. case 3 : {
  31398. const vector_t vec(parameters[1]);
  31399. amount = std::min(vec.size(),
  31400. static_cast<std::size_t>(scalar_t(parameters[2])()));
  31401. return T(fd->write(vec, amount) ? 1 : 0);
  31402. }
  31403. }
  31404. return T(0);
  31405. }
  31406. };
  31407. template <typename T>
  31408. class read : public exprtk::igeneric_function<T>
  31409. {
  31410. public:
  31411. typedef typename exprtk::igeneric_function<T> igfun_t;
  31412. typedef typename igfun_t::parameter_list_t parameter_list_t;
  31413. typedef typename igfun_t::generic_type generic_type;
  31414. typedef typename generic_type::string_view string_t;
  31415. typedef typename generic_type::scalar_view scalar_t;
  31416. typedef typename generic_type::vector_view vector_t;
  31417. using exprtk::igeneric_function<T>::operator();
  31418. read()
  31419. : igfun_t("TS|TST|TV|TVT")
  31420. { details::perform_check<T>(); }
  31421. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  31422. {
  31423. details::file_descriptor* fd = details::make_handle(scalar_t(parameters[0])());
  31424. std::size_t amount = 0;
  31425. switch (ps_index)
  31426. {
  31427. case 0 : {
  31428. string_t buffer(parameters[1]);
  31429. amount = buffer.size();
  31430. return T(fd->read(buffer,amount) ? 1 : 0);
  31431. }
  31432. case 1 : {
  31433. string_t buffer(parameters[1]);
  31434. amount = std::min(buffer.size(),
  31435. static_cast<std::size_t>(scalar_t(parameters[2])()));
  31436. return T(fd->read(buffer,amount) ? 1 : 0);
  31437. }
  31438. case 2 : {
  31439. vector_t vec(parameters[1]);
  31440. amount = vec.size();
  31441. return T(fd->read(vec,amount) ? 1 : 0);
  31442. }
  31443. case 3 : {
  31444. vector_t vec(parameters[1]);
  31445. amount = std::min(vec.size(),
  31446. static_cast<std::size_t>(scalar_t(parameters[2])()));
  31447. return T(fd->read(vec,amount) ? 1 : 0);
  31448. }
  31449. }
  31450. return T(0);
  31451. }
  31452. };
  31453. template <typename T>
  31454. class getline : public exprtk::igeneric_function<T>
  31455. {
  31456. public:
  31457. typedef typename exprtk::igeneric_function<T> igfun_t;
  31458. typedef typename igfun_t::parameter_list_t parameter_list_t;
  31459. typedef typename igfun_t::generic_type generic_type;
  31460. typedef typename generic_type::string_view string_t;
  31461. typedef typename generic_type::scalar_view scalar_t;
  31462. using exprtk::igeneric_function<T>::operator();
  31463. getline()
  31464. : igfun_t("T",igfun_t::e_rtrn_string)
  31465. { details::perform_check<T>(); }
  31466. inline T operator() (std::string& result,
  31467. parameter_list_t parameters)
  31468. {
  31469. details::file_descriptor* fd = details::make_handle(scalar_t(parameters[0])());
  31470. return T(fd->getline(result) ? 1 : 0);
  31471. }
  31472. };
  31473. template <typename T>
  31474. struct eof : public exprtk::ifunction<T>
  31475. {
  31476. using exprtk::ifunction<T>::operator();
  31477. eof()
  31478. : exprtk::ifunction<T>(1)
  31479. { details::perform_check<T>(); }
  31480. inline T operator() (const T& v)
  31481. {
  31482. details::file_descriptor* fd = details::make_handle(v);
  31483. return (fd->eof() ? T(1) : T(0));
  31484. }
  31485. };
  31486. template <typename T>
  31487. struct package
  31488. {
  31489. open <T> o;
  31490. close <T> c;
  31491. write <T> w;
  31492. read <T> r;
  31493. getline<T> g;
  31494. eof <T> e;
  31495. bool register_package(exprtk::symbol_table<T>& symtab)
  31496. {
  31497. #define exprtk_register_function(FunctionName,FunctionType) \
  31498. if (!symtab.add_function(FunctionName,FunctionType)) \
  31499. { \
  31500. exprtk_debug(( \
  31501. "exprtk::rtl::io::file::register_package - Failed to add function: %s\n", \
  31502. FunctionName)); \
  31503. return false; \
  31504. } \
  31505. exprtk_register_function("open" ,o)
  31506. exprtk_register_function("close" ,c)
  31507. exprtk_register_function("write" ,w)
  31508. exprtk_register_function("read" ,r)
  31509. exprtk_register_function("getline",g)
  31510. exprtk_register_function("eof" ,e)
  31511. #undef exprtk_register_function
  31512. return true;
  31513. }
  31514. };
  31515. } // namespace exprtk::rtl::io::file
  31516. } // namespace exprtk::rtl::io
  31517. } // namespace exprtk::rtl
  31518. } // namespace exprtk
  31519. #endif
  31520. #ifndef exprtk_disable_rtl_vecops
  31521. namespace exprtk
  31522. {
  31523. namespace rtl { namespace vecops {
  31524. namespace helper
  31525. {
  31526. template <typename Vector>
  31527. inline bool invalid_range(const Vector& v, const std::size_t r0, const std::size_t r1)
  31528. {
  31529. if (r0 > (v.size() - 1))
  31530. return true;
  31531. else if (r1 > (v.size() - 1))
  31532. return true;
  31533. else if (r1 < r0)
  31534. return true;
  31535. else
  31536. return false;
  31537. }
  31538. template <typename T>
  31539. struct load_vector_range
  31540. {
  31541. typedef typename exprtk::igeneric_function<T> igfun_t;
  31542. typedef typename igfun_t::parameter_list_t parameter_list_t;
  31543. typedef typename igfun_t::generic_type generic_type;
  31544. typedef typename generic_type::scalar_view scalar_t;
  31545. typedef typename generic_type::vector_view vector_t;
  31546. static inline bool process(parameter_list_t& parameters,
  31547. std::size_t& r0, std::size_t& r1,
  31548. const std::size_t& r0_prmidx,
  31549. const std::size_t& r1_prmidx,
  31550. const std::size_t vec_idx = 0)
  31551. {
  31552. if (r0_prmidx >= parameters.size())
  31553. return false;
  31554. if (r1_prmidx >= parameters.size())
  31555. return false;
  31556. if (!scalar_t(parameters[r0_prmidx]).to_uint(r0))
  31557. return false;
  31558. if (!scalar_t(parameters[r1_prmidx]).to_uint(r1))
  31559. return false;
  31560. return !invalid_range(vector_t(parameters[vec_idx]), r0, r1);
  31561. }
  31562. };
  31563. }
  31564. namespace details
  31565. {
  31566. template <typename T>
  31567. inline void kahan_sum(T& sum, T& error, const T v)
  31568. {
  31569. const T x = v - error;
  31570. const T y = sum + x;
  31571. error = (y - sum) - x;
  31572. sum = y;
  31573. }
  31574. } // namespace exprtk::rtl::details
  31575. template <typename T>
  31576. class all_true : public exprtk::igeneric_function<T>
  31577. {
  31578. public:
  31579. typedef typename exprtk::igeneric_function<T> igfun_t;
  31580. typedef typename igfun_t::parameter_list_t parameter_list_t;
  31581. typedef typename igfun_t::generic_type generic_type;
  31582. typedef typename generic_type::vector_view vector_t;
  31583. using exprtk::igeneric_function<T>::operator();
  31584. all_true()
  31585. : exprtk::igeneric_function<T>("V|VTT")
  31586. /*
  31587. Overloads:
  31588. 0. V - vector
  31589. 1. VTT - vector, r0, r1
  31590. */
  31591. {}
  31592. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  31593. {
  31594. const vector_t vec(parameters[0]);
  31595. std::size_t r0 = 0;
  31596. std::size_t r1 = vec.size() - 1;
  31597. if (
  31598. (1 == ps_index) &&
  31599. !helper::load_vector_range<T>::process(parameters, r0, r1, 1, 2, 0)
  31600. )
  31601. return std::numeric_limits<T>::quiet_NaN();
  31602. for (std::size_t i = r0; i <= r1; ++i)
  31603. {
  31604. if (vec[i] == T(0))
  31605. {
  31606. return T(0);
  31607. }
  31608. }
  31609. return T(1);
  31610. }
  31611. };
  31612. template <typename T>
  31613. class all_false : public exprtk::igeneric_function<T>
  31614. {
  31615. public:
  31616. typedef typename exprtk::igeneric_function<T> igfun_t;
  31617. typedef typename igfun_t::parameter_list_t parameter_list_t;
  31618. typedef typename igfun_t::generic_type generic_type;
  31619. typedef typename generic_type::vector_view vector_t;
  31620. using exprtk::igeneric_function<T>::operator();
  31621. all_false()
  31622. : exprtk::igeneric_function<T>("V|VTT")
  31623. /*
  31624. Overloads:
  31625. 0. V - vector
  31626. 1. VTT - vector, r0, r1
  31627. */
  31628. {}
  31629. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  31630. {
  31631. const vector_t vec(parameters[0]);
  31632. std::size_t r0 = 0;
  31633. std::size_t r1 = vec.size() - 1;
  31634. if (
  31635. (1 == ps_index) &&
  31636. !helper::load_vector_range<T>::process(parameters, r0, r1, 1, 2, 0)
  31637. )
  31638. return std::numeric_limits<T>::quiet_NaN();
  31639. for (std::size_t i = r0; i <= r1; ++i)
  31640. {
  31641. if (vec[i] != T(0))
  31642. {
  31643. return T(0);
  31644. }
  31645. }
  31646. return T(1);
  31647. }
  31648. };
  31649. template <typename T>
  31650. class any_true : public exprtk::igeneric_function<T>
  31651. {
  31652. public:
  31653. typedef typename exprtk::igeneric_function<T> igfun_t;
  31654. typedef typename igfun_t::parameter_list_t parameter_list_t;
  31655. typedef typename igfun_t::generic_type generic_type;
  31656. typedef typename generic_type::vector_view vector_t;
  31657. using exprtk::igeneric_function<T>::operator();
  31658. any_true()
  31659. : exprtk::igeneric_function<T>("V|VTT")
  31660. /*
  31661. Overloads:
  31662. 0. V - vector
  31663. 1. VTT - vector, r0, r1
  31664. */
  31665. {}
  31666. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  31667. {
  31668. const vector_t vec(parameters[0]);
  31669. std::size_t r0 = 0;
  31670. std::size_t r1 = vec.size() - 1;
  31671. if (
  31672. (1 == ps_index) &&
  31673. !helper::load_vector_range<T>::process(parameters, r0, r1, 1, 2, 0)
  31674. )
  31675. return std::numeric_limits<T>::quiet_NaN();
  31676. for (std::size_t i = r0; i <= r1; ++i)
  31677. {
  31678. if (vec[i] != T(0))
  31679. {
  31680. return T(1);
  31681. }
  31682. }
  31683. return T(0);
  31684. }
  31685. };
  31686. template <typename T>
  31687. class any_false : public exprtk::igeneric_function<T>
  31688. {
  31689. public:
  31690. typedef typename exprtk::igeneric_function<T> igfun_t;
  31691. typedef typename igfun_t::parameter_list_t parameter_list_t;
  31692. typedef typename igfun_t::generic_type generic_type;
  31693. typedef typename generic_type::vector_view vector_t;
  31694. using exprtk::igeneric_function<T>::operator();
  31695. any_false()
  31696. : exprtk::igeneric_function<T>("V|VTT")
  31697. /*
  31698. Overloads:
  31699. 0. V - vector
  31700. 1. VTT - vector, r0, r1
  31701. */
  31702. {}
  31703. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  31704. {
  31705. const vector_t vec(parameters[0]);
  31706. std::size_t r0 = 0;
  31707. std::size_t r1 = vec.size() - 1;
  31708. if (
  31709. (1 == ps_index) &&
  31710. !helper::load_vector_range<T>::process(parameters, r0, r1, 1, 2, 0)
  31711. )
  31712. return std::numeric_limits<T>::quiet_NaN();
  31713. for (std::size_t i = r0; i <= r1; ++i)
  31714. {
  31715. if (vec[i] == T(0))
  31716. {
  31717. return T(1);
  31718. }
  31719. }
  31720. return T(0);
  31721. }
  31722. };
  31723. template <typename T>
  31724. class count : public exprtk::igeneric_function<T>
  31725. {
  31726. public:
  31727. typedef typename exprtk::igeneric_function<T> igfun_t;
  31728. typedef typename igfun_t::parameter_list_t parameter_list_t;
  31729. typedef typename igfun_t::generic_type generic_type;
  31730. typedef typename generic_type::vector_view vector_t;
  31731. using exprtk::igeneric_function<T>::operator();
  31732. count()
  31733. : exprtk::igeneric_function<T>("V|VTT")
  31734. /*
  31735. Overloads:
  31736. 0. V - vector
  31737. 1. VTT - vector, r0, r1
  31738. */
  31739. {}
  31740. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  31741. {
  31742. const vector_t vec(parameters[0]);
  31743. std::size_t r0 = 0;
  31744. std::size_t r1 = vec.size() - 1;
  31745. if (
  31746. (1 == ps_index) &&
  31747. !helper::load_vector_range<T>::process(parameters, r0, r1, 1, 2, 0)
  31748. )
  31749. return std::numeric_limits<T>::quiet_NaN();
  31750. std::size_t cnt = 0;
  31751. for (std::size_t i = r0; i <= r1; ++i)
  31752. {
  31753. if (vec[i] != T(0)) ++cnt;
  31754. }
  31755. return T(cnt);
  31756. }
  31757. };
  31758. template <typename T>
  31759. class copy : public exprtk::igeneric_function<T>
  31760. {
  31761. public:
  31762. typedef typename exprtk::igeneric_function<T> igfun_t;
  31763. typedef typename igfun_t::parameter_list_t parameter_list_t;
  31764. typedef typename igfun_t::generic_type generic_type;
  31765. typedef typename generic_type::scalar_view scalar_t;
  31766. typedef typename generic_type::vector_view vector_t;
  31767. using exprtk::igeneric_function<T>::operator();
  31768. copy()
  31769. : exprtk::igeneric_function<T>("VV|VTTVTT")
  31770. /*
  31771. Overloads:
  31772. 0. VV - x(vector), y(vector)
  31773. 1. VTTVTT - x(vector), xr0, xr1, y(vector), yr0, yr1,
  31774. */
  31775. {}
  31776. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  31777. {
  31778. const vector_t x(parameters[0]);
  31779. vector_t y(parameters[(0 == ps_index) ? 1 : 3]);
  31780. std::size_t xr0 = 0;
  31781. std::size_t xr1 = x.size() - 1;
  31782. std::size_t yr0 = 0;
  31783. std::size_t yr1 = y.size() - 1;
  31784. if (1 == ps_index)
  31785. {
  31786. if (
  31787. !helper::load_vector_range<T>::process(parameters, xr0, xr1, 1, 2, 0) ||
  31788. !helper::load_vector_range<T>::process(parameters, yr0, yr1, 4, 5, 3)
  31789. )
  31790. return T(0);
  31791. }
  31792. const std::size_t n = std::min(xr1 - xr0 + 1, yr1 - yr0 + 1);
  31793. std::copy(x.begin() + xr0, x.begin() + xr0 + n, y.begin() + yr0);
  31794. return T(n);
  31795. }
  31796. };
  31797. template <typename T>
  31798. class rol : public exprtk::igeneric_function<T>
  31799. {
  31800. public:
  31801. typedef typename exprtk::igeneric_function<T> igfun_t;
  31802. typedef typename igfun_t::parameter_list_t parameter_list_t;
  31803. typedef typename igfun_t::generic_type generic_type;
  31804. typedef typename generic_type::scalar_view scalar_t;
  31805. typedef typename generic_type::vector_view vector_t;
  31806. using exprtk::igeneric_function<T>::operator();
  31807. rol()
  31808. : exprtk::igeneric_function<T>("VT|VTTT")
  31809. /*
  31810. Overloads:
  31811. 0. VT - vector, N
  31812. 1. VTTT - vector, N, r0, r1
  31813. */
  31814. {}
  31815. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  31816. {
  31817. vector_t vec(parameters[0]);
  31818. std::size_t n = 0;
  31819. std::size_t r0 = 0;
  31820. std::size_t r1 = vec.size() - 1;
  31821. if (!scalar_t(parameters[1]).to_uint(n))
  31822. return T(0);
  31823. if (
  31824. (1 == ps_index) &&
  31825. !helper::load_vector_range<T>::process(parameters, r0, r1, 2, 3, 0)
  31826. )
  31827. return T(0);
  31828. std::size_t dist = r1 - r0 + 1;
  31829. std::size_t shift = n % dist;
  31830. std::rotate(vec.begin() + r0, vec.begin() + r0 + shift, vec.begin() + r1 + 1);
  31831. return T(1);
  31832. }
  31833. };
  31834. template <typename T>
  31835. class ror : public exprtk::igeneric_function<T>
  31836. {
  31837. public:
  31838. typedef typename exprtk::igeneric_function<T> igfun_t;
  31839. typedef typename igfun_t::parameter_list_t parameter_list_t;
  31840. typedef typename igfun_t::generic_type generic_type;
  31841. typedef typename generic_type::scalar_view scalar_t;
  31842. typedef typename generic_type::vector_view vector_t;
  31843. using exprtk::igeneric_function<T>::operator();
  31844. ror()
  31845. : exprtk::igeneric_function<T>("VT|VTTT")
  31846. /*
  31847. Overloads:
  31848. 0. VT - vector, N
  31849. 1. VTTT - vector, N, r0, r1
  31850. */
  31851. {}
  31852. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  31853. {
  31854. vector_t vec(parameters[0]);
  31855. std::size_t n = 0;
  31856. std::size_t r0 = 0;
  31857. std::size_t r1 = vec.size() - 1;
  31858. if (!scalar_t(parameters[1]).to_uint(n))
  31859. return T(0);
  31860. if (
  31861. (1 == ps_index) &&
  31862. !helper::load_vector_range<T>::process(parameters, r0, r1, 2, 3, 0)
  31863. )
  31864. return T(0);
  31865. std::size_t dist = r1 - r0 + 1;
  31866. std::size_t shift = (dist - (n % dist)) % dist;
  31867. std::rotate(vec.begin() + r0, vec.begin() + r0 + shift, vec.begin() + r1 + 1);
  31868. return T(1);
  31869. }
  31870. };
  31871. template <typename T>
  31872. class shift_left : public exprtk::igeneric_function<T>
  31873. {
  31874. public:
  31875. typedef typename exprtk::igeneric_function<T> igfun_t;
  31876. typedef typename igfun_t::parameter_list_t parameter_list_t;
  31877. typedef typename igfun_t::generic_type generic_type;
  31878. typedef typename generic_type::scalar_view scalar_t;
  31879. typedef typename generic_type::vector_view vector_t;
  31880. using exprtk::igeneric_function<T>::operator();
  31881. shift_left()
  31882. : exprtk::igeneric_function<T>("VT|VTTT")
  31883. /*
  31884. Overloads:
  31885. 0. VT - vector, N
  31886. 1. VTTT - vector, N, r0, r1
  31887. */
  31888. {}
  31889. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  31890. {
  31891. vector_t vec(parameters[0]);
  31892. std::size_t n = 0;
  31893. std::size_t r0 = 0;
  31894. std::size_t r1 = vec.size() - 1;
  31895. if (!scalar_t(parameters[1]).to_uint(n))
  31896. return T(0);
  31897. if (
  31898. (1 == ps_index) &&
  31899. !helper::load_vector_range<T>::process(parameters, r0, r1, 2, 3, 0)
  31900. )
  31901. return T(0);
  31902. std::size_t dist = r1 - r0 + 1;
  31903. if (n > dist)
  31904. return T(0);
  31905. std::rotate(vec.begin() + r0, vec.begin() + r0 + n, vec.begin() + r1 + 1);
  31906. for (std::size_t i = r1 - n + 1; i <= r1; ++i)
  31907. {
  31908. vec[i] = T(0);
  31909. }
  31910. return T(1);
  31911. }
  31912. };
  31913. template <typename T>
  31914. class shift_right : public exprtk::igeneric_function<T>
  31915. {
  31916. public:
  31917. typedef typename exprtk::igeneric_function<T> igfun_t;
  31918. typedef typename igfun_t::parameter_list_t parameter_list_t;
  31919. typedef typename igfun_t::generic_type generic_type;
  31920. typedef typename generic_type::scalar_view scalar_t;
  31921. typedef typename generic_type::vector_view vector_t;
  31922. using exprtk::igeneric_function<T>::operator();
  31923. shift_right()
  31924. : exprtk::igeneric_function<T>("VT|VTTT")
  31925. /*
  31926. Overloads:
  31927. 0. VT - vector, N
  31928. 1. VTTT - vector, N, r0, r1
  31929. */
  31930. {}
  31931. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  31932. {
  31933. vector_t vec(parameters[0]);
  31934. std::size_t n = 0;
  31935. std::size_t r0 = 0;
  31936. std::size_t r1 = vec.size() - 1;
  31937. if (!scalar_t(parameters[1]).to_uint(n))
  31938. return T(0);
  31939. if (
  31940. (1 == ps_index) &&
  31941. !helper::load_vector_range<T>::process(parameters, r0, r1, 2, 3, 0)
  31942. )
  31943. return T(0);
  31944. std::size_t dist = r1 - r0 + 1;
  31945. if (n > dist)
  31946. return T(0);
  31947. std::size_t shift = (dist - (n % dist)) % dist;
  31948. std::rotate(vec.begin() + r0, vec.begin() + r0 + shift, vec.begin() + r1 + 1);
  31949. for (std::size_t i = r0; i < r0 + n; ++i)
  31950. {
  31951. vec[i] = T(0);
  31952. }
  31953. return T(1);
  31954. }
  31955. };
  31956. template <typename T>
  31957. class sort : public exprtk::igeneric_function<T>
  31958. {
  31959. public:
  31960. typedef typename exprtk::igeneric_function<T> igfun_t;
  31961. typedef typename igfun_t::parameter_list_t parameter_list_t;
  31962. typedef typename igfun_t::generic_type generic_type;
  31963. typedef typename generic_type::string_view string_t;
  31964. typedef typename generic_type::vector_view vector_t;
  31965. using exprtk::igeneric_function<T>::operator();
  31966. sort()
  31967. : exprtk::igeneric_function<T>("V|VTT|VS|VSTT")
  31968. /*
  31969. Overloads:
  31970. 0. V - vector
  31971. 1. VTT - vector, r0, r1
  31972. 2. VS - vector, string
  31973. 3. VSTT - vector, string, r0, r1
  31974. */
  31975. {}
  31976. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  31977. {
  31978. vector_t vec(parameters[0]);
  31979. std::size_t r0 = 0;
  31980. std::size_t r1 = vec.size() - 1;
  31981. if ((1 == ps_index) && !helper::load_vector_range<T>::process(parameters, r0, r1, 1, 2, 0))
  31982. return T(0);
  31983. if ((3 == ps_index) && !helper::load_vector_range<T>::process(parameters, r0, r1, 2, 3, 0))
  31984. return T(0);
  31985. bool ascending = true;
  31986. if ((2 == ps_index) || (3 == ps_index))
  31987. {
  31988. if (exprtk::details::imatch(to_str(string_t(parameters[1])),"ascending"))
  31989. ascending = true;
  31990. else if (exprtk::details::imatch(to_str(string_t(parameters[1])),"descending"))
  31991. ascending = false;
  31992. else
  31993. return T(0);
  31994. }
  31995. if (ascending)
  31996. std::sort(vec.begin() + r0, vec.begin() + r1 + 1, std::less<T> ());
  31997. else
  31998. std::sort(vec.begin() + r0, vec.begin() + r1 + 1, std::greater<T>());
  31999. return T(1);
  32000. }
  32001. };
  32002. template <typename T>
  32003. class nthelement : public exprtk::igeneric_function<T>
  32004. {
  32005. public:
  32006. typedef typename exprtk::igeneric_function<T> igfun_t;
  32007. typedef typename igfun_t::parameter_list_t parameter_list_t;
  32008. typedef typename igfun_t::generic_type generic_type;
  32009. typedef typename generic_type::scalar_view scalar_t;
  32010. typedef typename generic_type::vector_view vector_t;
  32011. using exprtk::igeneric_function<T>::operator();
  32012. nthelement()
  32013. : exprtk::igeneric_function<T>("VT|VTTT")
  32014. /*
  32015. Overloads:
  32016. 0. VT - vector, nth-element
  32017. 1. VTTT - vector, nth-element, r0, r1
  32018. */
  32019. {}
  32020. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  32021. {
  32022. vector_t vec(parameters[0]);
  32023. std::size_t n = 0;
  32024. std::size_t r0 = 0;
  32025. std::size_t r1 = vec.size() - 1;
  32026. if (!scalar_t(parameters[1]).to_uint(n))
  32027. return T(0);
  32028. if ((1 == ps_index) && !helper::load_vector_range<T>::process(parameters, r0, r1, 2, 3, 0))
  32029. return std::numeric_limits<T>::quiet_NaN();
  32030. std::nth_element(vec.begin() + r0, vec.begin() + r0 + n , vec.begin() + r1 + 1);
  32031. return T(1);
  32032. }
  32033. };
  32034. template <typename T>
  32035. class iota : public exprtk::igeneric_function<T>
  32036. {
  32037. public:
  32038. typedef typename exprtk::igeneric_function<T> igfun_t;
  32039. typedef typename igfun_t::parameter_list_t parameter_list_t;
  32040. typedef typename igfun_t::generic_type generic_type;
  32041. typedef typename generic_type::scalar_view scalar_t;
  32042. typedef typename generic_type::vector_view vector_t;
  32043. using exprtk::igeneric_function<T>::operator();
  32044. iota()
  32045. : exprtk::igeneric_function<T>("VT|VTT|VTTT|VTTTT")
  32046. /*
  32047. Overloads:
  32048. 0. VT - vector, increment
  32049. 1. VTT - vector, increment, base
  32050. 2. VTTTT - vector, increment, r0, r1
  32051. 3. VTTTT - vector, increment, base, r0, r1
  32052. */
  32053. {}
  32054. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  32055. {
  32056. vector_t vec(parameters[0]);
  32057. T increment = scalar_t(parameters[1])();
  32058. T base = ((1 == ps_index) || (3 == ps_index)) ? scalar_t(parameters[2])() : T(0);
  32059. std::size_t r0 = 0;
  32060. std::size_t r1 = vec.size() - 1;
  32061. if ((2 == ps_index) && !helper::load_vector_range<T>::process(parameters, r0, r1, 2, 3, 0))
  32062. return std::numeric_limits<T>::quiet_NaN();
  32063. else if ((3 == ps_index) && !helper::load_vector_range<T>::process(parameters, r0, r1, 3, 4, 0))
  32064. return std::numeric_limits<T>::quiet_NaN();
  32065. else
  32066. {
  32067. long long j = 0;
  32068. for (std::size_t i = r0; i <= r1; ++i, ++j)
  32069. {
  32070. vec[i] = base + (increment * j);
  32071. }
  32072. }
  32073. return T(1);
  32074. }
  32075. };
  32076. template <typename T>
  32077. class sumk : public exprtk::igeneric_function<T>
  32078. {
  32079. public:
  32080. typedef typename exprtk::igeneric_function<T> igfun_t;
  32081. typedef typename igfun_t::parameter_list_t parameter_list_t;
  32082. typedef typename igfun_t::generic_type generic_type;
  32083. typedef typename generic_type::vector_view vector_t;
  32084. using exprtk::igeneric_function<T>::operator();
  32085. sumk()
  32086. : exprtk::igeneric_function<T>("V|VTT")
  32087. /*
  32088. Overloads:
  32089. 0. V - vector
  32090. 1. VTT - vector, r0, r1
  32091. */
  32092. {}
  32093. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  32094. {
  32095. const vector_t vec(parameters[0]);
  32096. std::size_t r0 = 0;
  32097. std::size_t r1 = vec.size() - 1;
  32098. if ((1 == ps_index) && !helper::load_vector_range<T>::process(parameters, r0, r1, 1, 2, 0))
  32099. return std::numeric_limits<T>::quiet_NaN();
  32100. T result = T(0);
  32101. T error = T(0);
  32102. for (std::size_t i = r0; i <= r1; ++i)
  32103. {
  32104. details::kahan_sum(result, error, vec[i]);
  32105. }
  32106. return result;
  32107. }
  32108. };
  32109. template <typename T>
  32110. class axpy : public exprtk::igeneric_function<T>
  32111. {
  32112. public:
  32113. typedef typename exprtk::igeneric_function<T> igfun_t;
  32114. typedef typename igfun_t::parameter_list_t parameter_list_t;
  32115. typedef typename igfun_t::generic_type generic_type;
  32116. typedef typename generic_type::scalar_view scalar_t;
  32117. typedef typename generic_type::vector_view vector_t;
  32118. using exprtk::igeneric_function<T>::operator();
  32119. axpy()
  32120. : exprtk::igeneric_function<T>("TVV|TVVTT")
  32121. /*
  32122. y <- ax + y
  32123. Overloads:
  32124. 0. TVV - a, x(vector), y(vector)
  32125. 1. TVVTT - a, x(vector), y(vector), r0, r1
  32126. */
  32127. {}
  32128. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  32129. {
  32130. const vector_t x(parameters[1]);
  32131. vector_t y(parameters[2]);
  32132. std::size_t r0 = 0;
  32133. std::size_t r1 = std::min(x.size(),y.size()) - 1;
  32134. if ((1 == ps_index) && !helper::load_vector_range<T>::process(parameters, r0, r1, 3, 4, 1))
  32135. return std::numeric_limits<T>::quiet_NaN();
  32136. else if (helper::invalid_range(y, r0, r1))
  32137. return std::numeric_limits<T>::quiet_NaN();
  32138. const T a = scalar_t(parameters[0])();
  32139. for (std::size_t i = r0; i <= r1; ++i)
  32140. {
  32141. y[i] = (a * x[i]) + y[i];
  32142. }
  32143. return T(1);
  32144. }
  32145. };
  32146. template <typename T>
  32147. class axpby : public exprtk::igeneric_function<T>
  32148. {
  32149. public:
  32150. typedef typename exprtk::igeneric_function<T> igfun_t;
  32151. typedef typename igfun_t::parameter_list_t parameter_list_t;
  32152. typedef typename igfun_t::generic_type generic_type;
  32153. typedef typename generic_type::scalar_view scalar_t;
  32154. typedef typename generic_type::vector_view vector_t;
  32155. using exprtk::igeneric_function<T>::operator();
  32156. axpby()
  32157. : exprtk::igeneric_function<T>("TVTV|TVTVTT")
  32158. /*
  32159. y <- ax + by
  32160. Overloads:
  32161. 0. TVTV - a, x(vector), b, y(vector)
  32162. 1. TVTVTT - a, x(vector), b, y(vector), r0, r1
  32163. */
  32164. {}
  32165. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  32166. {
  32167. const vector_t x(parameters[1]);
  32168. vector_t y(parameters[3]);
  32169. std::size_t r0 = 0;
  32170. std::size_t r1 = std::min(x.size(),y.size()) - 1;
  32171. if ((1 == ps_index) && !helper::load_vector_range<T>::process(parameters, r0, r1, 4, 5, 1))
  32172. return std::numeric_limits<T>::quiet_NaN();
  32173. else if (helper::invalid_range(y, r0, r1))
  32174. return std::numeric_limits<T>::quiet_NaN();
  32175. const T a = scalar_t(parameters[0])();
  32176. const T b = scalar_t(parameters[2])();
  32177. for (std::size_t i = r0; i <= r1; ++i)
  32178. {
  32179. y[i] = (a * x[i]) + (b * y[i]);
  32180. }
  32181. return T(1);
  32182. }
  32183. };
  32184. template <typename T>
  32185. class axpyz : public exprtk::igeneric_function<T>
  32186. {
  32187. public:
  32188. typedef typename exprtk::igeneric_function<T> igfun_t;
  32189. typedef typename igfun_t::parameter_list_t parameter_list_t;
  32190. typedef typename igfun_t::generic_type generic_type;
  32191. typedef typename generic_type::scalar_view scalar_t;
  32192. typedef typename generic_type::vector_view vector_t;
  32193. using exprtk::igeneric_function<T>::operator();
  32194. axpyz()
  32195. : exprtk::igeneric_function<T>("TVVV|TVVVTT")
  32196. /*
  32197. z <- ax + y
  32198. Overloads:
  32199. 0. TVVV - a, x(vector), y(vector), z(vector)
  32200. 1. TVVVTT - a, x(vector), y(vector), z(vector), r0, r1
  32201. */
  32202. {}
  32203. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  32204. {
  32205. const vector_t x(parameters[1]);
  32206. const vector_t y(parameters[2]);
  32207. vector_t z(parameters[3]);
  32208. std::size_t r0 = 0;
  32209. std::size_t r1 = std::min(x.size(),y.size()) - 1;
  32210. if ((1 == ps_index) && !helper::load_vector_range<T>::process(parameters, r0, r1, 3, 4, 1))
  32211. return std::numeric_limits<T>::quiet_NaN();
  32212. else if (helper::invalid_range(y, r0, r1))
  32213. return std::numeric_limits<T>::quiet_NaN();
  32214. else if (helper::invalid_range(z, r0, r1))
  32215. return std::numeric_limits<T>::quiet_NaN();
  32216. const T a = scalar_t(parameters[0])();
  32217. for (std::size_t i = r0; i <= r1; ++i)
  32218. {
  32219. z[i] = (a * x[i]) + y[i];
  32220. }
  32221. return T(1);
  32222. }
  32223. };
  32224. template <typename T>
  32225. class axpbyz : public exprtk::igeneric_function<T>
  32226. {
  32227. public:
  32228. typedef typename exprtk::igeneric_function<T> igfun_t;
  32229. typedef typename igfun_t::parameter_list_t parameter_list_t;
  32230. typedef typename igfun_t::generic_type generic_type;
  32231. typedef typename generic_type::scalar_view scalar_t;
  32232. typedef typename generic_type::vector_view vector_t;
  32233. using exprtk::igeneric_function<T>::operator();
  32234. axpbyz()
  32235. : exprtk::igeneric_function<T>("TVTVV|TVTVVTT")
  32236. /*
  32237. z <- ax + by
  32238. Overloads:
  32239. 0. TVTVV - a, x(vector), b, y(vector), z(vector)
  32240. 1. TVTVVTT - a, x(vector), b, y(vector), z(vector), r0, r1
  32241. */
  32242. {}
  32243. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  32244. {
  32245. const vector_t x(parameters[1]);
  32246. const vector_t y(parameters[3]);
  32247. vector_t z(parameters[4]);
  32248. std::size_t r0 = 0;
  32249. std::size_t r1 = std::min(x.size(),y.size()) - 1;
  32250. if ((1 == ps_index) && !helper::load_vector_range<T>::process(parameters, r0, r1, 4, 5, 1))
  32251. return std::numeric_limits<T>::quiet_NaN();
  32252. else if (helper::invalid_range(y, r0, r1))
  32253. return std::numeric_limits<T>::quiet_NaN();
  32254. else if (helper::invalid_range(z, r0, r1))
  32255. return std::numeric_limits<T>::quiet_NaN();
  32256. const T a = scalar_t(parameters[0])();
  32257. const T b = scalar_t(parameters[2])();
  32258. for (std::size_t i = r0; i <= r1; ++i)
  32259. {
  32260. z[i] = (a * x[i]) + (b * y[i]);
  32261. }
  32262. return T(1);
  32263. }
  32264. };
  32265. template <typename T>
  32266. class axpbz : public exprtk::igeneric_function<T>
  32267. {
  32268. public:
  32269. typedef typename exprtk::igeneric_function<T> igfun_t;
  32270. typedef typename igfun_t::parameter_list_t parameter_list_t;
  32271. typedef typename igfun_t::generic_type generic_type;
  32272. typedef typename generic_type::scalar_view scalar_t;
  32273. typedef typename generic_type::vector_view vector_t;
  32274. using exprtk::igeneric_function<T>::operator();
  32275. axpbz()
  32276. : exprtk::igeneric_function<T>("TVTV|TVTVTT")
  32277. /*
  32278. z <- ax + b
  32279. Overloads:
  32280. 0. TVTV - a, x(vector), b, z(vector)
  32281. 1. TVTVTT - a, x(vector), b, z(vector), r0, r1
  32282. */
  32283. {}
  32284. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  32285. {
  32286. const vector_t x(parameters[1]);
  32287. vector_t z(parameters[3]);
  32288. std::size_t r0 = 0;
  32289. std::size_t r1 = x.size() - 1;
  32290. if ((1 == ps_index) && !helper::load_vector_range<T>::process(parameters, r0, r1, 4, 5, 1))
  32291. return std::numeric_limits<T>::quiet_NaN();
  32292. else if (helper::invalid_range(z, r0, r1))
  32293. return std::numeric_limits<T>::quiet_NaN();
  32294. const T a = scalar_t(parameters[0])();
  32295. const T b = scalar_t(parameters[2])();
  32296. for (std::size_t i = r0; i <= r1; ++i)
  32297. {
  32298. z[i] = (a * x[i]) + b;
  32299. }
  32300. return T(1);
  32301. }
  32302. };
  32303. template <typename T>
  32304. class dot : public exprtk::igeneric_function<T>
  32305. {
  32306. public:
  32307. typedef typename exprtk::igeneric_function<T> igfun_t;
  32308. typedef typename igfun_t::parameter_list_t parameter_list_t;
  32309. typedef typename igfun_t::generic_type generic_type;
  32310. typedef typename generic_type::scalar_view scalar_t;
  32311. typedef typename generic_type::vector_view vector_t;
  32312. using exprtk::igeneric_function<T>::operator();
  32313. dot()
  32314. : exprtk::igeneric_function<T>("VV|VVTT")
  32315. /*
  32316. Overloads:
  32317. 0. VV - x(vector), y(vector)
  32318. 1. VVTT - x(vector), y(vector), r0, r1
  32319. */
  32320. {}
  32321. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  32322. {
  32323. const vector_t x(parameters[0]);
  32324. const vector_t y(parameters[1]);
  32325. std::size_t r0 = 0;
  32326. std::size_t r1 = std::min(x.size(),y.size()) - 1;
  32327. if ((1 == ps_index) && !helper::load_vector_range<T>::process(parameters, r0, r1, 2, 3, 0))
  32328. return std::numeric_limits<T>::quiet_NaN();
  32329. else if (helper::invalid_range(y, r0, r1))
  32330. return std::numeric_limits<T>::quiet_NaN();
  32331. T result = T(0);
  32332. for (std::size_t i = r0; i <= r1; ++i)
  32333. {
  32334. result += (x[i] * y[i]);
  32335. }
  32336. return result;
  32337. }
  32338. };
  32339. template <typename T>
  32340. class dotk : public exprtk::igeneric_function<T>
  32341. {
  32342. public:
  32343. typedef typename exprtk::igeneric_function<T> igfun_t;
  32344. typedef typename igfun_t::parameter_list_t parameter_list_t;
  32345. typedef typename igfun_t::generic_type generic_type;
  32346. typedef typename generic_type::scalar_view scalar_t;
  32347. typedef typename generic_type::vector_view vector_t;
  32348. using exprtk::igeneric_function<T>::operator();
  32349. dotk()
  32350. : exprtk::igeneric_function<T>("VV|VVTT")
  32351. /*
  32352. Overloads:
  32353. 0. VV - x(vector), y(vector)
  32354. 1. VVTT - x(vector), y(vector), r0, r1
  32355. */
  32356. {}
  32357. inline T operator() (const std::size_t& ps_index, parameter_list_t parameters)
  32358. {
  32359. const vector_t x(parameters[0]);
  32360. const vector_t y(parameters[1]);
  32361. std::size_t r0 = 0;
  32362. std::size_t r1 = std::min(x.size(),y.size()) - 1;
  32363. if ((1 == ps_index) && !helper::load_vector_range<T>::process(parameters, r0, r1, 2, 3, 0))
  32364. return std::numeric_limits<T>::quiet_NaN();
  32365. else if (helper::invalid_range(y, r0, r1))
  32366. return std::numeric_limits<T>::quiet_NaN();
  32367. T result = T(0);
  32368. T error = T(0);
  32369. for (std::size_t i = r0; i <= r1; ++i)
  32370. {
  32371. details::kahan_sum(result, error, (x[i] * y[i]));
  32372. }
  32373. return result;
  32374. }
  32375. };
  32376. template <typename T>
  32377. struct package
  32378. {
  32379. all_true <T> at;
  32380. all_false <T> af;
  32381. any_true <T> nt;
  32382. any_false <T> nf;
  32383. count <T> c;
  32384. copy <T> cp;
  32385. rol <T> rl;
  32386. ror <T> rr;
  32387. shift_left <T> sl;
  32388. shift_right<T> sr;
  32389. sort <T> st;
  32390. nthelement <T> ne;
  32391. iota <T> ia;
  32392. sumk <T> sk;
  32393. axpy <T> b1_axpy;
  32394. axpby <T> b1_axpby;
  32395. axpyz <T> b1_axpyz;
  32396. axpbyz <T> b1_axpbyz;
  32397. axpbz <T> b1_axpbz;
  32398. dot <T> dt;
  32399. dotk <T> dtk;
  32400. bool register_package(exprtk::symbol_table<T>& symtab)
  32401. {
  32402. #define exprtk_register_function(FunctionName,FunctionType) \
  32403. if (!symtab.add_function(FunctionName,FunctionType)) \
  32404. { \
  32405. exprtk_debug(( \
  32406. "exprtk::rtl::vecops::register_package - Failed to add function: %s\n", \
  32407. FunctionName)); \
  32408. return false; \
  32409. } \
  32410. exprtk_register_function("all_true" ,at)
  32411. exprtk_register_function("all_false" ,af)
  32412. exprtk_register_function("any_true" ,nt)
  32413. exprtk_register_function("any_false" ,nf)
  32414. exprtk_register_function("count" , c)
  32415. exprtk_register_function("copy" ,cp)
  32416. exprtk_register_function("rotate_left" ,rl)
  32417. exprtk_register_function("rol" ,rl)
  32418. exprtk_register_function("rotate_right" ,rr)
  32419. exprtk_register_function("ror" ,rr)
  32420. exprtk_register_function("shftl" ,sl)
  32421. exprtk_register_function("shftr" ,sr)
  32422. exprtk_register_function("sort" ,st)
  32423. exprtk_register_function("nth_element" ,ne)
  32424. exprtk_register_function("iota" ,ia)
  32425. exprtk_register_function("sumk" ,sk)
  32426. exprtk_register_function("axpy" ,b1_axpy)
  32427. exprtk_register_function("axpby" ,b1_axpby)
  32428. exprtk_register_function("axpyz" ,b1_axpyz)
  32429. exprtk_register_function("axpbyz",b1_axpbyz)
  32430. exprtk_register_function("axpbz" ,b1_axpbz)
  32431. exprtk_register_function("dot" ,dt)
  32432. exprtk_register_function("dotk" ,dtk)
  32433. #undef exprtk_register_function
  32434. return true;
  32435. }
  32436. };
  32437. } // namespace exprtk::rtl::vecops
  32438. } // namespace exprtk::rtl
  32439. } // namespace exprtk
  32440. #endif
  32441. namespace exprtk
  32442. {
  32443. namespace information
  32444. {
  32445. static const char* library = "Mathematical Expression Toolkit";
  32446. static const char* version = "2.7182818284590452353602874713526624977572470936999595749"
  32447. "669676277240766303535475945713821785251664274274663919320";
  32448. static const char* date = "20200101";
  32449. static inline std::string data()
  32450. {
  32451. static const std::string info_str = std::string(library) +
  32452. std::string(" v") + std::string(version) +
  32453. std::string(" (") + date + std::string(")");
  32454. return info_str;
  32455. }
  32456. } // namespace information
  32457. #ifdef exprtk_debug
  32458. #undef exprtk_debug
  32459. #endif
  32460. #ifdef exprtk_error_location
  32461. #undef exprtk_error_location
  32462. #endif
  32463. #ifdef exprtk_disable_fallthrough_begin
  32464. #undef exprtk_disable_fallthrough_begin
  32465. #endif
  32466. #ifdef exprtk_disable_fallthrough_end
  32467. #undef exprtk_disable_fallthrough_end
  32468. #endif
  32469. } // namespace exprtk
  32470. #endif