/*Dale Swanson Feburary 12 2007*/
#include <cstdlib>
#include <iostream>
#include <fstream>
#include <math.h>
//#include <time>
double startm = 0; //stores staring money
double goalm = 0; //stores goal money
double curm = 0; //stores current money
double bet[10]; //stores the bets 1 - 8, then 9 will store the multiplier to use from there.
int x; 
int y;
int z; //my general use varibles, used for answering questions, loops, any temp need.
double tested = 0; //stores number of patterns tested
double good = 0; //stores number of patterns that where above the threshold
double thres = 0; //stores the threshold to consider a pattern good, as a 2 digit % of times reached goal
double numtests = 0; //stores how many times to test each betting pattern before recording results
int mode; //stores auto - 1, or manual mode - 2
double odds = 0; //stores the odds, as in 1 out of x, thus 2 will be a coin toss, a double to allow for slightly in favor of the house odds, 2.1
double pay = 0; //stores the payoff if you win as in x times your bet back, so 2 would be a normal bet
int test;
double results[14][10000];
double pattest = 0; //the number of patterns to test
double goodres = 0; //will store the number of good results

//time_t seconds; //should seed the random number generator
//time(&seconds);

using namespace std;

ofstream resfile; //makes our stream to output to our text file


//ofstream results;

/*
double ran(double b, double a) //returns a random number between b min, and a max
{
 double c;
 //c=double(rand() % int((a-b)+b)+1);
 c=rand() % int(a);
 
 cout<<"\n(a-b)+b)+1 = "<<((a-b)+b)+1<<", a - "<<a<<", b - "<<b<<", c - "<<c;
 return c;
}
*/

double ran(double a, double b) //returns a random number between a min, and b max
{
       int k;
       if (rand() == 138) 
       {
                  srand(rand() + clock());
       }
       
       if (rand() > rand() * 5)
       {
                  for (k = ((rand() / 1000) + (rand() % 28) + 7); k > 3; k--)
                  {
                      rand();
                  }
       }
       
 double c = 0;
 c=(rand() % int(b - a + 1)) + a;
 /*
 I wrote this forumla, basicly takes a random number from 1 - 32k, from rand and finds the remainder when divided by
 the result of the second part.  Note you subtract a, then find the remainder, then add a back.
 */
 return c;
}



