-2

So I'm making a program that assorts moving cars on a traffic light system. It sorts cars by north, east, south, west and moves in a clockwise order. I'm encountering a problem where I implement a goto and a reset to the counter that is a measure of how many cars will be able to pass through on a given run.

I have tried setting the goto to a different place, re arranging how it assorts my vector and check for the index and also trying to spot where the counter reset might not work. This program runs on a linux server and uses a child, and parent process.

#include <iostream>
#include <vector>
#include <queue>
#include <unistd.h>
#include <sys/wait.h>

//Jeremy Bayangos - 1646316
//OS Class - Castro - Mon/Wed
//COSC3613
using namespace std;

struct cars
{
   string name;
   char dr;
   int t;
};
bool init(vector<cars> &arr, char direct) {
   if (!arr.empty())
      for (vector<cars>::size_type i = 0; i < arr.size(); ++i) {
         if (arr.at(i).dr == direct) {
            return true;
         }
      } return false;
}
int direct_counter(vector<cars> &arr, char n)
{
   int count = 0;
   if (!arr.empty())
      for (int i = 0; i < arr.size(); ++i) {
         if (arr.at(i).dr == n) {
            count++;
         }
      } return count;

}
char direct_bound(char e)
{
   if (e == 'E')
   {
      cout << "Current direction: Eastbound" << endl;
   }
   if (e == 'S')
   {
      cout << "Current direction: Southbound" << endl;
   }
   if (e == 'W')
   {
      cout << "Current direction: Westbound" << endl;
   }
   if (e == 'N')
   {
      cout << "Current direction: Northbound" << endl;
   }
}
char direct_shift(char e)
{
   if (e == 'N')
   {
      return 'E';
   }
   else if (e == 'E')
   {
      return 'S';
   }
   else if (e == 'S')
   {
      return 'W';
   }
   else if (e == 'W')
   {
      return 'N';
   }
   else
   {
      return '\0';
   }
}


int main() {

   vector <cars> keeper;
   queue <cars> que;

   char track;  //starting direction
   int car_num; //starting car num

   string plate;
   char dir;
   int sec;
   cin >> track;
   cin >> car_num;


   while (cin >> plate >> dir >> sec) //takes the input of plate, 
      direction and time
      {
         cars temp;
         temp.name = plate;
         temp.dr = dir;
         temp.t = sec;
         keeper.push_back(temp);
      }
   char curr_dir = track;
   int counter = 0;
   while (not keeper.empty())
   {
      for (auto i = 0; i < keeper.size(); i++) {
truckstop:
         if (init(keeper, curr_dir))//if directions is inside 
            vector
            {
               if (keeper.at(i).dr == curr_dir)// if current 
                  direction its facing is correct
                  {
                     if (car_num == 1 or 
                         direct_counter(keeper, curr_dir == 1))
                     {
                        que.push(keeper[i]); //pushes 
                        vector at i into queue
                           keeper.erase(keeper.begin() + 
                                        i); // deletes vector at index i
                        curr_dir = 
                           direct_shift(curr_dir);
                        counter = 0;
                        break;
                     }
                     else if (car_num > 1) {
                        que.push(keeper[i]); //pushes 
                        vector at i into queue
                           keeper.erase(keeper.begin() + 
                                        i); // deletes vector at index i
                        counter++;
                        if (counter == car_num) {
                           curr_dir = 
                              direct_shift(curr_dir);
                           counter = 0;
                           break;
                        }
                        else {
                           counter = 0;
                           goto truckstop;
                        }

                     }
                  }
            }
         else
         {
            curr_dir = direct_shift(curr_dir);
            goto truckstop;
         }
      }
   }

   int pid;
   char d1 = que.front().dr;
   char d2;
   while (not que.empty())
   {
      if (d1 != d2)
      {
         direct_bound(que.front().dr);
      }
      if ((pid = fork() == 0))
      {
         cout << "Car " << que.front().name << " is using the 
            intersection for " <<
            que.front().t << " sec(s)." << endl;
         sleep(que.front().t);
         exit(0);
      }
      else
      {
         d1 = que.front().dr;
         wait(0);
         que.pop();
         if (not que.empty())
         {
            d2 = que.front().dr;
         }
      }
   }
   return 0;

}
R Sahu
  • 204,454
  • 14
  • 159
  • 270
Jeremy S Nero
  • 45
  • 1
  • 7
  • 1
    Unrelated, but do have a read through [What is wrong with goto?](https://stackoverflow.com/questions/3517726/what-is-wrong-with-using-goto) – TrebledJ Feb 19 '19 at 03:36
  • My usage of goto was just a recommendation from someone, if you have better suggestions then please help so. – Jeremy S Nero Feb 19 '19 at 03:41
  • 5
    Well, that recommendation was ill-advised. Rewrite your code to use proper structured constructs such as `do-while`, etc. – PaulMcKenzie Feb 19 '19 at 03:43
  • Please provide a [mcve]. – Passer By Feb 19 '19 at 04:58
  • 1
    You rubber duck wants to know what `direct_bound` returns. – user4581301 Feb 19 '19 at 06:43
  • 1
    To replace the `goto` use `continue` and chose a better location for the `i++` that's currently in the `for` loop's iteration expression. `goto` "evil" because it has to be used with extreme care. And even when you do use it correctly, it raises a lot of questions from people who look at your code. It's not worth defending the choice to use it in a code review if a regular construct is available. – user4581301 Feb 19 '19 at 07:01

1 Answers1

0

You access the 'que' from parent and child process without synchronization and that can lead to unpredictable results. I'd suggest to first implement your logic without 'fork'.

J.R.
  • 1,880
  • 8
  • 16