diff --git a/CMakeLists.txt b/CMakeLists.txt index cc629b75..9c9ac947 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -112,6 +112,8 @@ add_subdirectory(rnn) add_subdirectory(rnn_tests) add_subdirectory(rnn_examples) +add_subdirectory(strategic) + # add_subdirectory(opencl) add_subdirectory(weights) diff --git a/strategic/CMakeLists.txt b/strategic/CMakeLists.txt new file mode 100644 index 00000000..4cf33f06 --- /dev/null +++ b/strategic/CMakeLists.txt @@ -0,0 +1,5 @@ +add_executable(evaluate_strategy evaluate_strategy.cxx forecaster.cxx trivial_forecaster.cxx strategy.cxx linucb.cxx bandit_strategy.cxx simple_stock_strategy.cxx state.cxx portfolio.cxx oracle.cxx portfolio_oracle.cxx) +target_link_libraries(evaluate_strategy examm_strategy exact_common exact_time_series exact_weights examm_nn pthread) + +add_executable(evaluate_bandit_strategy evaluate_bandit_strategy.cxx forecaster.cxx trivial_forecaster.cxx strategy.cxx linucb.cxx bandit_strategy.cxx simple_stock_strategy.cxx state.cxx portfolio.cxx oracle.cxx portfolio_oracle.cxx) +target_link_libraries(evaluate_bandit_strategy examm_strategy exact_common exact_time_series exact_weights examm_nn pthread) diff --git a/strategic/Data/stocks/AAPL_cleaned_with_predictions.csv b/strategic/Data/stocks/AAPL_cleaned_with_predictions.csv new file mode 100644 index 00000000..503f1bfc --- /dev/null +++ b/strategic/Data/stocks/AAPL_cleaned_with_predictions.csv @@ -0,0 +1,588 @@ +AAPL_RET,VOL_CHANGE,BA_SPREAD,ILLIQUIDITY,AAPL_PRC,sprtrn,DJI_Return,AAPL_predicted_RET +0.039833,-0.322814017617287,0.0002981815693981,1.94355448461434E-12,134.17999,0.007525,0.007583855,-0.0248544 +-0.020718,0.3096727656299750,0.001522146234562,-7.88190432463714E-13,131.39999,0.015366,0.015878141,-0.0675307 +-0.080061,0.285037453796781,0.0002481800132362,-2.57649577989058E-12,120.88,-0.035126,-0.027757926,-0.00765739 +0.000662,0.2898581554111920,8.26719576718825E-05,1.6505821104989E-14,120.96,-0.008133,-0.00563466,-0.0720853 +-0.067295,-0.3040439989104300,0.0007090941322461,-2.58485294433442E-12,112.82,-0.027756,-0.022479399,0.0146677 +0.039887,-0.2345064687418160,0.0005114217524718,1.92467290404744E-12,117.32,0.020145,0.015984212,-0.00786192 +-0.032646,0.0303070577170123,0.0004405674508767,-1.58053209365508E-12,113.49,-0.017585,-0.014526979,0.00752038 +-0.013129,-0.0073599020654093,8.928571428576E-05,-6.4886261071151E-13,112.0,0.000533,0.004759853,0.00104569 +0.029955,-0.225915737741596,8.66889168220287E-05,1.85687977676206E-12,115.355,0.012742,0.011844636,0.00165723 +0.001604,0.3179970018241320,8.65501125150676E-05,7.53196796786897E-14,115.54,0.005219,8.11E-05,-0.00760638 +-0.029514,-0.1595455151823540,0.000178364398466,-1.69913746296326E-12,112.13,-0.004619,0.001313823,-0.0044394 +-0.015964,0.1460760734919180,0.0003625158600689,-8.14924844366447E-13,110.34,-0.008412,-0.004651777,-0.0277133 +-0.03172,0.6162505646257860,9.35979034070116E-05,-1.03466421408347E-12,106.84,-0.011183,-0.008764989,0.00391942 +0.030326,-0.3184307082328120,0.0001816860465117,1.4086296446104E-12,110.08,-0.011571,-0.018429799,-0.00201564 +0.015716,-0.0645624818850023,8.94374385118068E-05,7.68310383129563E-13,111.81,0.010518,0.005174673,0.00134653 +-0.041946,-0.1768673022199500,0.0002800597460791,-2.60031202564577E-12,107.12,-0.023721,-0.019240889,0.00317031 +0.010269,0.111812294251014,0.0001848087229716,5.66754044606313E-13,108.22,0.002987,0.001954502,0.00343733 +0.037516,-0.1049929326593920,8.90630566441496E-05,2.22977818583889E-12,112.28,0.015977,0.013369965,-0.00395362 +0.023869,-0.0817444304305146,8.6986778009787E-05,1.5089381448647E-12,114.96,0.016111,0.015091639,0.00239307 +-0.007568,-0.2730198747683480,0.0002629503023928,-6.63124346594872E-13,114.09,-0.004813,-0.004763635,-0.00106046 +0.015076,0.4252763558093340,0.0002590449874795,9.13066516005453E-13,115.81,0.008254,0.01198569,0.00361478 +0.008462,-0.1859715364717520,8.56237691582405E-05,6.24295380269646E-13,116.79,0.005293,0.001267063,-0.00361005 +-0.03228,0.2457260698621180,8.84799150593268E-05,-1.97550634324702E-12,113.02,-0.009572,-0.004820445,0.00735311 +0.030791,-0.2655612318388110,0.0006866952789699,2.48910077641218E-12,116.5,0.017976,0.016827413,-0.00209652 +-0.028669,0.5201619707890040,0.0002651113467656,-1.56954710419295E-12,113.16,-0.013988,-0.013353428,0.00431218 +0.016967,-0.4001876003164160,0.0002606882168926,1.52280577536946E-12,115.08,0.017406,0.019108694,0.00074994 +-0.000956,-0.1383932591262900,8.69792119683841E-05,-9.96789791313071E-14,114.97,0.008007,0.004312152,0.00264119 +0.017396,0.2044878440428180,8.54920064974362E-05,1.48013970325313E-12,116.97,0.008791,0.005677669,0.000453781 +0.063521,1.3901354324509600,0.0010450160771703,2.12619080295787E-12,124.4,0.016419,0.008766923,-0.00295765 +-0.026527,0.0916665194711077,0.0003303055326176,-8.35524698355114E-13,121.1,-0.006307,-0.005468882,0.000968941 +0.000743,-0.4241198105522190,0.0004125752949914,4.06074003736216E-14,121.19,-0.006623,-0.005781438,0.00454697 +-0.003961,-0.2547605942525700,0.00057990224505,-2.91641243168049E-13,120.71,-0.001528,-0.000694423,-0.00296652 +-0.014001,0.0252610711848368,0.0005041169551336,-1.01974595277337E-12,119.02,0.000135,0.003934532,0.00671757 +-0.025542,0.0452044001066211,8.6221762372867E-05,-1.82651585927802E-12,115.98,-0.01633,-0.014363636,-0.0015912 +0.013192,0.031412057289371,8.50991404987245E-05,9.02724571173932E-13,117.51,0.004727,0.004020835,0.00498579 +-0.005446,-0.2772897777044850,8.556515786776E-05,-5.18477414376488E-13,116.87,-0.002196,-0.003460718,-0.0041303 +-0.009583,0.134229091324612,0.0006047516198704,-8.12147582744474E-13,115.75,0.005219,0.005417774,0.00715328 +-0.006134,-0.1887613496428670,8.69262865089613E-05,-6.44763927868555E-13,115.04,0.003446,-0.000990346,-0.00155585 +8.7E-05,0.3517748952088710,0.000173837461973,6.76447485487276E-15,115.05,-0.01859,-0.022946051,0.00394117 +0.013472,-0.1749061695447590,0.0001715265866208,1.25265547558331E-12,116.6,-0.003026,-0.008025586,-0.00404282 +-0.046312,0.5596209613867650,0.0008992805755395,-2.89512822400628E-12,111.2,-0.035288,-0.034345619,0.0068706 +0.03705,0.0150961112080074,0.000780437044745,2.20016609829403E-12,115.32,0.011947,0.005247376,-0.00192213 +-0.056018,0.3035104443989470,0.0007348888480617,-2.7034394304926E-12,108.86,-0.01213,-0.005908291,0.0059151 +-0.000827,-0.3549691493896850,9.19371150132473E-05,-6.19260342983244E-14,108.77,0.012318,0.015978325,0.00501413 +0.015354,-0.124008725844135,9.05469032958249E-05,1.29262409216263E-12,110.44,0.017799,0.020611977,6.09471E-05 +0.040837,0.2843794074163750,8.6994345367472E-05,2.57174928907079E-12,114.95,0.022047,0.01337811,0.000836964 +0.035494,-0.0856262838610629,0.0002520373015206,2.36079649463307E-12,119.03,0.01946,0.019481692,-0.00206688 +-0.001134,-0.0942190486919127,8.42530963012124E-05,-8.35094804621174E-14,118.69,-0.000288,-0.002352197,0.00174494 +-0.019968,0.349354676660591,8.59697386519163E-05,-1.11196447590288E-12,116.32,0.0117,0.029465753,0.00321305 +-0.003009,-0.1203534456731720,8.62291972062181E-05,-1.91064086932845E-13,115.97,-0.0014,0.009018091,0.000572739 +0.030353,-0.1734286882817050,0.0001673780232656,2.26304018343697E-12,119.49,0.007652,-0.000791582,0.000784043 +-0.002343,-0.0786754650463538,0.0002516567402063,-1.90050566620763E-13,119.21,-0.009979,-0.010798861,-0.00173294 +0.000419,-0.2105010429559300,8.38504108670561E-05,4.30305825346312E-14,119.26,0.01361,0.01374272,0.004662 +0.00872,0.115905466646546,8.31255195344215E-05,7.95575609092616E-13,120.3,0.011648,0.015964448,-0.00217208 +-0.007564,-0.1849603114136880,0.0002512773264092,-8.53169679890248E-13,119.39,-0.004792,-0.005578878,0.0041702 +-0.011391,0.0240130336538118,8.47242226553005E-05,-1.26915833240308E-12,118.03,-0.011564,-0.011581293,-0.000716813 +0.005168,-0.0250989390484226,8.42886041807579E-05,5.87593772832133E-13,118.64,0.003946,0.001522179,0.00374809 +-0.010958,-0.0078782660107054,8.52224305437627E-05,-1.2697144619858E-12,117.34,-0.006793,-0.007453389,-0.00147443 +-0.029743,0.737894143585287,0.0002635046113307,-2.04385118150742E-12,113.85,0.005636,0.011201301,0.00763425 +0.011594,-0.1098144730827840,8.68281670574378E-05,8.84730367875437E-13,115.17,0.016162,0.015375167,-0.000462001 +0.007467,-0.3283888888493410,8.61846074291573E-05,8.42121958514051E-13,116.03,-0.001584,-0.005783404,0.00244834 +0.004826,-0.3894536712540340,8.57706492837371E-05,8.87169338783025E-13,116.59,0.002397,0.001268674,-0.00117711 +0.0211,2.627347436053290,0.0001679966400671,1.04723562772351E-12,119.05,-0.004595,-0.00908476,0.00128845 +0.030827,-0.2437369489549400,8.14863102997955E-05,1.96261171384995E-12,122.72,0.011271,0.006251275,-0.00378134 +0.002934,-0.3050909630660350,8.12479688008216E-05,2.68017488485136E-13,123.08,0.001791,0.00200742,0.00270424 +-0.001137,-0.113408858205206,0.0008947454042622,-1.17282814488356E-13,122.94,-0.000624,0.002868795,-0.000609195 +-0.005613,-0.0091886744821021,8.17995910020868E-05,-5.8765486480077E-13,122.25,0.008836,0.008299774,0.00464282 +0.01227,0.109177766154576,0.0003232323232322,1.14412733320105E-12,123.75,-0.001936,-0.004913278,-0.00199988 +0.005091,-0.0521874832213088,0.0002411963338157,4.98316320126036E-13,124.38,0.002787,0.003461674,0.00263841 +-0.020904,0.4023308108416620,0.0005748070290687,-1.49023760101526E-12,121.78,-0.007949,-0.003482161,0.000498777 +0.011989,-0.2945693541391650,0.0002434274586173,1.19723398952078E-12,123.24,-0.001285,-0.002313054,0.00266959 +-0.006735,0.0682771606563994,8.16926721672323E-05,-6.33847126904697E-13,122.41,-0.001265,0.001570351,-0.00211779 +-0.005147,-0.0875562340449592,0.0005748070290687,-5.33624688372829E-13,121.78,-0.004359,-0.006151105,0.00510705 +0.05009,0.9856021200377220,7.81983109165242E-05,2.49065682200114E-12,127.88,0.012921,0.011310858,-0.00624308 +-0.000547,-0.3760910352831080,7.82411391910267E-05,-4.36181009612114E-14,127.81,0.001773,-0.001482533,0.00305365 +0.006963,-0.0389683230748827,0.0003885780885779,5.73752257505415E-13,128.7,0.005758,0.004935578,-0.000873602 +-0.01589,1.0409994642722900,7.8954640558927E-05,-6.51876351703523E-13,126.655,-0.003511,-0.00410246,0.00421315 +0.012435,-0.3710530155174870,7.80628558061491E-05,8.01135130697612E-13,128.23,-0.003906,0.001239218,-0.00166259 +0.028465,0.3981255387415590,0.00030330603579,1.27536856977906E-12,131.88,-0.002073,-0.006650002,-0.000790646 +-0.006976,-0.4790166629523590,7.64355470041771E-05,-6.04153644268682E-13,130.96001,0.000746,0.003808708,7.90854E-05 +0.007712,-0.3774192679463590,0.0002273243919072,1.0645737556734E-12,131.97,0.003537,0.002324575,0.00301534 +0.035766,1.2664506568829600,0.0001463896407931,2.10315514907159E-12,136.69,0.008723,0.006758359,-0.00466213 +-0.013315,-0.0278987528318507,0.0002965077482021,-8.16304133974368E-13,134.87,-0.002227,-0.002246443,0.00402074 +-0.008527,-0.2104789743348810,7.47083457970964E-05,-6.67824545913325E-13,133.72,0.001342,0.002435767,0.000525595 +-0.007703,0.0372159569325276,0.0002260908885372,-5.86158404939137E-13,132.69,0.006439,0.006475592,0.00438712 +-0.024719,0.4457535132208640,7.7351054787065E-05,-1.33401925125648E-12,129.41,-0.014755,-0.012500289,0.000436837 +0.012364,-0.3185758615425710,7.64063870245506E-05,9.67244136715884E-13,131.00999,0.007083,0.005548888,0.00352114 +-0.033662,0.5883528019251070,0.0007898894154819,-1.71569766170073E-12,126.6,0.00571,0.014405322,0.000891392 +0.034123,-0.293285153855532,7.63061411550271E-05,2.3797511434167E-12,130.92,0.014847,0.00686781,0.00414026 +0.008631,-0.0406757351553689,7.58046194624953E-05,6.22081972823986E-13,132.05,0.005492,0.001831114,-0.00544809 +-0.023249,-0.0427993020213741,7.75314002170174E-05,-1.79227151872192E-12,128.98,-0.006555,-0.002870967,0.00793174 +-0.001396,-0.0858815855091617,0.0002329192546583,-1.17893265171178E-13,128.8,0.000416,0.001934941,-0.00351356 +0.016227,-0.0365913905282487,7.64000305599428E-05,1.3997184469294E-12,130.89,0.002276,-0.000264535,0.00356012 +-0.015127,0.0169053031579613,7.75735008920247E-05,-1.30285056028553E-12,128.91,-0.003753,-0.002219901,-0.00222305 +-0.013731,0.2637552425121120,7.8653452886622E-05,-9.48823418883005E-13,127.14,-0.00719,-0.005719622,0.00638141 +0.005427,-0.2029714703260480,0.0001564577955097,4.67970633560551E-13,127.83,0.008136,0.003772921,-0.00182228 +0.032856,0.1493032945821240,7.57403620388617E-05,2.386706319397E-12,132.03,0.013936,0.008336793,0.00213703 +0.036658,0.1562622819774130,7.30620296631176E-05,2.22157539714473E-12,136.87,0.000317,-0.000396657,-0.00627304 +0.016074,-0.0511740870727254,0.000287696822629,1.01042596703189E-12,139.07001,-0.003011,-0.005742534,0.00191367 +0.027684,0.3775961178658330,0.0001398684578785,1.22921526059931E-12,142.92,0.003616,-0.001193035,-0.00439449 +0.001679,-0.3759166224490780,6.99217658563431E-05,1.19255523015016E-13,143.16,-0.001489,-0.000741632,0.00246483 +-0.007684,0.4475088245061390,0.0010559622694636,-3.79965198488947E-13,142.06,-0.025678,-0.020489005,-0.00180802 +-0.034985,0.001118115744034,0.0003647968487855,-1.79068442644856E-12,137.09,0.009761,0.009906206,0.00752255 +-0.037421,0.2451647415776270,0.0002273416014442,-1.59804567969316E-12,131.96001,-0.019312,-0.020283402,0.00319808 +0.01652,-0.4015985284233520,7.44744297004335E-05,1.15977896669686E-12,134.14,0.016052,0.007647465,0.0037785 +0.006337,-0.2159105965968250,7.41536355173431E-05,5.63819354860749E-13,134.99001,0.013898,0.015741153,-0.00182002 +-0.007778,0.0790974862436044,7.47349559503814E-05,-6.46330820741894E-13,133.94,0.001009,0.001176999,0.00498632 +0.025758,-0.0634829269554451,7.27127156271647E-05,2.2281198003719E-12,137.39,0.010853,0.01081448,-0.00369724 +-0.003093,-0.0986650193775855,7.31939217019722E-05,-2.98205848066136E-13,136.75999,0.003897,0.002974668,0.00359075 +0.001097,-0.0605138526841786,7.31137243444166E-05,1.12454379284912E-13,136.91,0.007399,0.007625456,-0.000537447 +-0.006574,0.0770475209593666,7.34504869825204E-05,-6.29838118718613E-13,136.00999,-0.001113,-0.000316376,0.00379627 +-0.004558,-0.0486723073130722,0.0001476475367457,-4.61134530105396E-13,135.39,-0.000345,0.00197511,-0.000203384 +-0.00192,-0.1182340971372620,7.40028121067928E-05,-2.20717141033082E-13,135.13,0.001662,-0.000225892,0.00361749 +0.001776,-0.0664855605942539,7.38716111397718E-05,2.18316270031408E-13,135.37,0.004711,0.000881341,-0.00019348 +-0.016104,0.3397179264064930,7.50807117650793E-05,-1.50180776184713E-12,133.19,-0.000569,0.002045546,0.00464833 +-0.017644,0.2179153761791260,7.65056557627184E-05,-1.37528150255101E-12,130.84,-0.00032,0.002863631,0.00102842 +-0.008636,-0.0090881639405115,0.0002312851567893,-6.85234488141098E-13,129.71001,-0.004416,-0.003785772,0.00425059 +0.001233,-0.0985717792201065,0.0003080003080002,1.08398471406334E-13,129.87,-0.001855,3.11E-05,-0.00160463 +-0.029799,0.1852688107798400,7.936507936512E-05,-2.2781546927723E-12,126.0,-0.007733,0.000869018,0.00543135 +-0.001111,0.5232824712420300,7.94533608772058E-05,-5.58210437029757E-14,125.86,0.001256,0.000496806,0.000398665 +-0.004052,-0.2982145138306610,7.9776625448671E-05,-2.91281120804974E-13,125.35,0.011352,0.01346054,0.00366154 +-0.034783,0.3340173162454360,8.26514587982901E-05,-1.94188421579283E-12,120.99,-0.024479,-0.017516178,0.00165358 +0.002232,0.1095585796402060,0.0006597394029358,1.12055237925892E-13,121.26,-0.00475,-0.014955751,0.0042218 +0.053851,-0.292710769294962,7.82533844588067E-05,3.6270654505767E-12,127.79,0.023791,0.019498688,-0.00481957 +-0.020894,-0.1203716694098170,7.99232736573299E-05,-1.63400784176439E-12,125.12,-0.008081,-0.004565971,0.00343912 +-0.024457,0.1045078306874220,8.19269211862273E-05,-1.77508968546046E-12,122.06,-0.013066,-0.003868232,0.00232277 +-0.015812,0.577031877453948,0.0002497294597519,-7.39410032759592E-13,120.13,-0.013417,-0.011063263,0.00341285 +0.010738,-0.1370657995744800,0.0002470762642068,5.75712289068115E-13,121.42,0.019496,0.018502055,0.000371938 +-0.041674,0.0043157705237946,8.59401856308449E-05,-2.32147238180736E-12,116.36,-0.005359,0.009719829,0.00525067 +0.040607,-0.161264725992244,8.2586612710122E-05,2.59171771764898E-12,121.085,0.014155,0.000952782,0.00063137 +-0.009126,-0.1355312360257630,8.33472245374655E-05,-6.79985167734101E-13,119.98,0.00603,0.014584962,6.07434E-05 +0.016503,-0.0797472857826649,8.19940964249828E-05,1.31451700850481E-12,121.96,0.010395,0.005838629,0.00253919 +-0.007625,-0.1446421569871770,8.2624142774561E-05,-7.15516574964363E-13,121.03,0.001015,0.009020947,2.44606E-05 +0.024457,0.0511687482314644,8.0651665456933E-05,2.13116446858012E-12,123.99,0.006492,0.005333361,0.00115045 +0.012743,0.2441086282491920,7.96368559368552E-05,8.81308441779795E-13,125.57,-0.00157,-0.003869448,-0.00221914 +-0.006451,-0.0286431107367574,0.0002404616864379,-4.62290525021954E-13,124.76,0.002879,0.005770492,0.0032891 +-0.033905,0.0850233328638661,8.29668962083374E-05,-2.31789004967503E-12,120.53,-0.014761,-0.004636335,0.0027791 +-0.00448,0.5282747155007040,0.0001666805567131,-2.01305560698621E-13,119.99,-0.000603,-0.007130666,0.0032393 +0.028336,-0.39692321572939,8.1043844720035E-05,2.05309374648295E-12,123.39,0.007025,0.003163804,-0.00118214 +-0.006889,-0.1470447292078520,8.16060062019823E-05,-5.89253610287134E-13,122.54,-0.007631,-0.009411474,0.000376035 +-0.019994,-0.0724067682855561,8.3270880173246E-05,-1.88130502353304E-12,120.09,-0.005467,-9.53E-05,0.00410269 +0.004164,0.1163667871269680,0.0001658512314453,3.49509424145863E-13,120.59,0.00524,0.006151127,-8.20856E-05 +0.005141,-0.0486943803251189,8.2501443775191E-05,4.51282565041288E-13,121.21,0.016631,0.013899622,0.00310203 +0.001485,-0.1404690709340060,8.23791086580865E-05,1.51433317258903E-13,121.39,-0.000868,0.002978035,-0.000448448 +-0.012274,0.0601125632301964,0.0002502085070892,-1.19534384134874E-12,119.9,-0.003158,-0.003147598,0.00374467 +0.018766,0.3806000813199580,0.0001637331150224,1.29938024136941E-12,122.15,0.003623,-0.002582945,-0.00113651 +0.006959,-0.3655841623278730,8.13008130081717E-05,7.54268075683177E-13,123.0,0.011825,0.005204733,0.00198766 +0.023577,0.181285577432487,7.94281175535417E-05,2.1134496866849E-12,125.9,0.014438,0.011280369,-0.000227473 +0.002462,-0.0958670411793752,7.92330243244664E-05,2.43495579192757E-13,126.21,-0.000974,-0.002891776,0.000865263 +0.01339,0.0413274054093417,0.0001563721657544,1.25493009152982E-12,127.9,0.001475,0.00047931,-0.000154754 +0.019234,0.0648832033773725,7.67106474377946E-05,1.66085907459056E-12,130.36,0.004221,0.001713453,-0.000491881 +0.020213,0.2001435397564020,7.51156058497517E-05,1.42550844433992E-12,132.995,0.00772,0.00886566,-0.00113616 +-0.013196,-0.1429150484962010,7.61200795396749E-05,-1.1003390203711E-12,131.24001,-0.000196,-0.001633199,0.00274997 +0.024307,-0.0019603596686614,7.44625511018343E-05,1.98261261786492E-12,134.42999,0.003295,-0.00201891,-0.000671159 +-0.017853,-0.0441669068060058,0.0003028857077935,-1.55116926179502E-12,132.03,-0.004088,0.001592204,0.0014523 +0.018708,0.0241110617504758,7.42750929367118E-05,1.5580400894884E-12,134.5,0.011094,0.009045052,0.00135696 +-0.002528,-0.0493024537778784,0.0001490757304711,-2.22016472610842E-13,134.16,0.003609,0.004838514,0.00020305 +0.005069,0.1102935535680150,7.40878077722942E-05,3.98930193276723E-13,134.84,-0.005306,-0.003597677,0.00140018 +-0.01283,0.0054776532060381,7.51258357748547E-05,-1.0172715766381E-12,133.11,-0.006802,-0.007521889,0.000716133 +0.00293,-0.2737735441509290,7.48314606740654E-05,3.1895926801775E-13,133.5,0.009306,0.009343455,0.0029144 +-0.011685,0.2281202370611270,7.57920266787245E-05,-1.04799743706245E-12,131.94,-0.009211,-0.009415217,0.00060627 +0.018039,-0.0679896794189631,0.0001489725916487,1.70513592749527E-12,134.32001,0.010929,0.006730262,0.00163558 +0.002978,-0.1510750809963400,0.0001484560570072,3.30605899771889E-13,134.72,0.001782,-0.00181879,-1.86886E-05 +-0.00245,-0.0137831408377763,0.0002975667832427,-2.7646788373847E-13,134.39,-0.000215,9.89E-05,0.00211531 +-0.006027,0.6335805271498310,0.0011977092379098,-4.18856020520817E-13,133.58,-0.000846,-0.004841875,0.0016586 +-0.000749,0.401658085379843,7.49925082411035E-05,-3.71645212867576E-14,133.48,0.006763,0.007095736,0.00207309 +-0.015133,-0.272806024086794,0.0003043511102731,-1.04844106258553E-12,131.46001,-0.007195,-0.005446443,0.00205734 +0.008215,-0.3160790887044280,7.54489267729E-05,8.25405583481837E-13,132.53999,0.002748,0.007037047,0.000810703 +-0.035386,0.8302279882987150,0.0001564333202971,-2.01387409954385E-12,127.85,-0.006678,0.000580443,0.00343813 +0.001955,-0.3892339598444330,0.0001562060767987,1.81812731827321E-13,128.10001,0.000704,0.002850863,0.0026666 +0.012802,-0.06436789367807,7.71543026705679E-05,1.25639290090411E-12,129.74001,0.008165,0.009295596,-0.000944626 +0.005318,0.0096278675893719,0.0001536748211601,5.1506757347985E-13,130.21001,0.007373,0.006635028,0.00207946 +-0.025805,0.1099473925451640,7.8833267638984E-05,-2.31137943633327E-12,126.85,-0.010436,-0.001004705,0.00175517 +-0.00741,0.4318288363507310,7.9421809228742E-05,-4.67008443547059E-13,125.91,-0.008674,-0.013633325,0.00339543 +-0.024939,-0.110429824125237,8.14531237273366E-05,-1.81206308841767E-12,122.77,-0.021449,-0.019886685,0.00115087 +0.01792,-0.0562362801878685,8.00192046091471E-05,1.3553625823986E-12,124.97,0.012173,0.012915132,0.00199059 +0.019845,-0.2262304236761920,0.0001569242840329,1.90205412025184E-12,127.45,0.014918,0.010601538,-0.0010534 +-0.009259,-0.09346539961044,0.0002375861249703,-9.88077762860119E-13,126.27,-0.00253,-0.001580468,0.00288788 +-0.011246,-0.1470843411249820,8.00961153384471E-05,-1.42308442809298E-12,124.85,-0.008517,-0.00778171,0.00145601 +-0.001282,0.4616957156427540,0.0001603977865105,-1.11127248200093E-13,124.69,-0.002943,-0.004833174,0.0017709 +0.021012,-0.169772494492707,7.85484251040052E-05,2.14868086607471E-12,127.31,0.010555,0.005549598,-0.00020153 +-0.014767,0.0319801727545345,7.97257434425984E-05,-1.48520547574328E-12,125.43,-0.000784,0.003629001,0.00178912 +0.013314,-0.2042612152997190,7.86782061369403E-05,1.66068844887925E-12,127.1,0.009911,0.005441461,0.00239593 +-0.001574,0.1411436172864860,0.0002364066193852,-1.7231693581162E-13,126.9,-0.002125,-0.002370169,-0.000910436 +-0.000394,-0.2143643893120180,0.0001576665352779,-5.49249217698852E-14,126.85,0.001877,0.00030863,0.00322693 +-0.012377,0.6725829617611920,0.0002394636015324,-1.04450295883796E-12,125.28,0.001165,0.004125211,0.000576968 +-0.005348,-0.2468731660417130,0.0001605007623785,-6.0248523625058E-13,124.61,0.000769,0.001880437,0.0037082 +-0.002648,-0.0511245903879454,8.04634695847353E-05,-3.15221223811645E-13,124.28,-0.000492,0.001328124,-0.00062586 +0.006276,-0.1233119610790070,0.0001599232368463,8.46872721093431E-13,125.06,0.001447,0.000725093,0.00231844 +-0.012154,0.2855918403474030,8.09454427714983E-05,-1.29140410041547E-12,123.54,-0.003629,-0.000674555,0.000178664 +0.019022,-0.0139246419589681,7.94344268806507E-05,2.01143204075245E-12,125.89,0.008834,0.005187013,0.00199488 +7.9E-05,-0.0545758817024741,7.94281175535417E-05,8.83517394148927E-15,125.9,-0.000797,-0.003629616,-0.0013698 +0.006672,0.0468633225418642,7.89016884961742E-05,7.08053531781859E-13,126.74,0.000175,-0.000878364,0.00281467 +0.003077,-0.2352597116390910,7.86596397388903E-05,4.25685872619778E-13,127.13,-0.001824,-0.004412731,-0.00167178 +-0.008023,0.2513047941109100,7.92958528269377E-05,-8.94198518748867E-13,126.11,0.004652,0.000554405,0.0045862 +0.009833,-0.2483989787602090,7.85237534354544E-05,1.44393089194957E-12,127.35,0.001948,0.000387721,-0.00141134 +0.024578,0.8118957047246820,7.67167381975973E-05,1.94414527634555E-12,130.48,0.001815,-0.002489923,0.000208623 +-0.006438,-0.352738741387078,7.70595495216579E-05,-7.91878331269441E-13,129.64,-0.002012,-0.002745321,-0.000481663 +0.003934,0.4635959294181170,7.67575932969042E-05,3.29318048211427E-13,130.14999,-0.00539,-0.007745232,0.00238469 +0.012601,0.0530146070362997,7.58024186813257E-05,9.89266966067914E-13,131.78999,-0.000436,-0.006176902,-0.00203299 +-0.010092,0.1265715530213580,0.0001533803347093,-7.10447473822235E-13,130.46001,-0.013125,-0.01576927,0.00263065 +0.014104,-0.2687667187359990,7.56613756615457E-05,1.33893238325866E-12,132.3,0.014002,0.017629596,-0.000689621 +0.012698,-0.061257480818334,7.46380056724206E-05,1.26801692540554E-12,133.98,0.005125,0.002025251,0.00097094 +-0.00209,-0.1945755667881550,7.4794315631944E-05,-2.59668805368271E-13,133.7,-0.001083,-0.002101595,-1.59632E-05 +-0.002169,0.1421453726587530,7.48819428829634E-05,-2.36458366107867E-13,133.41,0.005811,0.009522931,0.00261594 +-0.002249,0.0289477870965473,0.0001501765457141,-2.38819041522892E-13,133.11,0.003331,0.00693104,7.96825E-05 +0.012546,-0.1224052787773130,7.41207894345432E-05,1.49925673307801E-12,134.78,0.002315,-0.004372742,0.00140086 +0.0115,0.0403940731983678,7.32780752586823E-05,1.30588433696163E-12,136.33,0.000277,0.000263088,-0.0018639 +0.004621,-0.0213705260659754,0.0001460280267211,5.33730726088955E-13,136.96001,0.001328,0.006130319,0.00143687 +0.002263,-0.1700974596573850,7.28491294528368E-05,3.14240272012476E-13,137.27,0.005222,0.003797391,-0.000513687 +0.019596,0.504662970168847,0.0002858673702582,1.77368770116958E-12,139.96001,0.0075,0.004412496,0.00119273 +0.014718,0.3692793594368040,7.04830305592346E-05,9.58784307560934E-13,142.02,-0.002022,-0.006007542,-0.00265573 +0.017955,-0.0301107460163421,0.0001384104490273,1.18469533383917E-12,144.57001,0.003359,0.003019835,0.000749487 +-0.0092,0.0080231238828427,6.98827094468513E-05,-6.07788487139229E-13,143.24001,-0.008561,-0.007492675,-0.00110272 +0.013055,-0.0553749394202195,0.0002067397146992,9.01257839911811E-13,145.11,0.011278,0.013021654,0.00260446 +-0.004204,-0.2362759340114990,6.91349480968009E-05,-3.81617169317404E-13,144.5,0.003451,0.003613965,-0.00144994 +0.007889,0.321928048698219,0.000137393573194,5.3748520445384E-13,145.64,-0.003517,-0.003068639,0.00272599 +0.0241,0.2590215010410240,6.69795552784665E-05,1.27346172119544E-12,149.14999,0.001165,0.001273802,-0.00481895 +-0.004492,-0.1596146376144900,6.73491379309732E-05,-2.83717020540312E-13,148.48,-0.003262,0.001539768,0.0026013 +-0.014076,-0.126199553986358,0.0002049320308762,-1.03197502518109E-12,146.39,-0.007539,-0.008550827,-0.000181683 +-0.026914,0.3022210791859570,7.02000702000064E-05,-1.55715703845967E-12,142.45,-0.01587,-0.020924112,0.00515208 +0.025974,-0.2009809151813880,6.83544350568628E-05,1.83315636953746E-12,146.14999,0.015163,0.016193057,-0.00203468 +-0.005132,-0.2272403946945990,6.87070198561647E-05,-4.71126274156081E-13,145.39999,0.008242,0.008287315,0.00227997 +0.009629,0.0317428218782966,6.81880108993358E-05,8.48591601076993E-13,146.8,0.002017,0.000728535,0.000413593 +0.011989,-0.0765188291382633,6.73801830909672E-05,1.13056782712375E-12,148.56,0.010145,0.006840215,0.0006262 +0.002895,0.0139629288618017,0.0001342371881175,2.68463281607386E-13,148.99001,0.002382,0.002360358,3.4972E-05 +-0.0149,0.4464986462528370,0.0002044014444368,-9.69671024790452E-13,146.77,-0.004712,-0.002441051,0.00256466 +-0.012196,0.1344496671874380,6.90440060699579E-05,-7.08271118111641E-13,144.98,-0.000186,-0.003639339,0.00236432 +0.004552,-0.5230674949654520,0.0001373249107386,5.51765920253369E-13,145.64,0.004206,0.004397294,0.00164091 +0.001511,0.2421714182597080,0.0004798436857259,1.47224474452473E-13,145.86,-0.005406,-0.004248667,-0.00114817 +-0.002331,-0.107725836377034,6.87877954921832E-05,-2.55136754751904E-13,145.52,-0.001843,-0.002785381,0.00265312 +0.012644,0.0312789078048185,0.0001357220412595,1.32520229265318E-12,147.36,0.008203,0.007986595,-0.0014362 +-0.002782,-0.1298264021315800,6.80503572643138E-05,-3.36015210645245E-13,146.95,-0.004632,-0.009218672,0.00217581 +0.000749,-0.1774347428473050,6.79994560042901E-05,1.09897622220945E-13,147.06,0.006005,0.007805613,-2.03435E-05 +-0.00476,0.166618487714885,0.0003421376762007,-6.02434777694853E-13,146.14,0.001675,0.004114211,0.00260888 +-0.000342,-0.0963554197062521,6.84509548907585E-05,-4.79159556390981E-14,146.09,-0.00094,-0.003029386,-8.38579E-05 +-0.003354,0.4111394001045910,6.8681313964133E-05,-3.34122923546355E-13,145.60001,0.000993,0.004638511,0.00219496 +0.001786,-0.2971704964560570,6.84903331963263E-05,2.52696880421553E-13,145.86,0.002468,0.006246957,-0.000364819 +0.020773,0.5214940516353530,6.71636778829398E-05,1.89242234587945E-12,148.89,0.002952,0.000419412,0.000205238 +0.00141,-0.1952965896587000,6.71361457319425E-05,1.59400608371867E-13,149.10001,0.001607,0.000437392,-0.00122435 +0.013548,0.7443815091285610,6.6172578083582E-05,8.66284019947592E-13,151.12,0.002621,0.0030978,0.00159761 +-0.006154,-0.1093562077916490,0.0002662627338703,-4.44548848384487E-13,150.19,-0.007061,-0.00791899,-0.00170157 +-0.025501,-0.0640743235685363,6.83246788739472E-05,-2.01974463577726E-12,146.36,-0.010748,-0.010824967,0.00538215 +0.002323,0.0020407290546713,0.0002044989775051,1.83187305475778E-13,146.7,0.001257,-0.001904147,-0.00081047 +0.010157,-0.2996636441469090,0.0001349618732708,1.1321817786131E-12,148.19,0.008142,0.006475504,0.0020497 +0.010257,-0.0073011766893315,0.0001336583973243,1.14004400637506E-12,149.71001,0.008524,0.006139873,-0.00142768 +-0.000601,-0.1916617760457660,6.68359844939908E-05,-8.26882508833961E-14,149.62,0.001496,0.000864587,0.0026154 +-0.008421,0.2126582205520160,0.0,-9.63534814564737E-13,148.36,0.00222,0.001109483,0.000397164 +-0.005527,-0.1757593899671760,0.0002033347026795,-7.71518377202542E-13,147.53999,-0.005825,-0.005433588,0.00256675 +0.007185,0.1478215955854710,0.0002018842394425,8.67561163763078E-13,148.60001,0.008808,0.00689174,-0.000581144 +0.030417,0.6306311420835540,6.53735632183521E-05,2.18585270736907E-12,153.12,0.004307,-0.00157833,-0.000173868 +-0.008425,-0.0498594257276474,0.0001975894092076,-6.42629842801527E-13,151.83,-0.001349,-0.00110479,-0.0012031 +0.004479,-0.0690303045253134,6.56350446290273E-05,3.65338799858055E-13,152.50999,0.000312,-0.001363072,0.00329859 +0.007475,-0.1146020076600990,6.51480680214981E-05,6.83523036074273E-13,153.64999,0.002843,0.003717917,-0.00305766 +0.00423,-0.1878341365707920,0.0004536616979908,4.74246576955328E-13,154.3,-0.000335,-0.00210842,0.00296598 +0.015489,0.4225549398351990,6.38841023678761E-05,1.20210613809686E-12,156.69,-0.003395,-0.007608051,-0.00353968 +-0.010084,-0.0958786296813043,6.44703758622326E-05,-8.74433968668384E-13,155.11,-0.001319,-0.001963809,0.00360771 +-0.006705,-0.2297325368566830,0.0001297462108297,-7.59929141711455E-13,154.07001,-0.004606,-0.004330196,-0.000632854 +-0.033102,1.457289375769610,0.0002013828287574,-1.57903421780664E-12,148.97,-0.007723,-0.007788561,0.00533396 +0.003893,-0.2727407951393280,0.0001336676696757,2.54357697088477E-13,149.55,0.002277,0.007567969,1.20246E-06 +-0.009562,0.0672492392454415,0.0003375641371861,-5.91038919796582E-13,148.12,-0.005747,-0.00837573,0.001793 +0.006144,-0.2376124980557200,0.0001342682681338,4.95088434874107E-13,149.03,0.008474,0.006848958,0.00107872 +-0.00161,-0.1838468941613790,6.71416134917151E-05,-1.59215666672908E-13,148.78999,-0.001551,-0.001811616,0.000911974 +-0.018348,0.9095584589119050,0.0002053950431329,-9.67961569448919E-13,146.06,-0.009111,-0.004789499,0.00161622 +-0.021361,-0.0493327289654849,0.000209878270603,-1.2112671512124E-12,142.94,-0.016977,-0.017765283,0.00314834 +0.003428,-0.3857080091575620,6.9790146398212E-05,3.15353844186093E-13,143.42999,-0.000812,-0.00149038,2.24219E-05 +0.016872,0.00732503957466,6.84950244433727E-05,1.51526209144925E-12,145.85001,0.00952,0.009978835,0.000509682 +0.006719,-0.1515080861645560,6.80378669208454E-05,7.06431065553563E-13,146.83,0.012135,0.01478473,-0.000568676 +0.000613,-0.1754256657359440,0.0002041927579635,7.81141459772947E-14,146.92,0.001461,0.000954404,0.00247797 +-0.01055,0.3874839468989740,0.0001375111783724,-9.7926410627656E-13,145.37,-0.002776,0.002051011,-0.000266655 +-0.023801,0.4689545189841280,0.0002114015925586,-1.54062173924315E-12,141.91,-0.020364,-0.016329024,0.00359985 +0.006483,-0.3153368442735800,0.0002100399075824,6.0896656054361E-13,142.83,0.001569,0.002645204,-0.000781421 +-0.009312,0.1939425236258240,0.0002120141342756,-7.39503045783916E-13,141.5,-0.01191,-0.015899548,0.00202624 +0.008127,0.063387419530293,0.001191657987498,6.02033191734086E-13,142.64999,0.011491,0.014257776,2.38979E-05 +-0.024606,0.038058378827892,0.0002156101768003,-1.80023484655399E-12,139.14,-0.012986,-0.009425354,0.00270961 +0.014158,-0.1778177037145580,7.07958330381699E-05,1.24227040314962E-12,141.11,0.010524,0.00916833,0.000825016 +0.006307,0.0299156491671874,7.04225352112036E-05,5.33955238610743E-13,142.0,0.004103,0.00298171,-0.000194649 +0.009084,-0.258448622324818,6.97187570463766E-05,1.02775687878432E-12,143.28999,0.008298,0.009819369,0.000929337 +-0.002722,-0.0478473866203305,0.0002098670545743,-3.24323544493179E-13,142.89999,-0.001914,-0.000250077,0.000435549 +-0.00063,0.0966565296653587,7.00231076254527E-05,-6.84910551308067E-14,142.81,-0.006866,-0.00720053,0.000747697 +-0.009103,0.1332552285794470,0.0001414034443788,-8.81295672184938E-13,141.50999,-0.002417,-0.003412528,0.00149073 +-0.00424,0.0781889917361047,0.0001419345681641,-3.82343175904012E-13,140.91,0.003023,-1.55E-05,0.00188277 +0.020226,-0.1122031895874410,6.94908228637727E-05,2.01366717288471E-12,143.75999,0.017063,0.015555093,0.000492851 +0.007513,-0.0284278454982012,0.0001380143606738,7.6412698071247E-13,144.84,0.00746,0.01094744,-0.000969057 +0.011806,0.2598300545811820,6.83043329923064E-05,9.4198861366507E-13,146.55,0.003375,-0.001024298,0.0012077 +0.01508,-0.1075939137129020,6.71551537479112E-05,1.32825474075207E-12,148.75999,0.007393,0.005635481,-0.00183437 +0.003361,-0.2354600191514050,6.70641877973734E-05,3.85914482132685E-13,149.25999,0.003664,0.004287727,0.00145058 +0.001474,0.0518116120490121,0.0001338640620819,1.60672816058437E-13,149.48,0.002996,-0.000175845,-0.000328067 +-0.005285,-0.0411866654635169,6.73212724459888E-05,-6.04028146085219E-13,148.69,-0.001073,0.002076826,0.00216641 +-0.000336,-0.1389886678325410,6.72093649086124E-05,-4.46157973791041E-14,148.64,0.004748,0.001797485,0.000187609 +0.004575,0.2011377615220620,6.69032904564347E-05,5.03460434044149E-13,149.32001,0.00182,0.000440122,0.00145391 +-0.003148,-0.0794936681321443,0.000134363444114,-3.77529882704752E-13,148.85001,-0.005052,-0.007444372,-0.000406148 +0.024992,0.783245573953059,0.0007864586231593,1.63978217185058E-12,152.57001,0.009829,0.006756393,0.000327403 +-0.018156,0.2491958416962020,0.0002002670226969,-9.71252508885013E-13,149.8,0.001949,0.002493057,8.72175E-05 +-0.005607,-0.4026194077470240,6.70649793859958E-05,-5.0493275831009E-13,148.96001,0.0018,0.002632116,0.00438561 +0.007116,-0.072215412901288,0.0001332489001465,6.85823415267126E-13,150.02,0.00368,0.003864501,-0.00260668 +0.009799,-0.2123293253629760,6.60769644151618E-05,1.18734961836114E-12,151.49001,0.006461,0.002911,0.00267395 +-0.003499,0.1082093371407350,6.61764662044453E-05,-3.83920299021214E-13,150.96001,0.004182,-0.000922287,-0.00114618 +0.003577,0.09294211532425,0.000264344262295,3.58343318795817E-13,151.28,0.003733,0.005639393,0.00302708 +-0.005553,-0.1662957126524160,0.0,-6.70987146913926E-13,150.44,0.000888,0.002870229,-0.00170424 +0.002459,0.0315975817015907,0.0002651680923016,2.87321368181919E-13,150.81,-0.003499,-0.003080742,0.00266863 +-0.019163,0.1474431206139760,0.0001351406165495,-1.98950471137566E-12,147.92,-0.008226,-0.006609009,-0.000474167 +-0.000338,-0.3702234578111410,6.76269696354291E-05,-5.5738915928457E-14,147.87,0.000551,-0.004398869,0.00402743 +0.014337,0.5547543229580490,0.0002666177567425,1.49918790068087E-12,149.99001,0.007223,0.0049853,-0.00321578 +6.7E-05,-0.0710627023927675,6.65999999999182E-05,7.54149175400629E-15,150.0,-1.1E-05,-0.000356212,0.00286011 +0.006667,-0.0002708521135472,6.61589403972697E-05,7.4566690848416E-13,151.0,0.003865,0.001517689,-0.00172961 +0.01649,0.4976705930034180,0.0008468955080528,1.21147819329849E-12,153.49001,-0.002602,-0.005842695,0.000672011 +0.028536,0.5531498993999180,0.0001899664280737,1.31236661649957E-12,157.87,0.003385,-0.001672691,-0.00413493 +0.016976,-0.1496753681506200,6.23481781376149E-05,9.02821689348894E-13,160.55,-0.001399,-0.007498233,0.000229853 +0.002927,0.0018544142440461,0.000496832691591,1.54922754982801E-13,161.02,-0.003197,0.000485072,-0.001838 +0.002422,-0.182424873458506,6.19540301096023E-05,1.56418581215531E-13,161.41,0.001657,0.005461956,0.00156221 +0.003284,-0.2777577389027080,0.0003088180807707,2.92691936154008E-13,161.94,0.002294,-0.000263079,-0.000981739 +-0.031678,0.1095928682586670,0.0017218289649893,-2.62773815406066E-12,156.81,-0.022725,-0.025277329,0.00413607 +0.021874,0.152885564578701,6.24063865197644E-05,1.54017166868373E-12,160.24001,0.0132,0.006779543,-0.000565118 +0.031578,0.961120686399733,6.05565638233157E-05,1.09905476120614E-12,165.3,-0.018961,-0.018562834,-0.00439465 +-0.003206,-0.1238899522609610,0.0001213206287552,-1.27771584457539E-13,164.77,-0.011815,-0.013388338,-0.00107226 +-0.00613,-0.1028847792054900,0.0008549096760448,-2.74001758656613E-13,163.75999,0.014194,0.018157348,0.00319231 +-0.011724,-0.1364246743852850,6.18512110726278E-05,-6.14031136298259E-13,161.84,-0.008449,-0.001723767,-0.000299395 +0.021503,-0.0898858280695443,0.0001814662363013,1.21137389066362E-12,165.32001,0.011731,0.018708839,0.000321102 +0.035446,0.1204076723772570,5.84764609462969E-05,1.72124518811494E-12,171.17999,0.020707,0.013977858,-0.00307313 +0.022783,-0.0287767432170866,0.0006854009595613,1.11373995858433E-12,175.08,0.003085,0.000988826,-0.000209632 +-0.00297,-0.0681987070888391,0.0002291475710357,-1.56277997126888E-13,174.56,-0.007181,-1.64E-06,-0.00280276 +0.028013,0.0589727691431372,5.56701030927151E-05,1.35399632793155E-12,179.45,0.009549,0.006049468,0.000698972 +-0.020674,0.3291895429189290,0.0009673380580778,-7.67658878467122E-13,175.74001,-0.009136,-0.008897144,-0.0015413 +-0.008023,-0.0911713748564192,5.73624734698039E-05,-3.30443395861024E-13,174.33,-0.007471,-0.002994858,0.00422288 +0.028509,-0.0598669693905956,5.57724484104345E-05,1.21435257358089E-12,179.3,0.016348,0.010782356,-0.00400445 +-0.039264,0.147532409984485,0.0004064205507035,-1.51700938045762E-12,172.25999,-0.008743,-0.000829145,0.00534449 +-0.006502,0.3037115868754100,0.0001752950800514,-1.93951014233456E-13,171.14,-0.010288,-0.014825465,0.00027753 +-0.008122,-0.4515047382688560,0.0004123711340205,-4.45324859446893E-13,169.75,-0.011388,-0.012251544,0.00152642 +0.019087,-0.1518346657835400,0.0004045898372974,1.21076502965633E-12,172.99001,0.017778,0.016046504,-0.00083905 +0.015319,0.0106318691812796,5.69346390343367E-05,9.47015784438491E-13,175.64,0.01018,0.007359018,-6.29975E-05 +0.003644,-0.2584187334806920,0.000453823462673,3.0266820844866E-13,176.28,0.006224,0.005500603,0.00054818 +0.022975,0.0967690543119774,0.0001109077801808,1.700841440631E-12,180.33,0.013839,0.009786227,-2.61367E-05 +-0.005767,0.0562243094708154,0.0004462602736494,-4.06550070858697E-13,179.28999,-0.00101,0.002639828,-0.000913216 +0.000502,-0.2122743672454620,5.57475749804376E-05,4.4902947779683E-14,179.38,0.001402,0.002484132,0.00269564 +-0.006578,-0.0417190301792896,0.0002804713804712,-6.18071133454511E-13,178.2,-0.00299,-0.002481616,-0.00135697 +-0.003535,0.0721483605926329,0.0001689474478263,-3.10897481791775E-13,177.57001,-0.002626,-0.001642321,0.00303995 +0.025004,0.6344187741863290,5.48870971312494E-05,1.31264814000101E-12,182.00999,0.006374,0.006790571,-0.00426075 +-0.012692,-0.052561507565206,0.0002782971619366,-7.12303411209596E-13,179.7,-0.00063,0.005865505,0.00269419 +-0.0266,-0.0477266750666012,0.0006859707294763,-1.61051059695624E-12,174.92,-0.019393,-0.010666924,0.000570018 +-0.016693,0.0253906850893621,5.80813953487659E-05,-1.0023929358595E-12,172.0,-0.000964,-0.004687014,0.00429281 +0.000988,-0.0947079568984464,0.000348492768775,6.54700711379865E-14,172.17,-0.00405,-0.0001327,-0.00140761 +0.000116,0.2183888698075220,0.0002904349846101,6.30822954161143E-15,172.19,-0.001441,-0.004493006,0.00184137 +0.016784,-0.2875008937856080,5.711674663006E-05,1.25988827349944E-12,175.08,0.00916,0.005077742,-0.00128492 +0.00257,-0.0177617312578229,0.0002278243035379,1.9590161700654E-13,175.53,0.002818,0.001056514,0.00124286 +-0.019028,0.1297239309082270,0.0007550380393751,-1.30878749997336E-12,172.19,-0.014244,-0.004869045,-0.000125928 +0.005111,-0.0479805646438775,0.0001156179513711,3.67385633535339E-13,173.07001,0.00082,-0.005588265,0.00252072 +-0.018894,0.1329142856104960,0.0004122497055358,-1.22187640710294E-12,169.8,-0.018388,-0.015129838,-0.00103598 +-0.021025,0.0407089921687282,6.01576129458636E-05,-1.33456074600617E-12,166.23,-0.00969,-0.009608002,0.00487666 +-0.010347,-0.0361730491502656,0.0002430855414919,-6.88549003551251E-13,164.50999,-0.011037,-0.008942903,-0.00115576 +-0.012765,0.3433623804749990,0.0004925805061263,-6.40512414390784E-13,162.41,-0.018915,-0.012963113,0.00259739 +-0.004864,0.3243294193893680,0.0007424823660438,-1.85191878024423E-13,161.62,0.002772,0.002892976,-0.000772878 +-0.011385,-0.2878051974914050,0.0009388534234573,-6.15651993735085E-13,159.78,-0.012172,-0.00194298,0.00243486 +-0.000563,-0.065515407805994,0.0008766986035442,-3.25974179574236E-14,159.69,-0.001497,-0.00377986,-0.000774955 +-0.002943,0.1261757442546670,0.0006908679814092,-1.51753599234756E-13,159.22,-0.005384,-0.000213901,0.0015906 +0.069778,0.4753386941416010,0.0002936065285034,2.27972255386372E-12,170.33,0.024348,0.016530286,-0.00486115 +0.026126,-0.3577908681702320,0.001830815882824,1.29526710345932E-12,174.78,0.018886,0.011702956,-0.00122352 +-0.000973,-0.2536304399777680,0.0002290246835806,-6.4694588869311E-14,174.61,0.006863,0.00778151,0.00130405 +0.007044,-0.0147870482476832,0.0004550159235669,4.72058464156918E-13,175.84,0.009423,0.006329285,0.000915139 +-0.01672,0.0526133825327899,0.0009254482894996,-1.08259629044778E-12,172.89999,-0.024391,-0.014543299,-0.000574946 +-0.001677,-0.0773884155338239,0.0004640640408375,-1.18039488593062E-13,172.39,0.005157,-0.000610116,0.00270975 +-0.004235,-0.0631335172720106,0.0002912734475125,-3.19530950172109E-13,171.66,-0.003702,3.96E-05,-0.000808987 +0.018467,-0.0315349203990958,5.72556197448612E-05,1.41261902247245E-12,174.83,0.008401,0.010591063,0.000414072 +0.008294,-0.0475724486589829,0.0002836396641707,6.60653435628263E-13,176.28,0.014517,0.008608387,-0.00171463 +-0.023599,0.2744720675971180,0.0004067511038811,-1.51058319850921E-12,172.12,-0.018116,-0.014718964,0.00376209 +-0.020218,0.0866674320879321,0.0004743833017076,-1.21552342981105E-12,168.64,-0.018969,-0.014287983,-0.000600171 +0.001423,-0.1270483125479540,0.0013619729985788,9.78638296565987E-14,168.88,-0.003841,-0.004948081,0.00203073 +0.023152,-0.2543146035955150,0.000347184463637,2.08693932821794E-12,172.78999,0.015767,0.012227792,-0.00260111 +-0.001389,-0.0480084109783814,0.0002898290350622,-1.31702512424955E-13,172.55,0.000881,-0.001559649,0.00211325 +-0.021269,0.1378561580487620,0.0002961274277594,-1.81087412994011E-12,168.88,-0.021173,-0.017811687,3.70534E-05 +-0.009356,0.1919771925170410,0.0013748356246263,-6.74599072993303E-13,167.3,-0.007166,-0.006786295,0.00276892 +-0.017812,0.099525005502187,0.0001216528650406,-1.18923748854156E-12,164.32001,-0.010143,-0.014160268,0.000151941 +-0.025864,-0.0134020682799278,0.0006246641703838,-1.7967674698364E-12,160.07001,-0.018412,-0.013836148,0.00420321 +0.01668,0.5677463116122500,0.0006759247464714,7.2699609299283E-13,162.74001,0.014957,0.002778796,-0.000300044 +0.012965,-0.3484355905626010,0.000303306017391,8.56163203252456E-13,164.85001,0.022373,0.025130213,0.0012407 +0.001638,-0.1078326104860640,0.0001816254844961,1.21043336927741E-13,165.12,-0.002443,-0.004878289,-0.000740677 +-0.011628,0.0158491166554302,0.0001838235294117,-8.55819803482873E-13,163.2,-0.015473,-0.017633711,0.00215578 +0.020588,-0.0430263436229779,0.0001801152737752,1.55146123176542E-12,166.56,0.018643,0.017912697,-0.000976548 +-0.001981,-0.0381647304284662,0.0004210431330084,-1.5551484536841E-13,166.23,-0.005255,-0.002852982,3.87413E-05 +-0.018408,0.0932357006698678,0.0003064288778575,-1.34663304926418E-12,163.17,-0.007934,-0.005322124,0.00199577 +-0.023718,0.149783912358433,0.0004394224733207,-1.54571363463927E-12,159.3,-0.029518,-0.023722344,0.00186967 +-0.011676,0.3609262873056990,0.0006351626016259,-5.65732529436562E-13,157.44,-0.007234,-0.005629282,0.000654686 +0.034997,-0.3027484798094100,0.0004295796256519,2.34973631496921E-12,162.95,0.025698,0.020029313,0.00029901 +-0.027186,0.1532732607661190,0.0003784380519808,-1.62694061976141E-12,158.52,-0.004292,-0.003370151,0.000927407 +-0.023909,-0.081334440140934,0.000452400956505,-1.5956583331215E-12,154.73,-0.012962,-0.006929475,0.0051318 +-0.026562,0.1213938465912770,0.0001327844907713,-1.62395121521729E-12,150.62,-0.007421,3.18E-05,-0.000371435 +0.029677,-0.1449194581312770,0.0013540524856535,2.06074391626143E-12,155.09,0.021408,0.018184769,0.00261782 +0.029015,0.1004285097158170,0.0003133028385236,1.77927424486253E-12,159.59,0.022384,0.015464955,-0.00443764 +0.006454,-0.2606848562663360,6.21964886065728E-05,5.31894781647407E-13,160.62,0.012348,0.012261366,0.00358294 +0.020919,0.6443255160737300,0.0001220270764728,1.02697206839481E-12,163.98,0.011662,0.007951332,-0.00358947 +0.008538,-0.2290563821278140,6.04668037247001E-05,5.39087347896546E-13,165.38,-0.000435,-0.005810439,0.00122011 +0.020801,-0.149192354034951,0.0001184101339646,1.51221967636968E-12,168.82001,0.011304,0.007364708,-0.0022507 +0.008234,0.2024949217863600,0.0004113154097106,4.93738628932825E-13,170.21001,-0.012273,-0.012898411,-0.000513951 +0.022678,-0.0809890218234661,5.75055978912972E-05,1.44687641900706E-12,174.07001,0.014344,0.01017045,-0.00158786 +0.003734,-0.106831627634817,5.72344322343802E-05,2.6573514642896E-13,174.72,0.005066,0.004416767,0.000241382 +0.005037,0.1226262380266730,5.70045525623494E-05,3.17709010610669E-13,175.60001,0.007145,0.002715117,0.000546669 +0.019134,0.1145565343102700,5.58225270549981E-05,1.06250208138014E-12,178.96001,0.012257,0.009677933,-0.000417863 +-0.00665,-0.0901742467685396,0.0007312257411261,-4.08587393114403E-13,177.77,-0.006294,-0.001852509,-0.000927584 +-0.017776,0.1243363452072380,5.72132180288423E-05,-9.88986740409917E-13,174.61,-0.015653,-0.015625196,0.00247944 +-0.001718,-0.2355956272580410,0.0004015260168664,-1.252573540962E-13,174.31,0.00341,0.004034735,-0.000273582 +0.023693,-0.0279191624718939,5.59852051108929E-05,1.73591251722657E-12,178.44,0.008091,0.002975719,-0.000299449 +-0.018942,-0.0414239765676661,0.0002285502113562,-1.47574846825943E-12,175.06,-0.012552,-0.008037919,-0.0010011 +-0.018451,0.2136301792233450,0.0002910434732003,-1.20672409434449E-12,171.83,-0.009717,-0.004176185,0.00403017 +0.001804,-0.1280610164902630,0.0009294760079006,1.35069006404889E-13,172.14,0.004253,0.002523693,-0.00149466 +-0.011909,-0.0139549653294671,0.0002351108236815,-9.15167806324935E-13,170.09,-0.002651,0.003977345,0.00259114 +-0.025516,-0.0565458940828862,6.02714932125957E-05,-2.13276250765624E-12,165.75,-0.016877,-0.011896015,0.0006729 +0.011523,0.097704685208483,0.0001192890373375,8.67429171620342E-13,167.66,-0.003418,-0.002556796,0.00112804 +0.016343,-0.1096436646151200,0.0001173708989066,1.35955344842749E-12,170.39999,0.011175,0.01005923,-0.00326446 +-0.029988,0.0680514196976538,6.04392316799567E-05,-2.40792445328197E-12,165.28999,-0.012144,-0.003279639,0.00397196 +-0.001331,-0.0845351702794086,0.0001211607123547,-1.16898818564932E-13,165.07001,-0.000205,-0.001147682,0.000540257 +0.014115,-0.0193239913583044,5.9677422919725E-05,1.24652257480666E-12,167.39999,0.016058,0.014515643,0.000699166 +-0.001016,0.0031303875836721,5.98576810382258E-05,-8.95358219637293E-14,167.23,-0.000619,0.007149277,-0.00119436 +-0.004844,0.2843288004263080,0.0001202379521691,-3.33994797490479E-13,166.42,-0.014753,-0.010466982,0.00112682 +-0.027821,-0.0281764765139018,0.0003089807966488,-2.03036802857786E-12,161.78999,-0.02774,-0.028205961,0.000699118 +0.006737,0.1326997735237530,0.0002455181728879,4.31159193683432E-13,162.88,0.005698,0.007040895,0.00165763 +-0.037328,-0.0041110697783682,0.0003826530612245,-2.49181974296116E-12,156.8,-0.028146,-0.023767814,0.000105878 +-0.001467,-0.0791399072969529,0.0007664941708824,-1.06501528686334E-13,156.57001,0.002098,0.001857692,0.00453115 +0.045155,0.477254897057503,0.0003667807382058,2.12322121253808E-12,163.64,0.024747,0.018451211,-0.00527083 +-0.036605,0.011925855752334,6.3431656418062E-05,-1.76553625275463E-12,157.64999,-0.036285,-0.027691027,0.0031067 +0.001966,-0.0626285948395579,0.0005065206060699,1.0096127717096E-13,157.96001,0.005675,0.002555979,0.000912226 +0.009623,-0.2786843375596010,6.27664910962033E-05,6.7857424355842E-13,159.48,0.004837,0.002035269,1.39509E-05 +0.041008,0.2156932828927510,0.0001806408866401,2.28495301747322E-12,166.02,0.029862,0.028140767,-0.00169009 +-0.055716,0.2056686331894800,6.37877144861319E-05,-2.72683025709698E-12,156.77,-0.03565,-0.031211298,0.00298135 +0.00472,-0.1093148027761190,0.0001270981688708,2.58514791035193E-13,157.28,-0.005674,-0.002987992,0.00302022 +-0.033189,0.1325748812074960,6.56977508879137E-05,-1.66008052179176E-12,152.06,-0.032037,-0.019868826,-0.00230232 +0.016112,-0.1232360489193430,0.0001295061892115,9.04607484391676E-13,154.50999,0.002458,-0.002634738,0.0032554 +-0.051841,0.2409326799286970,0.0002047781569965,-2.47374432934798E-12,146.5,-0.016463,-0.010156198,0.000940316 +-0.026894,0.2742039967390460,0.0002805836139168,-1.03499396356491E-12,142.56,-0.001296,-0.003260923,0.00865439 +0.031916,-0.3751476680666220,6.79083678880848E-05,1.90488590799497E-12,147.11,0.02387,0.014697603,-0.00395195 +-0.010672,-0.2397260648031710,0.000137487985261,-8.46829702087544E-13,145.53999,-0.003946,0.000831135,0.00298762 +0.025423,-0.0963492510462907,0.0002010184802319,2.17707565591422E-12,149.24001,0.02017,0.013380638,-0.000656492 +-0.056419,0.4012704708021220,7.09416225720773E-05,-3.65402098192592E-12,140.82001,-0.040395,-0.035661741,0.00324669 +-0.024641,0.2403075247491940,0.0002184200787462,-1.31919889314494E-12,137.35001,-0.005834,-0.007524259,0.00561797 +0.001747,0.0096473828744509,0.0002907188022384,9.24734275931206E-14,137.59,0.000146,0.000280597,-0.00191737 +0.040119,-0.1431445585331240,6.98064425967169E-05,2.38277743999946E-12,143.11,0.018555,0.019779343,-7.42725E-05 +-0.019216,-0.1154682514065400,0.0007125249358791,-1.31555668794897E-12,140.36,-0.008121,0.00151752,-0.00227873 +0.00114,-0.1118940362319830,7.12354113295083E-05,8.77792488294609E-14,140.52,0.009451,0.00600277,0.00505397 +0.0232,-0.0209223808242573,0.0001391014049242,1.78318964015321E-12,143.78,0.019883,0.016092953,-0.0036419 +0.040757,0.0087636946715872,6.67602245390013E-05,2.98382324537981E-12,149.64,0.024742,0.017641577,0.000549881 +-0.005346,0.1352900360135430,0.0005375571083043,-3.46594007747266E-13,148.84,-0.006274,-0.006709424,-0.00234887 +-0.000873,-0.2838178818806080,6.7312213885417E-05,-7.90974212089459E-14,148.71001,-0.007483,-0.005361927,0.00254178 +0.016811,-0.0261012825090783,0.0001983995636267,1.53811035437689E-12,151.21001,0.018431,0.013258395,-0.00262609 +-0.038556,0.2241137138432050,0.0002063557573254,-2.99736777207368E-12,145.38,-0.016347,-0.010484212,0.00455544 +0.005228,-0.0745259856302703,6.84275352401184E-05,4.36872766917954E-13,146.14,0.003137,0.00048882,0.000525039 +0.017586,-0.1724590770612950,0.0001344226928638,1.74512236318832E-12,148.71001,0.009523,0.008031387,-0.00125408 +-0.005043,-0.2042625273624890,6.75182436118227E-05,-6.32082583473379E-13,147.96001,-0.010794,-0.008114558,-0.00061665 +-0.035956,0.2872148069429000,7.00364554123398E-05,-3.63168541960973E-12,142.64,-0.023799,-0.019388999,0.00279468 +-0.038629,0.318529267642323,7.29235032450296E-05,-3.07800553221844E-12,137.13,-0.02911,-0.027267553,0.00359026 +-0.038285,0.3343594655666790,7.58265089474591E-05,-2.37719757586637E-12,131.88,-0.038768,-0.027906053,0.00166412 +0.006673,-0.3063123353372970,0.0001505724729265,5.93342569148636E-13,132.75999,-0.003774,-0.004977929,0.000513624 +0.020111,0.0794058839623259,0.0002215166670247,1.6239985323226E-12,135.42999,0.014593,0.010001677,-0.000838396 +-0.039651,0.2098001077479080,7.68107027526999E-05,-2.75590085157163E-12,130.06,-0.032512,-0.024176542,0.00212745 +0.011533,0.2148721404658240,7.59349346307096E-05,6.52290492178443E-13,131.56,0.002201,-0.001279478,0.00136337 +0.032761,-0.3977574732821730,7.35997644806867E-05,2.97909790356029E-12,135.87,0.024477,0.021461924,-0.00274334 +-0.003827,-0.087282793019724,0.0001478389251687,-3.82749941898352E-13,135.35001,-0.001302,-0.001543359,0.001582 +0.021574,-0.0204644651668587,7.22499457582102E-05,2.15624189191557E-12,138.27,0.009532,0.006371672,-0.00110099 +0.024517,0.2349589099736330,0.0002824368205564,1.93669998667479E-12,141.66,0.030563,0.026838044,0.000446051 +0.0,-0.1799980081241680,7.05209656924166E-05,0.0,141.66,-0.002973,-0.001981542,-0.000973922 +-0.02979,-0.0822883038661702,7.27590221186766E-05,-3.22313460228247E-12,137.44,-0.020143,-0.015626486,0.00265282 +0.013024,-0.015720543602168,0.0002153989801048,1.41323449549625E-12,139.23,-0.000712,0.002660043,-0.000564576 +-0.018028,0.4941137323482710,0.0004389994148625,-1.3333203494576E-12,136.72,-0.008759,-0.008181969,-0.000234808 +0.016164,-0.2821940360366180,7.20506781868629E-05,1.63894652092866E-12,138.92999,0.010554,0.010457371,0.00136033 +0.01893,0.033594634309054,7.07120655551998E-05,1.82251771876756E-12,141.56,0.001584,-0.004162407,-0.00322534 +0.009607,0.0085031291064812,7.00391827597432E-05,9.0840440686245E-13,142.92,0.003573,0.00225587,0.000502492 +0.023999,-0.1059959732284630,6.83976721285778E-05,2.47882212349018E-12,146.35001,0.014965,0.011175806,-0.0023714 +0.004715,-0.0250768530652834,6.7940701029616E-05,4.97188214203051E-13,147.03999,-0.00083,-0.001478447,0.00018247 +-0.014758,-0.0189126412388699,6.90964312831786E-05,-1.60996323492896E-12,144.87,-0.011527,-0.005243148,0.000190612 +0.006834,0.2251777854732700,0.0001371177841764,6.0437510132467E-13,145.86,-0.009244,-0.006175363,-0.000710496 +-0.002537,-0.0783806249917847,0.000206337191124,-2.44063871605136E-13,145.49001,-0.004457,-0.006731183,-0.000406293 +0.020482,0.0928712201317096,6.73536741428632E-05,1.76677345966039E-12,148.47,-0.002999,-0.004634586,-0.00152994 +0.01145,-0.0219866378481975,0.0007325031630819,9.98446343698353E-13,150.17,0.019201,0.021485021,-0.000991296 +-0.020643,0.0653436000199356,0.0002719793110777,-1.72528725618073E-12,147.07001,-0.008364,-0.006892374,0.00256562 +0.026722,0.0185485401386238,6.62251655628537E-05,2.13561521121094E-12,151.0,0.027628,0.02427995,-0.00010121 +0.01351,-0.2185930579711760,6.52770560164551E-05,1.36333991015019E-12,153.03999,0.005896,0.001501523,-0.00134631 +0.015094,0.0043377420344088,6.43707715241918E-05,1.4940564429761E-12,155.35001,0.009861,0.005084278,7.11699E-05 +-0.008111,0.0305588914427488,0.0001297942760724,-7.85418408904036E-13,154.09,-0.009332,-0.004295401,-0.00108794 +-0.007398,-0.2006238426534340,6.53808434128206E-05,-9.02848300794369E-13,152.95,0.001315,0.002844891,0.00216834 +-0.008826,0.0279882191766247,6.59630563348308E-05,-1.05712536825122E-12,151.60001,-0.011543,-0.007142848,-0.00127639 +0.034235,0.4266699474071940,0.0001275591636941,2.77901114522476E-12,156.78999,0.026156,0.013728893,0.00123213 +0.003572,0.0349252217395457,0.0005084206858328,2.79173372500953E-13,157.35001,0.012133,0.010312605,-0.00169852 +0.032793,0.2508884000164150,6.14731438972838E-05,1.98386373192686E-12,162.50999,0.014208,0.00969879,0.000300099 +-0.006153,-0.3341004463860420,6.18537590152544E-05,-5.62457294576849E-13,161.50999,-0.002823,-0.001422752,-0.00276676 +-0.009287,-0.1158835471261380,6.25585939979279E-05,-9.69216733467587E-13,160.00999,-0.006662,-0.012263663,0.00404634 +0.038248,0.3765187417035840,6.01938241135912E-05,2.7930010111131E-12,166.13,0.015638,0.012851213,-0.00509587 +-0.001926,-0.3275960732692540,6.03703033592309E-05,-2.09568376898975E-13,165.81,-0.000777,-0.00261119,0.00125696 +-0.001387,0.0218909801415383,6.0538248531065E-05,-1.48097543891644E-13,165.35001,-0.001626,0.002342068,-0.000873721 +-0.002903,0.0646231009142137,6.06538484866313E-05,-2.92001533914696E-13,164.87,-0.001238,0.000886196,0.000833371 +0.000303,0.0454301222827506,6.05748241572651E-05,2.91443267904928E-14,164.92,-0.004249,-0.001770466,-0.000912243 +0.026195,0.1123842825488280,5.91467703176247E-05,2.20721806594006E-12,169.24001,0.021291,0.01632681,-0.000352756 +-0.004432,-0.1857102551310310,0.0002373434484334,-4.60655766466437E-13,168.49001,-0.000705,0.000815387,-0.000536635 +0.021426,0.1904608944608410,0.0001161533924373,1.83145388383091E-12,172.10001,0.017322,0.012730092,0.000691931 +0.006334,-0.2054801402373040,5.77977943298925E-05,6.77152166184945E-13,173.19,0.003969,0.00448418,-0.00255119 +-0.000924,0.0425435572242458,5.77934462231457E-05,-9.48390903901329E-14,173.03,0.001876,0.007064378,0.00181359 +0.008785,0.411102272478838,0.0001145803494699,6.3343234782841E-13,174.55,-0.007238,-0.005027271,-0.00333416 +-0.002292,-0.2169611280114360,0.0001147861105246,-2.1153691316748E-13,174.14999,0.00227,0.00055087,0.00185087 +-0.015102,0.1296818973037290,5.83605410449073E-05,-1.2527330397767E-12,171.52,-0.0129,-0.008597325,-0.00077233 +-0.023029,-0.0211608462488881,5.96765495209489E-05,-1.99758967741066E-12,167.57001,-0.0214,-0.019080129,0.00261843 +-0.002029,-0.2141914365316460,0.0001793936494648,-2.24428807006087E-13,167.23,-0.002238,-0.004658279,-0.000246619 +0.001794,-0.0032945908323729,0.0001790724049424,1.98734734354199E-13,167.53,0.002916,0.001812257,0.000684787 +0.014923,-0.0507124495583382,0.0001176263012408,1.71583976027473E-12,170.03,0.014092,0.009783388,-0.00046777 +-0.037699,0.5419597533325270,6.11783400561917E-05,-2.92123534553289E-12,163.62,-0.033688,-0.030289183,0.00209045 +-0.01369,-0.0719842550405315,6.1965547155725E-05,-1.15896813934959E-12,161.38,-0.006666,-0.005712228,0.0023775 +-0.015305,0.0637433723570086,6.2928701780825E-05,-1.2369809152806E-12,158.91,-0.011028,-0.00959909,0.000378583 +-0.010635,0.128667408228968,6.35415341560625E-05,-7.69740984191066E-13,157.22,-0.007817,-0.008821384,0.00201615 +0.004707,-0.1560175408010180,0.0001899214870903,4.01770951576333E-13,157.96001,0.002996,0.004633077,-0.000304253 +-0.013611,0.037617416015234,6.41165522111299E-05,-1.13511259278168E-12,155.81,-0.010736,-0.010676522,0.00104108 +-0.008215,-0.0410429521536148,6.46476412346323E-05,-7.20343834106068E-13,154.53,-0.004095,-0.00552833,0.00148733 +0.009254,0.183639092026796,6.41190007617395E-05,6.7926935280126E-13,155.96001,0.018341,0.013998212,0.000764791 +-0.009618,-0.0286604556091985,6.4741676502487E-05,-7.33877248755501E-13,154.46001,0.006611,0.006118822,0.00211351 +0.01884,-0.1989357670797600,6.36080574442021E-05,1.761352671835E-12,157.37,0.015271,0.011870877,-8.92821E-05 +0.038508,0.5407035243601400,6.12494683504692E-05,2.25002582010745E-12,163.42999,0.010584,0.007142043,-0.00326582 +-0.05868,0.1698967823874030,6.50676027040697E-05,-3.11344773935202E-12,153.84,-0.043237,-0.039416811,0.00277997 +0.009555,-0.2834393701406460,6.44517416778963E-05,7.00808039133111E-13,155.31,0.003387,0.000968306,0.00260166 +-0.01893,0.0293840908972338,6.55640874188892E-05,-1.3748062501198E-12,152.37,-0.011318,-0.005565089,-0.0023109 +-0.01096,0.8226420155465020,0.0001327803583277,-4.41556493505811E-13,150.7,-0.007182,-0.004502332,0.00438962 +0.025083,-0.5058150095239960,6.4668565510019E-05,1.99483344383959E-12,154.48,0.006857,0.006399879,-0.00483537 +0.015665,0.3213411069948880,0.0001274697340644,9.28307716379777E-13,156.89999,-0.011272,-0.01010485,-0.000480642 +-0.020268,-0.0555545023110607,6.51183970857566E-05,-1.29804006162558E-12,153.72,-0.017116,-0.0170145,-0.00187511 +-0.006375,-0.1475743635021660,0.0001310069313208,-4.82034861715814E-13,152.74001,-0.008428,-0.00354825,0.00284573 +-0.015124,0.1082210178662440,0.0001330186886272,-1.04774822456975E-12,150.42999,-0.017233,-0.01616766,-0.00167746 +0.00226,-0.0280831455429048,0.0003979571532798,1.60727090213247E-13,150.77,-0.010341,-0.011138731,0.00139525 +0.006566,-0.0954883468802143,6.58276268994729E-05,5.12890908436438E-13,151.75999,-0.00212,-0.00429996,-0.00236041 +-0.012652,0.7393834005004500,6.68045915644855E-05,-5.75463137724469E-13,149.84,0.019672,0.018834741,0.00464331 +-0.049119,-0.1279800418607700,7.02554744525132E-05,-2.69435784927714E-12,142.48,-0.021126,-0.015433731,0.00256567 +-0.030039,-0.0248738231859343,7.2358900144652E-05,-1.74211282714818E-12,138.2,-0.015067,-0.017111691,0.00565541 +0.030753,-0.0847687649708068,7.02000702000064E-05,1.89057126174813E-12,142.45,0.025884,0.02664464,-0.00271424 +0.025623,-0.2278634097242740,6.84462649933488E-05,1.98908624794426E-12,146.10001,0.030584,0.02798931,0.000532756 +0.002053,-0.1003675910889180,6.83060155946111E-05,1.76789592124935E-13,146.39999,-0.002018,-0.001400275,-0.00108132 +-0.006626,-0.1384182934491970,6.86928466404194E-05,-6.66668260985802E-13,145.42999,-0.010245,-0.011459708,0.00115964 +-0.036719,0.2561720355882480,0.0002854593475622,-3.05314134968344E-12,140.09,-0.028004,-0.021056292,0.000775812 +0.002356,-0.1286724990258510,0.0003559322033898,2.2429939236973E-13,140.42,-0.007492,-0.003205409,0.00116509 +-0.010255,0.0282940640921725,0.0002158583968916,-9.59285341468851E-13,138.98,-0.006519,0.001243322,-0.00153429 +-0.004605,-0.0846843459655269,7.23579586527577E-05,-4.7279777509228E-13,138.34,-0.003291,-0.000969242,0.00275882 +0.033613,0.6058000374857210,0.0002098048667875,2.07923547461026E-12,142.99001,0.025966,0.028341219,-0.00369663 +-0.03224,-0.2167667977661840,0.0009393698511345,-2.63107188981475E-12,138.38,-0.023663,-0.013445667,0.00229848 +0.029123,-0.0384723393891188,7.02900077241351E-05,2.40184429191427E-12,142.41,0.02648,0.018592657,0.00036312 +0.009409,0.1627100965409420,6.96347826088522E-05,6.61170391772698E-13,143.75,0.011428,0.011196663,-0.00139678 +0.000765,-0.3763836196237060,6.95815376059647E-05,8.61353944365966E-14,143.86,-0.006672,-0.003275812,0.000393414 +-0.003267,0.0441383501929508,6.96701304136701E-05,-3.53453665655632E-13,143.39,-0.007951,-0.002965464,-0.00148701 +0.027059,0.3415990044229770,0.0004753853466423,2.12459888322542E-12,147.27,0.023725,0.024691133,0.000150374 +0.014803,-0.1223845211433300,6.6978922716588E-05,1.30505567145349E-12,149.45,0.011882,0.013417768,-0.00286046 +0.019338,-0.0164625150681126,6.56426414598326E-05,1.70052063654661E-12,152.34,0.016267,0.010702386,0.000962163 +-0.019627,0.1829375459676690,6.70237651810167E-05,-1.48823376001927E-12,149.35001,-0.007388,7.44E-05,-0.000276157 +-0.030465,0.234728501675892,0.0002071823204419,-1.92967261252314E-12,144.8,-0.006083,0.006098472,0.00348934 +0.075553,0.5089439678882510,6.42737855225674E-05,2.94869202062419E-12,155.74001,0.024626,0.025864398,-0.00596337 +-0.01541,-0.4055836713361980,6.527977044491E-05,-1.02762425872098E-12,153.34,-0.007454,-0.003921013,-0.00173902 +-0.017543,-0.1798281369415390,6.64454076631142E-05,-1.45183431864487E-12,150.64999,-0.004101,-0.002436383,0.00458703 +-0.037305,0.1654817682654660,6.88823002136643E-05,-2.75160452550512E-12,145.03,-0.025002,-0.015479018,-0.00084459 +-0.042405,0.0465414755457591,7.20046082948654E-05,-3.12102848819435E-12,138.88,-0.010586,-0.004557386,0.00689593 +-0.001944,0.4375830673953490,7.21925133691007E-05,-9.9887319450154E-14,138.38,0.013619,0.012561094,-0.00073564 +0.003902,-0.4079754322922320,7.19838756117975E-05,3.3734182135332E-13,138.92,0.009614,0.013078308,0.00229131 +0.004175,0.0850720598169791,7.16129032257185E-05,3.31261822201589E-13,139.5,0.005598,0.010169316,-0.0023054 +-0.03319,-0.171273728682979,0.0002224364202563,-3.28677445252728E-12,134.87,-0.020778,-0.019507615,0.00336681 +0.088975,0.5870915174249490,0.0002723496970109,5.09813039297238E-12,146.87,0.055434,0.036951279,-0.00150393 +0.019269,-0.2105343259450170,0.0004676018704074,1.37208230024652E-12,149.7,0.009241,0.000963604,-0.00421352 +-0.009486,-0.2187586000025900,0.0002022524952791,-8.72887107360453E-13,148.28,-0.008936,-0.006256994,0.00318905 +0.011869,0.2245021221900470,6.67155469684721E-05,8.81465049854383E-13,150.03999,0.008713,0.001676452,-0.0017315 +-0.008331,-0.2849475527385920,0.0001343504358053,-8.72536325113252E-13,148.78999,-0.008252,-0.00116375,0.000547857 +0.012971,0.2521684117236340,0.0001989782377919,1.07102578518199E-12,150.72,-0.003089,-0.000223754,-0.00220167 +0.003782,-0.0693048290780361,0.0004626875842875,3.34272941193301E-13,151.28999,0.004759,0.005943158,-8.4842E-05 +-0.02168,-0.2155224033554450,0.0001351935771363,-2.49676458495222E-12,148.00999,-0.003884,-0.001345658,0.00200822 +0.014661,-0.1177434901420170,0.0002662804811745,1.88610557185672E-12,150.17999,0.01358,0.011804659,-0.00069864 +0.005926,0.1257367661845120,0.0001985834249959,6.73226208090891E-13,151.07001,0.005915,0.002814146,-0.000184368 +-0.019594,-0.3964870006436920,0.0002025521571804,-3.76209465171448E-12,148.11,-0.000283,0.004473662,0.001539 +-0.026264,0.9713737309813380,0.0002080155318263,-2.62698388978444E-12,144.22,-0.015444,-0.01448656,0.00240347 +-0.021148,0.2062267008576750,7.09074165898851E-05,-1.79151306725264E-12,141.17,-0.001592,9.07E-05,0.00223799 +0.048594,0.3352504927297170,0.000202661622644,2.94010781545896E-12,148.03,0.030948,0.021777937,-0.00116991 +0.001892,-0.3625082016521410,0.0001349200997908,1.79228240689993E-13,148.31,-0.000868,-0.005630503,-0.00226667 +-0.003371,-0.080292928618845,6.7654421216365E-05,-3.48386369028237E-13,147.81,-0.001195,0.001013728,0.0024794 +-0.007983,0.050396592379047,0.0001363295369297,-7.91764835213191E-13,146.63,-0.017894,-0.014022046,-0.00295324 +-0.02537,-0.0606047173650663,0.0002099223287383,-2.74828892525751E-12,142.91,-0.014399,-0.010332597,0.00358532 +-0.013785,0.0775716497667726,7.10231304100616E-05,-1.40517652631667E-12,140.94,-0.001862,4.71E-05,0.000133231 +0.012133,-0.1081141666032970,7.01016523028912E-05,1.37007887255931E-12,142.64999,0.007522,0.005463391,0.00120686 +-0.003435,0.2244425980062270,7.03432751828285E-05,-3.17877664612002E-13,142.16,-0.00735,-0.009029194,-0.00199891 +0.01639,-0.0749133716841899,6.91397280683123E-05,1.61313017837701E-12,144.49001,0.014279,0.015789546,0.00090539 +0.006782,0.3338288998867630,6.88114387847838E-05,4.97064225290368E-13,145.47,0.00729,0.003046653,-0.00184468 +-0.015536,-0.1213508362883680,0.0002094825634046,-1.31637158193879E-12,143.21001,-0.006053,-0.004171643,0.00257966 +-0.046854,0.1994882164919660,7.33333333334982E-05,-3.47240758753323E-12,136.5,-0.024922,-0.022496759,0.00239248 +-0.014579,0.6189033483088580,0.0002974500258309,-6.77281088239478E-13,134.50999,-0.011138,-0.008486114,0.0034229 +-0.01591,-0.5031474673786270,0.0001510160912594,-1.51164167374613E-12,132.37,-0.009007,-0.004948955,-0.00143543 +-0.000529,-0.0237751913925865,7.56613756615457E-05,-5.15126904555107E-14,132.3,0.001037,0.002814595,0.00271792 +0.023809,0.106232400638061,0.0002214839424141,2.04707698962825E-12,135.45,0.014868,0.016034898,-0.00355262 +-0.023773,-0.0926275315040648,0.0002268017847689,-2.30749317732531E-12,132.23,-0.014452,-0.010456231,0.00239828 +-0.002798,-0.181475908978366,7.57621720007292E-05,-3.32728196284929E-13,131.86,0.005868,0.005342259,0.000677467 +-0.013878,0.0810931197539719,0.0002308697992771,-1.54801506960429E-12,130.03,-0.00405,0.001133267,0.00128592 +-0.030685,0.2382986903736960,7.93398920976746E-05,-2.85157095844114E-12,126.04,-0.012021,-0.011005731,0.00291121 +0.028324,-0.1153370864684370,0.0002314636216341,2.89337486019816E-12,129.61,0.017461,0.010496802,0.0 diff --git a/strategic/bandit.hxx b/strategic/bandit.hxx new file mode 100644 index 00000000..bf2dc972 --- /dev/null +++ b/strategic/bandit.hxx @@ -0,0 +1,18 @@ +#ifndef BANDIT_HXX +#define BANDIT_HXX + +#include +#include +#include +using namespace std; + +/** + * Class for any bandit +*/ +class Bandit{ + public: + virtual int select_arm(double* context) = 0; + virtual void update(double reward, double regret, int choice) = 0; +}; + +#endif \ No newline at end of file diff --git a/strategic/bandit_state.cxx b/strategic/bandit_state.cxx new file mode 100644 index 00000000..80eadc29 --- /dev/null +++ b/strategic/bandit_state.cxx @@ -0,0 +1,21 @@ +#include +#include +#include "strategic/state.hxx" + +class BanditState: public State { + private: + int choice; + + public: + BanditState(int choice) { + this->choice = choice; + } + + void update(int new_choice) { + this->choice = new_choice; + } + + int get_choice() { + return this->choice; + } +}; \ No newline at end of file diff --git a/strategic/bandit_strategy.cxx b/strategic/bandit_strategy.cxx new file mode 100644 index 00000000..91684881 --- /dev/null +++ b/strategic/bandit_strategy.cxx @@ -0,0 +1,192 @@ +#include +#include +#include +#include "common/log.hxx" +#include "common/arguments.hxx" +#include "linucb.cxx" + +#include "bandit_strategy.hxx" +#include "portfolio.hxx" + +string pr_suffix = "_PRC"; +string rt_suffix = "_predicted_RET"; + +BanditStrategy::BanditStrategy(const vector &arguments) { + n_arms = 3; + //get_argument(arguments, "--n_arms", false, n_arms); + + dimension = 7; + get_argument(arguments, "--dimension", false, dimension); + + alpha = 1.0; + get_argument(arguments, "--alpha", false, alpha); + + type = "linucb"; + get_argument(arguments, "--type", false, type); + + buy_threshold = 0; + get_argument(arguments, "--buy_threshold", false, buy_threshold); + + sell_threshold = 0; + get_argument(arguments, "--sell_threshold", false, sell_threshold); + + money_pool = 100.0; + get_argument(arguments, "--money_pool", false, money_pool); + + get_argument_vector(arguments, "--stocks", true, stocks); + + if (type == "linucb") { + Log::info("Selected type LinUCB\n"); + bandit = new LinUCB(n_arms, dimension, alpha); + } else { + cout << "Not supported" << endl; + } + + for (string stock : stocks) { + purchased_shares[stock] = 0; + bought_price[stock] = 0; + } + } + +void BanditStrategy::make_move(const map &context, const map &forecast){ + + double current_money = money_pool; + for (string stock : stocks) { + current_money += purchased_shares[stock] * context.at(stock + pr_suffix); + } + Log::info("current money: %lf\n", current_money); + + vector stocks_to_buy; + vector stocks_to_sell; + + bool missing_stock = false; + for (string stock : stocks) { + + if (context.find(stock + pr_suffix) == context.end()) { + //if (!context.contains(stock + pr_suffix)) { + Log::fatal("ERROR, user specified stock '%s' was being traded but '%s_PRC' was not found in context parameters.\n", stock.c_str(), stock.c_str()); + missing_stock = true; + } + + if (context.find(stock + rt_suffix) == context.end()) { + //if (!forecast.contains(stock + rt_suffix)) { + Log::fatal("ERROR, user specified stock '%s' was being traded but '%s_RET' was not found in forecast parameters.\n", stock.c_str(), stock.c_str()); + missing_stock = true; + } + } + + if (missing_stock) exit(1); + + // Getting context values + int n = context.size(); + double contextValues[n]; + int i = 0; + for (const auto it: context) { + contextValues[i] = it.second; + ++i; + } + + /** + * If arm = 0 BUY, arm = 1 SELL, arm = 2 HOLDOFF + */ + + int choice; + + //Buy first, then sell + if (buy_flag) { + choice = ((LinUCB*)bandit)->select_arm(contextValues, buy_step); + buy_flag = false; + } else { + choice = ((LinUCB*)bandit)->select_arm(contextValues, sell_step); + buy_flag = true; + } + + //int arm = bandit->select_arm(contextValues); + Log::info("Selected Arm is: %d ", choice); + + if (choice == 0) { + std::cout<<"Hence BUY"<last_choice = choice; + + + // Populate respective buy/sell vectors + for (string stock : stocks) { + double forecasted_return = forecast.at(stock + rt_suffix); + + if (choice == 0 && money_pool > 0){ + + stocks_to_buy.push_back(stock); + + } else if (choice == 1 && purchased_shares[stock] > 0) { + + stocks_to_sell.push_back(stock); + + }else { + Log::debug("Actual choice: 2 HOLDOFF\n"); + this->last_choice = 2; + Log::info("\tholding %s because purchased shares (%lf) == 0 or forecasted_return (%lf) >= sell_threshold (%lf) or price (%lf) <= bought price (%lf)\n", stock.c_str(), purchased_shares[stock], forecasted_return, sell_threshold, context.at(stock + pr_suffix), bought_price[stock]); + } + } + + /** + * Update stock states based on decision (Single company) + */ + if (choice == 1) { + + Log::info("selling %d stocks.\n", stocks_to_sell.size()); + //first sell of stocks to sell + for (string stock : stocks_to_sell) { + if (purchased_shares[stock] > 0) { + double stock_price = context.at(stock + pr_suffix); + double gain = purchased_shares[stock] * stock_price; + money_pool += gain; + + Log::info("\tsold %lf shares of %s for %lf$\n", purchased_shares[stock], stock.c_str(), gain); + + purchased_shares[stock] = 0; + bought_price[stock] = 0; + } + } + } else if (choice == 0) { + + Log::debug("Money pool: %5.5f\n", money_pool); + //if we have any money, use the money pool to buy stocks giving each an + //equal amount of money + if (money_pool > 0 && stocks_to_buy.size() > 0) { + Log::info("buying %d stocks.\n", stocks_to_buy.size()); + double money_per_stock = money_pool / stocks_to_buy.size(); + + for (string stock : stocks_to_buy) { + double stock_price = context.at(stock + pr_suffix); + double shares = money_per_stock / stock_price; + purchased_shares[stock] = shares; + bought_price[stock] = stock_price; + + Log::info("\tbought %lf shares of %s for %lf\n", shares, stock.c_str(), money_per_stock); + } + + //we've spent all our money + money_pool = 0; + } + } + } + +State* BanditStrategy::get_state(){ + //State *state = new BanditState(this->last_choice); + Portfolio *portfolio = new Portfolio(money_pool); + + for (string stock : stocks) { + portfolio->add_stock(stock, purchased_shares[stock]); + } + return portfolio; + } + +void BanditStrategy::report_reward(double reward) { + //std::cout<<"Update Reward: "<last_choice<bandit->update(reward, -1*reward, this->last_choice); + } \ No newline at end of file diff --git a/strategic/bandit_strategy.hxx b/strategic/bandit_strategy.hxx new file mode 100644 index 00000000..375a691a --- /dev/null +++ b/strategic/bandit_strategy.hxx @@ -0,0 +1,64 @@ +#ifndef BANDIT_STRATEGY_HXX +#define BANDIT_STRATEGY_HXX + +#include +#include +#include +#include "strategy.hxx" +#include "bandit.hxx" + +/** + * Bandit Stratefy to handle stock buy/sell + * for single company + * TODO: update for handlin multiple companies +*/ +class BanditStrategy: public Strategy { + + private: + int n_arms; + int dimension; + double alpha = 1.0; + string type; + Bandit *bandit; + int last_choice; + + //flag to check buy or sell cycle + bool buy_flag = true; + //bool holdoff_flag = false; + + double buy_threshold; + + vector buy_step{0, 2}; + vector sell_step{1, 2}; + + //sell the stock of the predicted return is less than this threshold + //but above the buying price. + double sell_threshold; + + //how much money we have to buy stocks with initially. + double money_pool; + + //This is used to determine which parameters need to be pulled from the + //context and forecast. For example, if a stock name is AAPL then the + //strategy will look for APPL_PRC (for price) from the context and + //APPL_RET (for returns) in the forecast. + vector stocks; + + //for each stock, track what price it was bought at the last + //time it was bought. + map bought_price; + + //fore each stock, track how many shares were purchased. + map purchased_shares; + + public: + BanditStrategy(const vector &arguments) ; + void make_move(const map &context, const map &forecast); + + State* get_state(); + + void report_reward(double reward); + +}; + +#endif \ No newline at end of file diff --git a/strategic/evaluate_bandit_strategy.cxx b/strategic/evaluate_bandit_strategy.cxx new file mode 100644 index 00000000..1c0f0318 --- /dev/null +++ b/strategic/evaluate_bandit_strategy.cxx @@ -0,0 +1,98 @@ +#include +using std::map; + +#include +using std::string; + +#include +using std::vector; + +#include "common/arguments.hxx" +#include "common/log.hxx" +#include "rnn/rnn_genome.hxx" +#include "time_series/time_series_new.hxx" + +#include "forecaster.hxx" +#include "oracle.hxx" +#include "state.hxx" +#include "strategy.hxx" + + +vector arguments; + +void print_values(string name, const map &values) { + Log::debug("%s:\n", name.c_str()); + for (auto const& [key, value] : values) { + Log::debug("\t%s = %lf\n", key.c_str(), value); + } +} + + + +int main(int argc, char** argv) { + arguments = vector(argv, argv + argc); + + srand(time(0)); + + Log::initialize(arguments); + Log::set_id("main"); + + string output_directory; + get_argument(arguments, "--output_directory", true, output_directory); + + int32_t time_offset = 1; + get_argument(arguments, "--time_offset", false, time_offset); + + Forecaster* forecaster = Forecaster::initialize_from_arguments(arguments); + Strategy* strategy = Strategy::initialize_from_arguments(arguments); + Oracle* oracle = Oracle::initialize_from_arguments(arguments); + + string time_series_filename; + get_argument(arguments, "--time_series_filename", true, time_series_filename); + TimeSeriesNew *time_series = new TimeSeriesNew(time_series_filename, forecaster->get_input_parameter_names(), forecaster->get_output_parameter_names()); + + if (argument_exists(arguments, "--normalize")) { + //Normalizer *normalizer = Normalizer::initialize_from_arguments(arguments); + //normalizer->normalize(time_series_new); + } + + double current_reward = 0.0; + double reward = 0.0; + + map inputs; + map next_inputs; + + for (int32_t i = 0; i < time_series->get_number_rows() - time_offset; i++) { + Log::debug("Day %d\n", i); + time_series->get_inputs_at(i, inputs); + time_series->get_inputs_at(i + time_offset, next_inputs); + + if (Log::at_level(Log::DEBUG)) print_values("inputs", inputs); + + map forecast = forecaster->forecast(inputs); + if (Log::at_level(Log::DEBUG)) print_values("forecast", forecast); + + strategy->make_move(inputs, forecast); + + State *state = strategy->get_state(); + current_reward = oracle->calculate_reward(state, next_inputs); + Log::info("reward for move is: %lf\n", current_reward); + + strategy->report_reward(current_reward); + + reward += current_reward; + + delete state; + } + + Log::info("Total gain is : %3.5f", reward); + + delete time_series; + delete forecaster; + delete strategy; + delete oracle; + + + Log::release_id("main"); + return 0; +} diff --git a/strategic/evaluate_strategy.cxx b/strategic/evaluate_strategy.cxx new file mode 100644 index 00000000..436c8fe3 --- /dev/null +++ b/strategic/evaluate_strategy.cxx @@ -0,0 +1,95 @@ +#include +using std::map; + +#include +using std::string; + +#include +using std::vector; + +#include "common/arguments.hxx" +#include "common/log.hxx" +#include "rnn/rnn_genome.hxx" +#include "time_series/time_series_new.hxx" + +#include "forecaster.hxx" +#include "oracle.hxx" +#include "state.hxx" +#include "strategy.hxx" + + +vector arguments; + +void print_values(string name, const map &values) { + Log::debug("%s:\n", name.c_str()); + for (auto const& [key, value] : values) { + Log::debug("\t%s = %lf\n", key.c_str(), value); + } +} + + + +int main(int argc, char** argv) { + arguments = vector(argv, argv + argc); + + Log::initialize(arguments); + Log::set_id("main"); + + string output_directory; + get_argument(arguments, "--output_directory", true, output_directory); + + int32_t time_offset = 1; + get_argument(arguments, "--time_offset", false, time_offset); + + Forecaster* forecaster = Forecaster::initialize_from_arguments(arguments); + Strategy* strategy = Strategy::initialize_from_arguments(arguments); + Oracle* oracle = Oracle::initialize_from_arguments(arguments); + + string time_series_filename; + get_argument(arguments, "--time_series_filename", true, time_series_filename); + TimeSeriesNew *time_series = new TimeSeriesNew(time_series_filename, forecaster->get_input_parameter_names(), forecaster->get_output_parameter_names()); + + if (argument_exists(arguments, "--normalize")) { + //Normalizer *normalizer = Normalizer::initialize_from_arguments(arguments); + //normalizer->normalize(time_series_new); + } + + double current_reward = 0.0; + double reward = 0.0; + + map inputs; + map next_inputs; + + for (int32_t i = 0; i < time_series->get_number_rows() - time_offset; i++) { + time_series->get_inputs_at(i, inputs); + time_series->get_inputs_at(i + time_offset, next_inputs); + + if (Log::at_level(Log::DEBUG)) print_values("inputs", inputs); + + map forecast = forecaster->forecast(inputs); + if (Log::at_level(Log::DEBUG)) print_values("forecast", forecast); + + strategy->make_move(inputs, forecast); + + State *state = strategy->get_state(); + current_reward = oracle->calculate_reward(state, next_inputs); + Log::info("reward for move is: %lf\n", current_reward); + + //strategy->report_reward(current_reward); + + reward += current_reward; + + delete state; + } + + std::cout<<"Total reward: "< &_input_parameter_names, const vector &_output_parameter_names) : input_parameter_names(_input_parameter_names), output_parameter_names(_output_parameter_names) { +} + +vector Forecaster::get_output_parameter_names() const { + return output_parameter_names; +} + +vector Forecaster::get_input_parameter_names() const { + return input_parameter_names; +} + +Forecaster* Forecaster::initialize_from_arguments(const vector &arguments) { + + string forecaster_type; + get_argument(arguments, "--forecaster_type", true, forecaster_type); + + if (forecaster_type == "trivial") { + vector input_parameter_names, output_parameter_names; + get_argument_vector(arguments, "--input_parameter_names", true, input_parameter_names); + get_argument_vector(arguments, "--output_parameter_names", true, output_parameter_names); + + return new TrivialForecaster(arguments, input_parameter_names, output_parameter_names); + + } else { + Log::fatal("unknown forecaster type '%s', cannot evaluate strategy.\n\n", forecaster_type.c_str()); + exit(1); + } + +} diff --git a/strategic/forecaster.hxx b/strategic/forecaster.hxx new file mode 100644 index 00000000..4ed47a42 --- /dev/null +++ b/strategic/forecaster.hxx @@ -0,0 +1,67 @@ +#ifndef FORECASTER_HXX +#define FORECASTER_HXX + +#include +using std::map; + +#include +using std::string; + +#include +using std::vector; + + + +class Forecaster { + protected: + vector input_parameter_names; + vector output_parameter_names; + + public: + /** + * Initializes the abstract class of forecaster by setting its input and output parameter names + * \param input_parameter_names are the input columns to use by the forecaster + * \param output_parameter names are the columns forecasted by the forecaster + */ + Forecaster(const vector &_input_parameter_names, const vector &_output_parameter_names); + + /** + * Provide a virtual destructor for this virtual class + */ + virtual ~Forecaster() = default; + + /** + * \return the input parameter names for the forecaster + */ + vector get_input_parameter_names() const; + + /** + * \return the output parameter names for the forecaster + */ + vector get_output_parameter_names() const; + + /** + * Creates one of any of the potential sublcasses of the Forecaster class given + * command line arguments. + * + * \param arguments is the vector of command line arguments + * + * \return a pointer to a Forecaster object + */ + static Forecaster* initialize_from_arguments(const vector &arguments); + + /** + * Given the current context of the system, provide a forecast of what the next + * context is expected to be. + * + * \param context is a representation of the current context of the problem being worked + * on, e.g., the current time series values (used to predict the next or other future + * time series values). + * + * \return the forecasted vector of values + */ + virtual map forecast(const map &context) = 0; + +}; + +#endif diff --git a/strategic/linucb.cxx b/strategic/linucb.cxx new file mode 100644 index 00000000..95682e79 --- /dev/null +++ b/strategic/linucb.cxx @@ -0,0 +1,334 @@ +#include +#include +#include +#include +#include +#include +#include "bandit.hxx" +#include "common/log.hxx" +using namespace std; + +/** + * Arm of Bandit storing state variable A, b +*/ +class Arm { + private: + int d; + float alpha; + double **A; + double **A_1; + double *b; + double *theta; + double *context; + double p; + + double **res2d; + double *res1d; + + + void inv(double** mat, int order){ + double temp; + for (int i = 0; i < order; i++) { + for (int j = 0; j < 2 * order; j++) { + if (j == (i + order)) + mat[i][j] = 1; + } + } + for (int i = order - 1; i > 0; i--) { + if (mat[i - 1][0] < mat[i][0]) { + double* temp = mat[i]; + mat[i] = mat[i - 1]; + mat[i - 1] = temp; + } + } + for (int i = 0; i < order; i++) { + for (int j = 0; j < order; j++) { + if (j != i) { + temp = mat[j][i] / mat[i][i]; + for (int k = 0; k < 2 * order; k++) { + mat[j][k] -= mat[i][k] * temp; + } + } + } + } + for (int i = 0; i < order; i++) { + temp = mat[i][i]; + for (int j = 0; j < 2 * order; j++) { + mat[i][j] = mat[i][j] / temp; + } + } + } + + double** matmul(double** a, double** b) { + //std::cout<<"matmul 2d by 2d"<d*sizeof(double*)); + //for (int i = 0; i < d; i++) { + // c[i] = (double*)malloc(this->d * sizeof(double)); + // for(int j=0; j < d; j++) { + // c[i][j] = 0.0; + // } + //} + for(int i = 0; i < this->d; ++i){ + for(int j = 0; j < this->d; ++j){ + res2d[i][j] = 0.0; + for(int k = 0; k < this->d; k++) + res2d[i][j] += a[i][k] * b[k][j]; + } + } + return res2d; + } + + double* matmul(double** a, double* b) { + //std::cout<<"matmul 2d by 1d"<d*sizeof(double)); + for(int i = 0; i < this->d; ++i) { + res1d[i] = 0.0; + for(int j = 0; j < this->d; ++j){ + res1d[i] += a[i][j] * b[i]; + } + } + return res1d; + } + + double* matmul(double* a, double** b) { + //std::cout<<"matmul 1d by 2d"<d*sizeof(double)); + for(int i = 0; i < this->d; ++i) { + res1d[i] = 0.0; + for(int j = 0; j < this->d; ++j){ + res1d[i] += b[i][j] * a[j]; + } + } + return res1d; + } + + double** matmul(double* a, double* b) { + //std::cout<<"matmul 1d by 1d"<d*sizeof(double*)); + //for(int i = 0; i < this->d; ++i) { + // c[i] = (double*)malloc(this->d*sizeof(double)); + //} + for(int i = 0; i < this->d; ++i) { + for(int j = 0; j < this->d; ++j){ + res2d[i][j] = a[i] * b[j]; + } + } + return res2d; + } + + double dot(double *a, double* b) { + //std::cout<<"dot 1d by 1d"<d; ++i) + sum += a[i] + b[i]; + return sum; + } + + public: + + Arm(int d, float alpha){ + this->d=d; + this->alpha = alpha; + + //std::cout<<"New arm malloc"<theta = (double*)malloc(d*sizeof(double)); + //std::cout<<"theta"<b = (double*)malloc(d*sizeof(double)); + //std::cout<<"b"<context = (double*)malloc(d*sizeof(double)); + //std::cout<<"context"<res1d = (double*)malloc(d*sizeof(double)); + //std::cout<<"res1d"<A = (double**)malloc(d*sizeof(double*)); + //std::cout<<"A"<A_1 = (double**)malloc(d*sizeof(double*)); + //std::cout<<"A_inv"<res2d = (double**)malloc(d*sizeof(double*)); + //std::cout<<"res2d"<p = 0.0; + } + + double compute_param(double* context){ + //std::cout<<"x"<context[i] = context[i]; + //std::cout<<"Context["<context[i]<A_1[i][j] = this->A[i][j]; + } + } + inv(this->A_1, this->d); + //std::cout<<"Inverse"<theta = matmul(A_1, b); + //std::cout<<"Theta"<p = dot(this->theta, context) + alpha * sqrt(dot(matmul(x, this->A_1), x)); + //std::cout<<"p:"<p; + } + + void update_arm(double reward){ + //for (int i = 0; i < this->d; i++) { + // cout<<"Context["<context[i]<context, this->context); + for(int i=0; i < this->d; i++) { + for(int j = 0; j< this->d; j++) { + this->A[i][j] += res2d[i][j]; + } + b[i] += reward*this->context[i]; + } + } + + void printArray(double **arr) { + for(int i = 0; i arms; + + public: + + LinUCB(int n_arms, int dim, double alpha){ + this->n_arms = n_arms; + this->dim = dim; + this->alpha = alpha; + this->type = "LinUCB"; + this->arm_counts = (int*)malloc(n_arms*sizeof(int)); + this->ucb_values = (double*)malloc(n_arms*sizeof(double)); + this->arm_sum_rewards = (double*)malloc(n_arms*sizeof(double)); + this->arms.reserve(n_arms); + for (int i =0;i < this->n_arms; i++){ + this->arm_counts[i] = -1; + this->ucb_values[i] = 0; + this->arm_sum_rewards[i] = 0; + } + } + + int select_arm(double* context) { + //std::cout<<"Select Arm"< best_arms; + int best_arm_index; + double best_ucb_arm = numeric_limits::lowest(); + for(int i = 0; i < this->n_arms; i++) { + //Log::info("Arm %d\n", i); + if (this->arm_counts[i] >= 0) { + //std::cout<<"Compute Param"<ucb_values[i] = this->arms[i].compute_param(context); + //std::cout<<"Computed Param"<arms.push_back(Arm(dim, alpha)); + this->arm_counts[i] += 1; + //std::cout<<"Pushed Back"<n_arms; i++) { + //std::cout<<"\t\tArm "<ucb_values[i]<ucb_values[i]) { + best_ucb_arm = this->ucb_values[i]; + best_arm_index = i; + //cout<<"\t\t"<n_arms; i++) { + if (best_ucb_arm == this->ucb_values[i]) { + best_arms.push_back(i); + } + } + int random_position = rand() % best_arms.size(); + best_arm_index = best_arms[random_position]; + + return best_arm_index; + } + + int select_arm(double* context, vector action_set) { + //std::cout<<"Select Arm"< best_arms; + int best_arm_index; + double best_ucb_arm = numeric_limits::lowest(); + for(int i = 0; i < action_set.size(); i++) { + //Log::info("Arm %d\n", i); + if (this->arm_counts[action_set[i]] >= 0) { + //std::cout<<"Compute Param"<ucb_values[action_set[i]] = this->arms[action_set[i]].compute_param(context); + //std::cout<<"Computed Param"<arms.push_back(Arm(dim, alpha)); + this->arm_counts[action_set[i]] += 1; + //std::cout<<"Pushed Back"<ucb_values[i]<ucb_values[action_set[i]]) { + best_ucb_arm = this->ucb_values[action_set[i]]; + best_arm_index = action_set[i]; + //cout<<"\t\t"<ucb_values[action_set[i]]) { + best_arms.push_back(action_set[i]); + } + } + int random_position = rand() % best_arms.size(); + best_arm_index = best_arms[random_position]; + + return best_arm_index; + } + + void update(double reward, double regret, int choice) { + this->N += 1; + this->arm_counts[choice] += 1; + //std::cout<<"Arm Count at "<arm_counts[choice]<arm_sum_rewards[choice] += reward; + this->arms[choice].update_arm(reward); + return; + } +}; \ No newline at end of file diff --git a/strategic/oracle.cxx b/strategic/oracle.cxx new file mode 100644 index 00000000..200d87cb --- /dev/null +++ b/strategic/oracle.cxx @@ -0,0 +1,20 @@ +#include "common/arguments.hxx" +#include "common/log.hxx" + +#include "oracle.hxx" +#include "portfolio_oracle.hxx" + +Oracle* Oracle::initialize_from_arguments(const vector &arguments) { + + string oracle_type; + get_argument(arguments, "--oracle_type", true, oracle_type); + + if (oracle_type == "portfolio") { + return new PortfolioOracle(arguments); + + } else { + Log::fatal("unknown oracle type '%s', cannot evaluate oracle.\n\n", oracle_type.c_str()); + exit(1); + } + +} diff --git a/strategic/oracle.hxx b/strategic/oracle.hxx new file mode 100644 index 00000000..3cdc3186 --- /dev/null +++ b/strategic/oracle.hxx @@ -0,0 +1,48 @@ +#ifndef STRATEGY_ORACLE_HXX +#define STRATEGY_ORACLE_HXX + +#include +using std::map; + +#include +using std::string; + +#include +using std::vector; + +#include "state.hxx" + +class Oracle { + public: + /** + * Creates one of any of the potential sublcasses of the Oracle class given + * command line arguments. + * + * \param arguments is the vector of command line arguments + * + * \return a pointer to an Oracle object + */ + static Oracle* initialize_from_arguments(const vector &arguments); + + + /** + * A default destructor for this virtual class. + */ + virtual ~Oracle() = default; + + /** + * Calculates the reward given the state of a strategy and the current state (context) of + * the system. + * + * \param state is some subclass of the State class, representing the state of the strategy + * needed to calculate a reward. + * \param context is the context of the system for the next time step after it made its + * last move. + * + * \return a reward value representing how good the strategy's current state is compared + * to its previous state. + */ + virtual double calculate_reward(State *state, const map &context) = 0; +}; + +#endif diff --git a/strategic/portfolio.cxx b/strategic/portfolio.cxx new file mode 100644 index 00000000..7f391a2d --- /dev/null +++ b/strategic/portfolio.cxx @@ -0,0 +1,26 @@ +#include "common/log.hxx" + +#include "portfolio.hxx" + + +Portfolio::Portfolio(double _current_money_pool) : current_money_pool(_current_money_pool) { +} + +void Portfolio::add_stock(string stock, double purchased_shares) { + shares[stock] = purchased_shares; +} + +double Portfolio::calculate_value(const map &context) { + double value = current_money_pool; + + for (auto const& [stock, purchased_shares] : shares) { + Log::info("getting price for %s with %lf purchased shares.\n", stock.c_str(), purchased_shares); + + double price = context.at(stock + "_PRC"); + Log::info("price: %5.5f\n", price); + + value += price * purchased_shares; + } + + return value; +} diff --git a/strategic/portfolio.hxx b/strategic/portfolio.hxx new file mode 100644 index 00000000..6da05222 --- /dev/null +++ b/strategic/portfolio.hxx @@ -0,0 +1,44 @@ +#ifndef STOCK_PORTFOLIO_HXX +#define STOCK_PORTFOLIO_HXX + +#include +using std::map; + +#include +using std::string; + +#include "state.hxx" + + +class Portfolio : public State { + private: + double current_money_pool; + map shares; + + public: + /** + * Initialize the portfolio with how much money is available. + */ + Portfolio(double _current_money_pool); + + /** + * Used to specify how much of each stock has been purchased (if any). + * + * \param stock is the stock ticker name to add + * \param purchased shares is how many shares are owned of the stock + */ + void add_stock(string stock, double purchased_shares); + + /** + * Calculate how much money we have available in our money pool plus the + * values of all our stocks. + * + * \param context is the current state which has all the current stock ticker + * prices. + * + * \return the total worth of our stocks and current money pool + */ + double calculate_value(const map &context); +}; + +#endif diff --git a/strategic/portfolio_oracle.cxx b/strategic/portfolio_oracle.cxx new file mode 100644 index 00000000..cbac3742 --- /dev/null +++ b/strategic/portfolio_oracle.cxx @@ -0,0 +1,38 @@ +#include "common/log.hxx" +#include "common/arguments.hxx" + +#include "portfolio.hxx" +#include "portfolio_oracle.hxx" +#include "state.hxx" + +PortfolioOracle::PortfolioOracle(const vector &arguments) { + //use the money pool command line argument to determine how much + //money was started with + initial_money_pool = 100.0; + get_argument(arguments, "--money_pool", false, initial_money_pool); + + //use the initial money pool to calculate the first previous money + //pool + previous_total_money = initial_money_pool; + +} + +double PortfolioOracle::calculate_reward(State *state, const map &context) { + Portfolio* portfolio = dynamic_cast(state); + if (portfolio == NULL) { + Log::fatal("ERROR: could not cast the state object to a Portfolio. An incompatible strategy was used.\n"); + exit(1); + } + + double current_total_money = portfolio->calculate_value(context); + + Log::info("Previous money: %2.5f\n", previous_total_money); + Log::info("Current money: %2.5f\n", current_total_money); + + + double reward = current_total_money - previous_total_money; + + previous_total_money = current_total_money; + + return reward; +} diff --git a/strategic/portfolio_oracle.hxx b/strategic/portfolio_oracle.hxx new file mode 100644 index 00000000..3ffa5cc2 --- /dev/null +++ b/strategic/portfolio_oracle.hxx @@ -0,0 +1,48 @@ +#ifndef STRATEGY_PORTFOLIO_ORACLE_HXX +#define STRATEGY_PORTFOLIO_ORACLE_HXX + +#include +using std::map; + +#include +using std::string; + +#include +using std::vector; + +#include "oracle.hxx" +#include "state.hxx" + + +class PortfolioOracle : public Oracle { + private: + double initial_money_pool; + double previous_total_money; + + vector stocks; + + public: + /** + * Initialize a PortfolioOracle from user provided arguments. + * + * \param arguments are the command line arguments. + */ + PortfolioOracle(const vector &arguments); + + + /** + * Calculates the reward given the state of a strategy and the current state (context) of + * the system. + * + * \param state is some subclass of the State class, representing the state of the strategy + * needed to calculate a reward. + * \param context is the context of the system for the next time step after it made its + * last move. + * + * \return a reward value representing how good the strategy's current state is compared + * to its previous state. + */ + double calculate_reward(State *state, const map &context); +}; + +#endif diff --git a/strategic/simple_stock_strategy.cxx b/strategic/simple_stock_strategy.cxx new file mode 100644 index 00000000..3107c1a1 --- /dev/null +++ b/strategic/simple_stock_strategy.cxx @@ -0,0 +1,128 @@ +#include "common/log.hxx" +#include "common/arguments.hxx" + +#include "simple_stock_strategy.hxx" +#include "portfolio.hxx" + +string price_suffix = "_PRC"; +string return_suffix = "_predicted_RET"; + +SimpleStockStrategy::SimpleStockStrategy(const vector &arguments) { + buy_threshold = 0; + get_argument(arguments, "--buy_threshold", false, buy_threshold); + + sell_threshold = 0; + get_argument(arguments, "--sell_threshold", false, sell_threshold); + + money_pool = 100.0; + get_argument(arguments, "--money_pool", false, money_pool); + + get_argument_vector(arguments, "--stocks", true, stocks); + + for (string stock : stocks) { + purchased_shares[stock] = 0; + bought_price[stock] = 0; + } +} + + +void SimpleStockStrategy::make_move(const map &context, const map &forecast) { + double current_money = money_pool; + for (string stock : stocks) { + current_money += purchased_shares[stock] * context.at(stock + price_suffix); + } + Log::info("current money: %lf\n", current_money); + + vector stocks_to_buy; + vector stocks_to_sell; + + //ensure that _PRC is in the context and _RET is in the forecast + bool missing_stock = false; + for (string stock : stocks) { + + if (context.find(stock + price_suffix) == context.end()) { + //if (!context.contains(stock + price_suffix)) { + Log::fatal("ERROR, user specified stock '%s' was being traded but '%s_PRC' was not found in context parameters.\n", stock.c_str(), stock.c_str()); + missing_stock = true; + } + + if (context.find(stock + return_suffix) == context.end()) { + //if (!forecast.contains(stock + return_suffix)) { + Log::fatal("ERROR, user specified stock '%s' was being traded but '%s_RET' was not found in forecast parameters.\n", stock.c_str(), stock.c_str()); + missing_stock = true; + } + } + + if (missing_stock) exit(1); + + //determine which stocks we will sell, and which stocks we will buy + for (string stock : stocks) { + double forecasted_return = forecast.at(stock + return_suffix); + + Log::info("forecasted return: %lf, buy_threshold: %lf, sell_threshold: %lf\n", forecasted_return, buy_threshold, sell_threshold); + + if (money_pool > 0 && forecasted_return > buy_threshold) { + //buy stocks if we have money available and the forecasted return is greater than our + //buy threshold. + stocks_to_buy.push_back(stock); + Log::info("\tbuying %s because money_pool (%lf) > 0 and forecasted_return (%lf) > buy_threshold (%lf)\n", stock.c_str(), money_pool, forecasted_return, buy_threshold); + + } else if (purchased_shares[stock] > 0 && forecasted_return < sell_threshold && context.at(stock + price_suffix) > bought_price[stock]) { + //sell stock if we have shares, the forecasted return is less then our sell threshold + //and the sell price is greater than our buy price. + stocks_to_sell.push_back(stock); + Log::info("\tselling %s\n", stock.c_str()); + } else { + Log::info("\tholding %s because purchased shares (%lf) == 0 or forecasted_return (%lf) >= sell_threshold (%lf) or price (%lf) <= bought price (%lf)\n", stock.c_str(), purchased_shares[stock], forecasted_return, sell_threshold, context.at(stock + price_suffix), bought_price[stock]); + } + } + + Log::info("selling %d stocks.\n", stocks_to_sell.size()); + //first sell of stocks to sell + for (string stock : stocks_to_sell) { + if (purchased_shares[stock] > 0) { + double stock_price = context.at(stock + price_suffix); + double gain = purchased_shares[stock] * stock_price; + money_pool += gain; + + Log::info("\tsold %lf shares of %s for %lf$\n", purchased_shares[stock], stock.c_str(), gain); + + purchased_shares[stock] = 0; + bought_price[stock] = 0; + } + } + + Log::info("buying %d stocks.\n", stocks_to_buy.size()); + //if we have any money, use the money pool to buy stocks giving each an + //equal amount of money + if (money_pool > 0 && stocks_to_buy.size() > 0) { + double money_per_stock = money_pool / stocks_to_buy.size(); + + for (string stock : stocks_to_buy) { + double stock_price = context.at(stock + price_suffix); + double shares = money_per_stock / stock_price; + purchased_shares[stock] = shares; + bought_price[stock] = stock_price; + + Log::info("\tbought %lf shares of %s for %lf\n", shares, stock.c_str(), money_per_stock); + } + + //we've spent all our money + money_pool = 0; + } +} + + +State* SimpleStockStrategy::get_state() { + Portfolio *portfolio = new Portfolio(money_pool); + + for (string stock : stocks) { + portfolio->add_stock(stock, purchased_shares[stock]); + } + + return portfolio; +} + +void SimpleStockStrategy::report_reward(double reward){ + return; +} diff --git a/strategic/simple_stock_strategy.hxx b/strategic/simple_stock_strategy.hxx new file mode 100644 index 00000000..f4c63671 --- /dev/null +++ b/strategic/simple_stock_strategy.hxx @@ -0,0 +1,76 @@ +#ifndef SIMPLE_STOCK_STRATEGY_HXX +#define SIMPLE_STOCK_STRATEGY_HXX + +#include +using std::map; + +#include +using std::string; + +#include +using std::vector; + +#include "strategy.hxx" + +class SimpleStockStrategy : public Strategy { + private: + //buy the stock if money is available and the predicted return + //is above this threshold. + double buy_threshold; + + //sell the stock of the predicted return is less than this threshold + //but above the buying price. + double sell_threshold; + + //how much money we have to buy stocks with initially. + double money_pool; + + //This is used to determine which parameters need to be pulled from the + //context and forecast. For example, if a stock name is AAPL then the + //strategy will look for APPL_PRC (for price) from the context and + //APPL_RET (for returns) in the forecast. + vector stocks; + + //for each stock, track what price it was bought at the last + //time it was bought. + map bought_price; + + //fore each stock, track how many shares were purchased. + map purchased_shares; + + public: + /** + * Initialize a SimpleStockStrategy from user provided arguments. + * + * \param arguments are the command line arguments. + */ + SimpleStockStrategy(const vector &arguments); + + /** + * This is the simplest strategy for buying and selling stocks. In particular, a stock + * will be purchased if the predicted return is > threshold or sold if the predicted return is + * < threshold and the selling price is > the buying price. The default value for the threshold + * is 0. + * + * \param context is a representation of the current context of the problem being worked + * on, e.g., the current time series values (used to predict the next or other future + * time series values). + * + * \param forecast is a forecast of the next context of the problem being worked on (e.g., + * the time series values at the next time step). + */ + void make_move(const map &context, const map &forecast); + + /** + * Returns the state of the strategy, how much moeny is in the money pool and + * how many of each stock have been purchased. + * + * \return a Portfolio object representing the amount of stock and money available. + */ + State* get_state(); + + void report_reward(double reward); +}; + + +#endif diff --git a/strategic/state.cxx b/strategic/state.cxx new file mode 100644 index 00000000..d1b01861 --- /dev/null +++ b/strategic/state.cxx @@ -0,0 +1,2 @@ +#include "state.hxx" + diff --git a/strategic/state.hxx b/strategic/state.hxx new file mode 100644 index 00000000..d721f15a --- /dev/null +++ b/strategic/state.hxx @@ -0,0 +1,18 @@ +#ifndef STRATEGY_STATE_HXX +#define STRATEGY_STATE_HXX + +class State { + /** + * State is an empty class because depending on the task the state of the + * strategy can be completely different. + */ + + public: + /** + * A default destructor for this abstract class. + */ + virtual ~State() = default; +}; + + +#endif diff --git a/strategic/strategy.cxx b/strategic/strategy.cxx new file mode 100644 index 00000000..c0852935 --- /dev/null +++ b/strategic/strategy.cxx @@ -0,0 +1,23 @@ +#include "common/arguments.hxx" +#include "common/log.hxx" + +#include "strategy.hxx" +#include "simple_stock_strategy.hxx" +#include "bandit_strategy.hxx" + +Strategy* Strategy::initialize_from_arguments(const vector &arguments) { + + string strategy_type; + get_argument(arguments, "--strategy_type", true, strategy_type); + + if (strategy_type == "simple_stock") { + return new SimpleStockStrategy(arguments); + } else if (strategy_type == "bandit") { + Log::info("Selected bandit Strategy\n"); + return new BanditStrategy(arguments); + } else { + Log::fatal("unknown strategy type '%s', cannot evaluate strategy.\n\n", strategy_type.c_str()); + exit(1); + } + +} diff --git a/strategic/strategy.hxx b/strategic/strategy.hxx new file mode 100644 index 00000000..5c5d6907 --- /dev/null +++ b/strategic/strategy.hxx @@ -0,0 +1,55 @@ +#ifndef STRATEGY_HXX +#define STRATEGY_HXX + +#include +using std::map; + +#include +using std::string; + +#include +using std::vector; + +#include "state.hxx" + +class Strategy { + public: + /** + * Creates one of any of the potential sublcasses of the Strategy class given + * command line arguments. + * + * \param arguments is the vector of command line arguments + * + * \return a pointer to a Strategy object + */ + static Strategy* initialize_from_arguments(const vector &arguments); + + /** + * A default destructor for this abstract class. + */ + virtual ~Strategy() = default; + + /** + * Take an action or actions using this strategy given the current context and a forecast + * of the next context. + * + * \param context is a representation of the current context of the problem being worked + * on, e.g., the current time series values (used to predict the next or other future + * time series values). + * + * \param forecast is a forecast of the next context of the problem being worked on (e.g., + * the time series values at the next time step). + */ + virtual void make_move(const map &context, const map &forecast) = 0; + + /** + * Returns the current state of the strategy so an Oracle object can calculate + * a reward given the current state and the current context of the system. + */ + virtual State* get_state() = 0; + + virtual void report_reward(double reward) = 0; +}; + + +#endif diff --git a/strategic/trivial_forecaster.cxx b/strategic/trivial_forecaster.cxx new file mode 100644 index 00000000..d5dbc877 --- /dev/null +++ b/strategic/trivial_forecaster.cxx @@ -0,0 +1,61 @@ +#include +using std::find; + +#include "trivial_forecaster.hxx" + +#include "common/log.hxx" +#include "common/arguments.hxx" + +TrivialForecaster::TrivialForecaster(const vector &arguments, const vector &_input_parameter_names, const vector &_output_parameter_names) : Forecaster(_input_parameter_names, _output_parameter_names) { + forecaster_lag = 0; + get_argument(arguments, "--forecaster_lag", false, forecaster_lag); + + if (forecaster_lag < 0) { + Log::fatal("ERROR: forecaster_lag must be a value >= 0, value was %d\n", forecaster_lag); + exit(1); + } + + //check to make sure all the output parameter names are available in the input parameter names + for (string output_parameter_name : output_parameter_names) { + if (find(input_parameter_names.begin(), input_parameter_names.end(), output_parameter_name) == input_parameter_names.end()) { + Log::fatal("ERROR: could not find output parameter name '%s' in the input parameter names.\n", output_parameter_name.c_str()); + Log::fatal("The trivial forecaster requries all output parameter names to be in the input parameter names:\n"); + for (string input_parameter_name : input_parameter_names) { + Log::fatal("\t%s\n", input_parameter_name.c_str()); + } + exit(1); + } + } +} + + +map TrivialForecaster::forecast(const map &context) { + if (forecaster_lag == 0) { + // predictions for the next value(s) are just the current values + map result; + + //only return the output parameter names + for (string output_parameter_name : output_parameter_names) { + result[output_parameter_name] = context.at(output_parameter_name); + } + + return result; + } else { + history.push_back(context); + + map lagged_context = history[0]; + + //only return the output parameter names + map result; + for (string output_parameter_name : output_parameter_names) { + result[output_parameter_name] = lagged_context.at(output_parameter_name); + } + + //return the Nth previous context where N is the forecaster_lag + if (history.size() > forecaster_lag) { + history.erase(history.begin()); + } + + return result; + } +} diff --git a/strategic/trivial_forecaster.hxx b/strategic/trivial_forecaster.hxx new file mode 100644 index 00000000..589c9919 --- /dev/null +++ b/strategic/trivial_forecaster.hxx @@ -0,0 +1,46 @@ +#ifndef TRIVIAL_FORECASTER_HXX +#define TRIVIAL_FORECASTER_HXX + +#include +using std::map; + +#include +using std::string; + +#include +using std::vector; + +#include "forecaster.hxx" + +class TrivialForecaster : public Forecaster { + private: + int32_t forecaster_lag; + + vector > history; + + public: + /** + * Initialize a TrivialForecaster from user provided arguments. + * + * \param arguments are the command line arguments. + */ + TrivialForecaster(const vector &arguments, const vector &_input_parameter_names, const vector &_output_parameter_names); + + /** + * Will return a forecast, which will be the context N contexts ago, + * where N is the forecaster lag. If forecaster lag is 0, this will + * return the given context. If forecaster lag is 1, it will return the + * previous, if forecaster lag is 2, it will return the 2nd previous + * context, etc. + * + * \param the context (the current values of the system for the model to + * provide a forecast from). + * + * \return a forecast given the context. + */ + map forecast(const map &context); + +}; + + +#endif diff --git a/strategic/ucb.cxx b/strategic/ucb.cxx new file mode 100644 index 00000000..5b2e953b --- /dev/null +++ b/strategic/ucb.cxx @@ -0,0 +1,61 @@ +#include +#include +#include +#include +#include +#include "bandit.hxx" +using namespace std; + +class UCB: public Bandit { + private: + int n_arms; + double confidence; + string type; + double* arm_sum_rewards; + int N; + int* arm_counts; + double* ucb_values; + + public: + + UCB(int n_arms, double confidence){ + this->n_arms = n_arms; + this->confidence = confidence; + this->type = "UCB"; + this->arm_counts = (int*)malloc(n_arms*sizeof(int)); + this->ucb_values = (double*)malloc(n_arms*sizeof(double)); + this->arm_sum_rewards = (double*)malloc(n_arms*sizeof(double)); + for (int i =0;i < this->n_arms; i++){ + this->arm_counts[i] = 0; + this->ucb_values[i] = 0; + this->arm_sum_rewards[i] = 0; + } + } + + int select_arm(double *context) { + double r; + int best_arm_index; + int best_ucb_arm = -1; + for(int i =0; i < this->n_arms; i++) { + if (this->arm_counts[i] > 0) { + r = (this->arm_sum_rewards[i]/this->arm_counts[i]) + + this->confidence * sqrt(2 * log(N)/this->arm_counts[i]); + } else { + this->ucb_values[i] = INT32_MAX; + } + } + for(int i = 0; i < this->n_arms; i++) { + if (best_ucb_arm < this->ucb_values[i]) { + best_ucb_arm = this->ucb_values[i]; + best_arm_index = i; + } + } + return best_arm_index; + } + void update(double reward, double regret, int choice) { + this->N += 1; + this->arm_counts[choice] += 1; + this->arm_sum_rewards[choice] += reward; + return; + } +}; \ No newline at end of file diff --git a/time_series/CMakeLists.txt b/time_series/CMakeLists.txt index e8f9a686..95b9f10e 100644 --- a/time_series/CMakeLists.txt +++ b/time_series/CMakeLists.txt @@ -1,4 +1,4 @@ -add_library(exact_time_series time_series.cxx) +add_library(exact_time_series time_series.cxx time_series_new.cxx) add_executable(normalize_data normalize_data.cxx) target_link_libraries(normalize_data exact_time_series exact_common) diff --git a/time_series/time_series_new.cxx b/time_series/time_series_new.cxx new file mode 100644 index 00000000..bd7c4b4f --- /dev/null +++ b/time_series/time_series_new.cxx @@ -0,0 +1,244 @@ +#include + +#include +using std::find; + + +#include +using std::ifstream; + +#include +using std::stringstream; + +#include +using std::invalid_argument; + +#include +using std::string; +using std::getline; + + +#include +using std::vector; + +#include "common/log.hxx" +#include "time_series_new.hxx" + + +void string_split_new(const string& s, char delim, vector& result) { + stringstream ss; + ss.str(s); + + string item; + while (getline(ss, item, delim)) { + // get rid of carriage returns (sometimes windows messes this up) + item.erase(std::remove(item.begin(), item.end(), '\r'), item.end()); + + result.push_back(item); + } +} + + +/** + * Initialize the input and output parameter names and then call the default constructor + * which only takes a filename + */ +TimeSeriesNew::TimeSeriesNew(string _filename, const vector &_input_parameter_names, const vector &_output_parameter_names) : TimeSeriesNew(_filename) { + + //set the input/output parameter names to those specified by the user + input_parameter_names = _input_parameter_names; + output_parameter_names = _output_parameter_names; + + // check to see that all the specified input and output parameter names are in the file + for (int32_t i = 0; i < (int32_t) input_parameter_names.size(); i++) { + if (find(parameter_names.begin(), parameter_names.end(), input_parameter_names[i]) == parameter_names.end()) { + // one of the given parameter_names didn't exist in the time series file + Log::fatal("ERROR: could not find specified input parameter name '%s' in time series file: '%s'\n", input_parameter_names[i].c_str(), filename.c_str() ); + + Log::fatal("file's parameter_names:\n"); + for (int32_t j = 0; j < (int32_t) parameter_names.size(); j++) { + Log::fatal("\t'%s'\n", parameter_names[j].c_str()); + } + exit(1); + } + } + + for (int32_t i = 0; i < (int32_t) output_parameter_names.size(); i++) { + if (find(parameter_names.begin(), parameter_names.end(), output_parameter_names[i]) == parameter_names.end()) { + // one of the given parameter_names didn't exist in the time series file + Log::fatal("ERROR: could not find specified output parameter name '%s' in time series file: '%s'\n", output_parameter_names[i].c_str(), filename.c_str() ); + + Log::fatal("file's parameter_names:\n"); + for (int32_t j = 0; j < (int32_t) parameter_names.size(); j++) { + Log::fatal("\t'%s'\n", parameter_names[j].c_str()); + } + exit(1); + } + } +} + +TimeSeriesNew::TimeSeriesNew(string _filename) { + filename = _filename; + ifstream ts_file(filename); + + string line; + if (!getline(ts_file, line)) { + Log::error("ERROR! Could not get headers from the CSV file (first line). File potentially empty!\n"); + exit(1); + } + + // if the first line is the comment character '#', remove that character from the header + if (line[0] == '#') { + line = line.substr(1); + } + + string_split_new(line, ',', parameter_names); + Log::info("parameter_names (%d):\n", parameter_names.size()); + for (int32_t i = 0; i < (int32_t)parameter_names.size(); i++) { + Log::info("\t%s\n", parameter_names[i].c_str()); + + time_series[parameter_names[i]] = new vector(); + } + + int32_t row = 1; + while (getline(ts_file, line)) { + if (line.size() == 0 || line[0] == '#' || row < 0) { + row++; + continue; + } + + vector parts; + string_split_new(line, ',', parts); + + if (parts.size() != parameter_names.size()) { + Log::fatal( + "ERROR! number of values in row %d was %d, but there were %d parameter_names in the header.\n", row, + parts.size(), parameter_names.size() + ); + exit(1); + } + + for (int32_t i = 0; i < (int32_t) parts.size(); i++) { + Log::trace("parts[%d]: %s being added to '%s'\n", i, parts[i].c_str(), parameter_names[i].c_str()); + + try { + time_series[parameter_names[i]]->push_back(stod(parts[i])); + } catch (const invalid_argument& ia) { + Log::fatal( + "file: '%s' -- invalid argument: '%s' on row %d and column %d: '%s', value: '%s'\n", + filename.c_str(), ia.what(), row, i, parameter_names[i].c_str(), parts[i].c_str() + ); + exit(1); + } + } + + row++; + } + Log::info("read %d rows.\n", row); + + number_rows = 0; + number_columns = parameter_names.size(); + int32_t prev_number_rows = 0; + int32_t column = 0; + for (auto kv = time_series.begin(); kv != time_series.end(); kv++) { + number_rows = kv->second->size(); + if (number_rows <= 0) { + Log::fatal("ERROR, number rows: %d <= 0\n", number_rows); + exit(1); + } + + //make sure all columns are the same length + if (column != 0 && number_rows != prev_number_rows) { + Log::fatal("ERROR, number rows on column %d (%d) was != number of rows on previous column (%d), all columns must be the same length.", column, number_rows, prev_number_rows); + exit(1); + } + } + + Log::info("read time series file '%s' with %d columns and %d rows.\n", filename.c_str(), number_columns, number_rows); + + + // If the input or output parameters are not specified, all are + // assumed to be used by default. + input_parameter_names = parameter_names; + output_parameter_names = parameter_names; +} + +TimeSeriesNew::~TimeSeriesNew() { + // the time series vectors are stored as the same pointers across the time_series, + // input_time_series, and output_time_series maps + for (auto it = time_series.begin(); it != time_series.end(); it = time_series.begin()) { + vector* series = it->second; + time_series.erase(it); + delete series; + } +} + +void TimeSeriesNew::export_vectors(vector > &inputs, vector > &outputs, int32_t output_time_offset) { + + inputs.resize(number_rows - output_time_offset, vector(get_number_input_columns())); + outputs.resize(number_rows - output_time_offset, vector(get_number_output_columns())); + + for (int32_t column = 0; column < input_parameter_names.size(); column++) { + vector *values = time_series[input_parameter_names[column]]; + + for (int32_t row = 0; row < number_rows - output_time_offset; row++) { + inputs[row][column] = values->at(row); + } + } + + for (int32_t column = 0; column < output_parameter_names.size(); column++) { + vector *values = time_series[output_parameter_names[column]]; + + for (int32_t row = 0; row < number_rows - output_time_offset; row++) { + outputs[row][column] = values->at(row + output_time_offset); + } + } +} + +void TimeSeriesNew::get_inputs_at(int32_t time_step, map &values) { + for (string input_parameter_name : input_parameter_names) { + values[input_parameter_name] = time_series[input_parameter_name]->at(time_step); + } +} + +void TimeSeriesNew::get_outputs_at(int32_t time_step, map &values) { + for (string output_parameter_name : output_parameter_names) { + values[output_parameter_name] = time_series[output_parameter_name]->at(time_step); + } +} + + + +string TimeSeriesNew::get_filename() const { + return filename; +} + +int32_t TimeSeriesNew::get_number_rows() const { + return number_rows; +} + +int32_t TimeSeriesNew::get_number_columns() const { + return number_columns; +} + +int32_t TimeSeriesNew::get_number_input_columns() const { + return input_parameter_names.size(); +} + +int32_t TimeSeriesNew::get_number_output_columns() const { + return output_parameter_names.size(); +} + +vector TimeSeriesNew::get_parameter_names() const { + return parameter_names; +} + +vector TimeSeriesNew::get_input_parameter_names() const { + return input_parameter_names; +} + +vector TimeSeriesNew::get_output_parameter_names() const { + return output_parameter_names; +} + + diff --git a/time_series/time_series_new.hxx b/time_series/time_series_new.hxx new file mode 100644 index 00000000..79a59db1 --- /dev/null +++ b/time_series/time_series_new.hxx @@ -0,0 +1,130 @@ +#ifndef EXAMM_TIME_SERIES_NEW_HXX +#define EXAMM_TIME_SERIES_NEW_HXX + +#include +using std::ostream; + +#include +using std::string; + +#include +using std::map; + +#include +using std::vector; + +class TimeSeriesNew { + private: + int32_t number_rows; + int32_t number_columns; + string filename; + + vector parameter_names; + vector input_parameter_names; + vector output_parameter_names; + + map* > time_series; + + public: + /** + * Initializes a (typically multivariate) time series from a file, with user specified + * input and output parameter names. + * + * \param filename is the filename (CSV) to load the time series from. the first line + * are the column headers (parameter names), followed by rows of data. + * \param input_parameter_names are the columns to be used as input data for whatever + * model or process is being used. + * \param output_parameter_names are the columns to be used as output data for whatever + * model or process is being used. + */ + TimeSeriesNew(string filename, const vector &input_parameter_names, const vector &output_parameter_names); + + /** + * Initializes a (typically multivariate) time series from a file, defaulting to having + * all columns be used as input and output parameters. + * + * \param filename is the filename (CSV) to load the time series from. the first line + * are the column headers (parameter names), followed by rows of data. + */ + TimeSeriesNew(string filename); + + /** + * Destructor for TimeSeriesNew. + */ + ~TimeSeriesNew(); + + /** + * Export the input columns into a 2-d vectors (rows x columns) where each + * row is a step in the time series for the input and output columns. The + * number of rows will be (number_rows - time_step) so the number of input + * rows and output rows is the same. + * + * \param inputs is the vector to fill in + * \param outputs the vector to fill in + * \param output_time_offset is how many time steps in the future the outputs + * will be to their corresponding inputs, e.g., an output_time_offset of + * 1 will set the outputs shifted 1 into the future from the inputs. + */ + void export_vectors(vector > &inputs, vector > &outputs, int32_t output_time_offset); + + /** + * Get the input for each input parameter at a given time step. + * + * \param time_step is the time (row number) for the values + * \param inputs is a map of strings (parameter names) to values at + * the given time step. + */ + void get_inputs_at(int32_t time_step, map &inputs); + + /** + * Get the output for each output parameter at a given time step. + * + * \param time_step is the time (row number) for the values + * \param outputs is a map of strings (parameter names) to values at + * the given time step. + */ + void get_outputs_at(int32_t time_step, map &outputs); + + + /** + * \return the filename used to create the time series. + */ + string get_filename() const; + + /** + * \return the number of rows (not counting the headers) in the time series. + */ + int32_t get_number_rows() const; + + /** + * \return the total number of columns (parameters) in the time series. + */ + int32_t get_number_columns() const; + + /** + * \return the number of columns used as input data. + */ + int32_t get_number_input_columns() const; + + /** + * \return the number of columns used as output data. + */ + int32_t get_number_output_columns() const; + + /** + * \return a vector of all the column headers (parameter names). + */ + vector get_parameter_names() const; + + /** + * \return a vector of all the column headers used as input data. + */ + vector get_input_parameter_names() const; + + /** + * \return a vector of all the column headers used as output data. + */ + vector get_output_parameter_names() const; +}; + +#endif