// File: RaceCourse.cpp // // Written by Richard Chang for CMSC202 Spring 2007 // #include #include //#include "Car.h" #include "RaceCourse.h" using namespace std ; // ---------------------------------------------------- // --------------------- Local Types ------------------ // // THINGs in the RaceCourse that are not Cars. // enum THING { WALL = -1, SPACE = 0 } ; // ---------------------------------------------------- // --------------------- Constructors ----------------- // RaceCourse::RaceCourse() { // do nothing Status = WAITING ; } RaceCourse::RaceCourse(unsigned int r, unsigned int c, unsigned int n, const vector& obs) { rows = r ; // could have used member initializers cols = c ; cars = n ; Status = WAITING ; // Make walls around the perimeter for (unsigned int i=0 ; i <= cols+1 ; i++) { Course[0][i] = WALL ; Course[rows+1][i] = WALL ; } for (unsigned int i=0 ; i <= rows+1 ; i++) { Course[i][0] = WALL ; Course[i][cols+1] = WALL ; } // Fill race course with spaces for (unsigned int i=1 ; i<=rows ; i++) { for (unsigned int j = 1 ; j<=cols ;j++) { Course[i][j] = SPACE ; } } // Initialize each car for (unsigned int i = 1 ; i <= cars ; i++) { CarList[i] = Car(this, i, InitialFuelLevel) ; CarPos[i].row = 1 ; CarPos[i].col = i ; Course[1][i] = i ; } // Install obstacles unsigned int x, y ; for (unsigned int i=0 ; i < obs.size() ; i++) { x = obs[i].row ; y = obs[i].col ; // Check that there's nothing there assert((1 <= x) && (x <= rows)) ; assert((1 <= y) && (y <= cols)) ; assert(Course[x][y] == SPACE) ; Course[x][y] = WALL ; } } Car * RaceCourse::GetCar(unsigned int i) { assert( (1 <= i) && (i <= cars) ) ; return &(CarList[i]) ; } unsigned int RaceCourse::GetNumOfCars() const { return cars ; } unsigned int RaceCourse::GetNumOfRows() const { return rows ; } unsigned int RaceCourse::GetNumOfCols() const { return cols ; } void RaceCourse::StartRace() { Status = STARTED ; Winner = 0 ; } RaceStatus RaceCourse::GetRaceStatus() { if (Status != STARTED) return Status ; for (unsigned int i=1 ; i <= cars ; i++) { if (CarList[i].GetFuelLevel() > 0) return STARTED ; } return Status = STALEMATE ; } // Used by PrettyPrintCourse() // void RaceCourse::PrintRaceStatus() { RaceStatus s ; s = GetRaceStatus() ; switch(s) { case WAITING : cout << "Status: WAITING\n" ; break ; case STARTED : cout << "Status: STARTED\n" ; break ; case FINISHED : cout << "Status: FINISHED\n" ; break ; case STALEMATE : cout << "Status: STALEMATE\n" ; break ; default: cout << "Status: UNKNOWN (Bad)\n" ; } } unsigned int RaceCourse::GetWinner() const { return Winner ; } void RaceCourse::PrettyPrintCourse() { unsigned int i, j ; int thing ; for (i = 0 ; i <= rows+1 ; i++) { for (j = 0 ; j <= cols+1 ; j++) { thing = Course[i][j] ; if (thing == WALL) { cout << "#" ; } else if (thing == SPACE) { cout << "."; } else { cout << thing ; } } cout << endl ; } PrintRaceStatus() ; } // facilitator for Car objects to call. // max = maximum number of steps to move. // xinc = -1, 0, +1 change in rows // yinc = -1, 0, +1 change in cols // Setting xinc and yinc allows Cars to specify // the direction (left, right, up or down) that they want to move. // unsigned int RaceCourse::MoveMe( unsigned int CarIndex, unsigned int max, int xinc, int yinc) { unsigned int steps ; unsigned int x, y ; RaceStatus s ; assert((1 <= CarIndex) && (CarIndex <= cars)) ; assert((xinc == 0) || (yinc == 0)) ; assert((-1 <= xinc) && (xinc <= 1)) ; assert((-1 <= yinc) && (yinc <= 1)) ; s = GetRaceStatus() ; // actually computes STALEMATE possibility if (s != STARTED) return 0 ; steps = 0 ; x = CarPos[CarIndex].row ; // OK, maybe x should be the col number y = CarPos[CarIndex].col ; // cout << "Debug: (x,y) = (" << x << "," << y << ")\n" ; Course[x][y] = SPACE ; // Keep going in the specified direction until // we run out of gas or hit something. // while ((steps < max) && (Course[x+xinc][y+yinc] == SPACE)) { steps++ ; x += xinc ; y += yinc ; // cout << "Debug: (x,y) = (" << x << "," << y << ")\n" ; } // Update Car's position. // CarPos[CarIndex].row = x ; CarPos[CarIndex].col = y ; Course[x][y] = CarIndex ; if ((x == rows) && (y == 1)) { Status = FINISHED ; Winner = CarIndex ; } return steps ; } // Returns the Position of the Car specified by CarIndex // Position RaceCourse::GetMyPosition(unsigned int CarIndex) const { assert((1 <= CarIndex) && (CarIndex <= cars)) ; return CarPos[CarIndex] ; }