void genpat() //will generate a betting pattern
{
     double sumbets = 1; //a place to store the sum of all previous bets
     for (x=1; x<9; x++) //will go through the 8 spots in the bet array
     {
         //sumbets = 1; //clears out temp so we can start totaling up the sums
         
         
         bet[x]=ran(sumbets, (sumbets + 5) * 5); //comes up with a random number with a min of the sum of the bets and the max of the sum plus 5 then times 5, trying to make the window pretty big as the huge number should just fail fast and weed themselves out anyway.
         sumbets = sumbets + bet[x]; //adding the latest bet to the sum
     }
     //now that it set 8 bets, it needs to come up with the repeater, past experience shows this should almost always be 2, but I'm going to allow it up to 5, don't want to limit it much at all.
     bet[9]=ran(1, 5);
     for (x=1; x<10; x++)
     {
         //cout<<"\n Bet "<<x<<" - "<<bet[x];
     }
}
         
         
void testpat() //will test the betting pattern
{
     double wins = 0; //will store the wins and loses (reaching goal, going broke)
     double loses = 0;
     double a = 0; //will be the result of each game
     double curbet = 0; //will store the current bet
     double numbets = 0; //will count the number of times we bet, will be used to see how long the pattern takes
     double goals = 0; //will couldnt how many times we
     double count = 0; //will count the number of tests
     double early = 0;
     //cout<<"Lost start - "<<loses;
     //cout<<"curbet "<<curbet;
     //cout<<"numbets "<<numbets;
     //system("PAUSE");
     for(count=numtests; count>0; count--) //will count down the number of tests
     {
         curm = startm; //sets your current money to the starting ammount
         //z = 0;
         
         if (test < count) 
         {
                  //cin>>test;
                  //cout<<"\n Count - "<<count<<", Wins - "<<wins<<", Loses - "<<loses;
         }
         //cout<<"\n Count - "<<count<<", Wins - "<<wins<<", Loses - "<<loses;
         for(z=0; z<1; ) //we will set z to something when you go broke or reach your goal
         {
                  //system("PAUSE");
              //cout<<"\n x - "<<x<<", y - "<<y<<", z - "<<z<<", Here Current Money - "<<curm;    
             if (curm > goalm) //tests to see if you are at your goal before placing the bet
             {
                    z=1; //1 for a win  
                    //cout<<"\nGoal  - "<<curm;
                  
             }
             else if (curm < 1) //tests to see if you are broke
             {
                  z=2; //2 for a lost
                  //cout<<"\nLost - "<<curm;
              
             }
             else //if you're not at your goal or broke then it's time to play
             {
                  if (y < 9) //if you are in the first 8 bets then you will use the next one in the pattern
                  {
                        curbet = bet[y]; //sets the bet to the next in the pattern
                  }
                  else //if you are at or above 9 then you will use the multiplier on the previous bet
                  {
                       curbet = curbet * bet[9]; //bet[9] stores the multiplier, so you are just using that
                  }
              
                  if (curm < curbet) //tests to see if you have enough money to place the next bet
                  {
                           curbet = curm;  //if you don't have enought then you will bet all that you do have
                  }
              
                  //now it's time to bet
                  //cout<<"\nCurrent Money, before bet - "<<curm;
                  //cout<<", Current Bet - "<<curbet;
                  
                  curm = curm - curbet; //places bet
                  //cout<<", Current Money, after  bet - "<<curm;
                  numbets++; //adds 1 to number of bets places this round
              
                  a = ran(1, odds); //decides if you win or lose, 1 wins, anything higher loses
                  
                  if (a == 1) //if you won
                  {
                        y = 1; //resets y to the first bet
                        curm = curm + (curbet * pay); //gives you your payoff
                        //cout<<", Win - "<<curm<<", Current bet - "<<curbet;
                  }
                  else //if you lost
                  {
                      y++; //advances to the next bet
                      //cout<<", Lose - "<<curm<<", Current bet - "<<curbet;
                          //the money was allready taken from you so no need to take it, we will check if you are broke at the begining of the next bet cycle
                  }
             }
         } 
         //since the only way to get out of the loop is to set z to something, and z only gets set when we go broke or reach our goal, we know one happened
         
         
         if(z==1) //if z is 1 then we reached our goal
         {
                 wins++; //adds 1 to number of wins
                 y = 1; //resets y to the first bet
                 //cout<<"\nWin  Count - "<<count<<", Wins - "<<wins<<", Loses - "<<loses<<", Sum - "<<wins + loses;
                 //system("PAUSE");
         }
         else if(z==2) //if z is 2 then we went broke
         {
              loses++; //adds 1 to the number of loses
              y = 1; //resets y to the first bet
              //cout<<"\nLose Count - "<<count<<", Wins - "<<wins<<", Loses - "<<loses<<", Sum - "<<wins + loses;
              //system("PAUSE");
         }
         else //shouldn't ever happen
         {
              cout<<"\nDon't know how this happened, z is equal to neither 1 or 2, here's some debug info:\n";
              cout<<"z - "<<z<<" y - "<<y<<" x - "<<x<<"\n"; //trys to help figure it out
              system("PAUSE"); //pauses so you see it
         }
         if (wins + loses == int(numtests / 100)&& loses > 40)
         {
                  early = wins / (wins + loses);
                  early = early * 100;
                  if (early < thres - 10)
                  {
                     cout<<"! ";
                     //cout<<"Wins - "<<wins<<", Loses - "<<loses<<", Sum - "<<wins+loses<<", % - "<<wins / (wins + loses) * 100<<", Early - "<<early;
                     //if (fabs((wins / (wins + loses) * 100) - early) > 10) cout<<" *";
                     count = 0;
                  }
         }

     }//moves on the the next round
     
     //we will only get here once all the tests are done, so we should be able to record the results
     
     if (mode == 2) cout<<"\nWins - "<<wins<<", Loses - "<<loses<<", Sum - "<<wins+loses<<" \n ";
     //cout<<"\nthreshould - "<<thres<<", (wins / (wins + loses)) * 100) = "<<(wins / (wins + loses)) * 100<<", Early - "<<early;
     //cout<<"\nWins - "<<wins<<", Loses - "<<loses<<", Sum - "<<wins+loses<<", % - "<<wins / (wins + loses) * 100<<", Early - "<<early;
     //if (fabs((wins / (wins + loses) * 100) - early) > 10) cout<<" *";
     if (thres < (wins / (wins + loses)) * 100) //tests to see if the number of wins was above threshold
     {
               
               
               
               //cout<<"Should write here";
               
               
               goodres++;
               
               
               //results[1][int(goodres)] = startm;
               //results[2][int(goodres)] = goalm;
               //results[3][int(goodres)] = wins;
               //results[4][int(goodres)] = loses; 
               
               resfile << goodres<<", ";
               resfile << startm<<", ";
               resfile << goalm<<", ";
               resfile << wins<<", ";
               resfile << loses<<", "; 
               
               cout<<"\nGood result # "<<goodres<<" of "<<pattest<<" - ";
               cout<<startm<<", ";
               cout<<goalm<<", ";
               cout<<wins<<", ";
               cout<<loses<<", ";
               for (x=1;x<10;x++) 
               {
                   //results[x + 4][int(goodres)] = bet[x];
                   cout<<bet[x]<<", ";
                   resfile << bet[x]<<", ";
               }
               resfile << "\n";
               
               //cout<<"\nNumber of good results - "<<goodres<<", out of "<<pattest;
               
               //resfile.close(); //closes file
     }
//we could put and else here to do something with the results that didn't meet the threshold, but for now nothing.

//and we are done


    
}

