I need to open new counter when old one closes

I am making a larger program that has the following part:
I will avoid putting the larger one and work out how the solution to this problem applies to that one.

Here, I have four tables/counters who count the number of customers in line.
I hope the comments help to understand.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
#include<iostream>
#include<conio.h>
using namespace std;


int main()
{
	int a=0,b=0,c=0,d=0;  //The four counters
	int flag[3];  //The array that keeps track whether they are open or closed
	int full[3];  //The array that keeps track whether they are full yet. (Full at 10)
	flag[0]=1;    //Initially 2 counters are open
	flag[1]=1;
	for(int m=0;m<=3;m++)   //Initially all counters are not full
	{
		full[m]=0;
	}   
	for(;;)
	{
		char name;
		cout<<"Enter counter name: \n";
		cin>>name;
		switch(name)
                {//this code is given below}

        cout<<"\n The tally: \n ";   //This part is just for reference or debugging so you guys understand the output
		cout<<" \t a \t "<<a<<endl; //I don't need to display output in my original program
		cout<<" \t b \t "<<b<<endl;
		cout<<" \t c \t "<<c<<endl;
		cout<<" \t d \t "<<d<<endl;
         }
             //The activator code goes here 


What I need to do is open the third counter 'c' when either of the initial counters are full. What I did in the switch case was this:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
switch(name){
			case 'a':
				{
					if(flag[0]==1)   //Only if counter is open
					{
						a++;
						if(a==10)
						{
							flag[0]=0;		//Close counter 
							full[0]=1;		//Counter is full
						}							
					}
					else			//If counter is closed
					{
						cout<<"Counter closed. \n ";  
					}
					break;
				}
			case 'b':
				{
					if(flag[1]==1)		//Only if counter is open
					{
						b++;
						if(1==10)
						{
							flag[1]=0;
							full[1]=1;
						}
					}
					else
					{
						cout<<"Counter closed. ";
					}
					break;
				}
			case 'c':
				{
					if(flag[2]==1) //Only if counter is open
					{
						c++;
						if(c==10)
						{
							flag[2]=0;
							full[2]=1;
						}
					}
					else
					{
						cout<<"Counter closed. ";
					}
					break;
				}
			case 'd':
				{
					if(flag[3]==1)   //Only if counter is open
					{
						d++;
						if(d==10)
						{
							flag[3]=0;
							full[3]=1;
						}
					}
					else
					{
						cout<<"Counter closed. ";
					}
					break;
				}			
		}


So the flag for any counter goes 0 as soon as it becomes full.
So I figured I could check all the counters if one of them is full, and open a counter which is not full.

so, the activator code given above is like,
1
2
3
4
if(full[0]==1 || full[1]==1)
{
    flag[2]==1;
}


Also, I need to check if 2 out of 3 counters are full and open another one which is not full.

If 3 out of 4 counters are full, do nothing.

How do I make it a bit more smooth? Say I have like 100 counters, I need to check everyone to see if say, 'n' are full, then search for the first unopened counter and open it.

An interesting twist is when I included decrementers (in my larger program), so now the counters can decrease and go back to zero.
example:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
case 'a':
				{
					if(a!=0)   //Only if counter is not empty
					{
						--a;
						if(a==0)
						{
							flag[0]=0;		//Close counter 
							full[0]=0;		//Counter is empty
						}							
					}
					else			//If counter is closed
					{
						cout<<"Counter closed. \n ";  
					}
					break;


So now, let's say at some point int the program, counters 'b' and 'c' are open, and 'b' gets full, I want to open 'a' again, not 'd'.

How do I do THAT?
start from the beginning of the list each time and pick the first candidate that can be opened.
if you do that, you get a, not d. check if its closed to find the candidate.

I assume you want this kind of logic..
a opens, a gets full, b opens, b and a are full so c opens, a becomes empty and closes, then b and c become full, and you open a again.


your switch repeats code with slight changes, looks like it should be made a function. Try not to repeat blocks of code generally, if you know about functions already.

c++ basic type boolean with values of true and false are better than using an int for this purpose.
bool flag = true;
flag = false;
if(flag)
etc
Last edited on
So I should replace the cases with functions that increment/decrement stuff... okay. But in my original problem, the counters are actually objects in an array. So I need to use references to objects?

I honestly am at a loss about references. Help me how I could pass an array of objects like
 
int counter[3];

to a function in switch case?

start from the beginning of the list each time and pick the first candidate that can be opened


I know that, but I need to check if they are full or not, then only check for unopened ones. How do I do that?

I assume you want this kind of logic..
a opens, a gets full, b opens, b and a are full so c opens, a becomes empty and closes, then b and c become full, and you open a again.


Um, no. 'a' and 'b' are already open, and the condition is that AT LEAST TWO MUST BE OPEN AT A TIME.

Now, if 'a' and 'b' are initial ones, 'a' gets full, 'c' opens, 'c' obtains some customers.

But 'a' loses some customers, then all 3 are open (because you can't refuse customers already in line and tell them to go elsewhere).

Now, if 'a' and 'c' get full, SINCE THE AT LEAST TWO RULE is violated, open 'd'.



@The Brahmnic Boy

I'm surprised that no one mentioned that your array size is too small. ( Unless I missed it in their text responses ).

You are looking at 4 flag[] and 4 full[] array locations. flag[0], flag[1], flag[2] and flag[3], and the same for full[]. So, you should change lines 9 and 10 in the first post, to
1
2
  int flag[4];  //The array that keeps track whether they are open or closed
   int full[4];  //The array that keeps track whether they are full yet. (Full at 10) 
void foo(int * ip, int size)
{
code...
}

int x[3];
foo(x,3); //pass it like this ]
^^ the above highlights why <vector> is awesome. if you can use vectors, do so.

arrays/pointers ... the data inside them is as if by reference: if you change x[1] = 11 in foo, it is changed in main too. Its another topic but it is critical to understand this following really small example...

void foo(int *& a)
{a = new int[3];} //a is a pointer, and it is passed by reference, so you are allowed to change the pointer itself, not just what is pointed TO. Here, we change it by getting memory for it.

void foo(int *a)
{
a = new int[3]; //a will revert back to null or whatever it was passed in as after foo is done..
}

and as above, the thing pointed TO is not governed by the reference or not of the pointer itself. the data under the pointer is modified by whoever goes to that memory block and changes it.

--------
I know that, but I need to check if they are full or not, then only check for unopened ones. How do I do that?

its still iteration.
for all the counters
result += is it {not full and open}

if result == 0
you need to open the first one available.
for all the counters, if closed, open it and reset it (if necessary?).

you need to work your rule of 2 logic into that as well. If it does not meet the rule of 2 logic you open one in that case too.
and you need similar reversed logic to close one ...
for all the counters
if counter is empty
if (pretend to close empty counter) means rule of 2 is still OK then close it.

take this easy.. do it explicitly, with extra loops and extra work and get it all down and working. It can be done in a lot less work but it will be convoluted to condense the logic down this far. You need to see it spelled out first, then if you want to play at making it tight we can do that after. Its complex, and a lot of logic.. you need to manage rule of 2 and who is open and who is full and what can be closed and what needs to be opened. Break it apart and work though that logic with explicit, simple to read and work with code.

Last edited on
Topic archived. No new replies allowed.