void recordresults()
{
     for (x=int(goodres); x>0; x--) //this will display the results
     {
         cout<<"\nPattern # "<<x<<" - "; 
         for(y=1; y <14; y++)
         {
                  cout<<results[y][x]<<", ";
         }
     }
     system("PAUSE");
}

int main(int argc, char *argv[])
{
     time_t seconds; //should seed the random number generator
     time(&seconds);
     srand((unsigned int) seconds);
     double timetest;
     timetest = clock();
     
     cout<<"\nSeed "<<seconds<<", timetest - "<<timetest;
     

    //ofstream file; //opens our results.csv file for the first time, and makes the first row, with the titles
    resfile.open("results.csv");
    
    //file.open("results.csv"); //opens results.csv to put our results in
    resfile << "Result #,Start Money,Goal Money,Wins,Loses,Bet 1,Bet 2,Bet 3,Bet 4,Bet 5,Bet 6,Bet 7,Bet 8,Multiplier\n";
    
    //resfile.close();
    
    //This whole block will get the various varibles
    
    cout<<"\nEnter the starting money, then goal money. ";
    cin>>startm>>goalm; //getting the starting and goal money
    if (startm == 0) startm = 50000;
    if (goalm == 0) goalm = 60000;
    cout<<"\nEnter the odds followed by the payoff, odds are in 1 out of x form, payoff is x times your bet, 2 is normal for both.";
    cin>>odds>>pay;
    if (odds == 0) odds = 2;
    if (pay == 0) pay = 2;
    cout<<"\nEnter the number of times to test each betting pattern before recording results. ";
    cin>>numtests; //getting the number of times to test each pattern
    if (numtests == 0) numtests = 10000;
    cout<<"\nDo you want automatic of manual mode 1 - Auto, 2 - Manual? ";
    cin>>mode; //setting auto or manual mode
    if (mode == 0) mode = 1;
    cout<<"\nEnter the threshold, as a percentage. ";
    cin>>thres; //getting the threshold
    if (thres == 0) thres = 80;
    cout<<"\nEnter the number of patterns to test. ";
    cin>>pattest; //getting the number of patterns to test
    if (pattest == 0) pattest = 300000;
    
    //end getting the varibles
    //Displaying the varibles
    cout<<"\nStaring money - "<<startm<<", goal money - "<<goalm<<", odds 1 in "<<odds<<", payoff bet x "<<pay<<", number of tests - "<<numtests;
    cout<<"\nMode - "<<mode<<", threshold - "<<thres<<", number of patterns to test - "<<pattest;
    
    
    timetest = clock();
    cout<<"\nSeed "<<seconds<<", timetest - "<<timetest;
    //cout<<"\n exp "<<exp(2);
    //for (x=int(goodres); x>0; x--)
    if (mode == 1) cout<<"\nTesting...\n";
    for (; int(goodres) < pattest; )
    {
        
    
        if (mode == 1) //if it's auto mode then generate a pattern
        {
              genpat();
        }    
        else //if it's not auto then ask for the pattern
        {
              cout<<"\nEnter eight bets, then a multiplier.\n";
              for (x=1; x<10; x++) //gets 8 bets then the last number will be the multiplier
              {
              if (x>8)
                  {
                     cout<<"And now the multiplier.\n";
                  }
                  cin>>bet[x];
                  if (bet[1] == 138) 
                  {
                             for (x=1; x<9; x++)
                             {
                                 bet[x] =  pow(2,(x-1));
                                 //cout<<" Bet # "<<x<<" is "<<bet[x];
                             }
                             bet[9] = 2;
                  }

              }
              cout<<"\nTesting...\n";   
        }
    
        //now we have either the computer generated pattern, or the user one, reguardless we can test it
        
        testpat();
        if (mode == 2) recordresults();
        
    }
    
    //if we left the loop then we have the number of patterns above the threshold that we wanted, so we can record them.
    
    recordresults();
    
    /*
    ofstream results;
    results.open("results.csv");
    results << "Text\n";
    results << x;
    results << y;
    results << z;
    results.close();
    */
    
    resfile.close();
    system("PAUSE");
    return EXIT_SUCCESS;
}
