New to multithreading

So i'm trying to set up multi-threading on a program and i can't get it to run my function. Any help would be appreciated on line 50. The function runs fine without using thread t1;

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
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
  #include <iostream>
#include <string>
#include <cstdlib>
#include <time.h> 
#include <windows.h>
#include <thread>

#include "cs132_JPDRoomba_sucky02_Environment.h"
#include "cs132_JPDRoomba_sucky02_FloorSensor.h"
#include "cs132_JPDRoomba_sucky02_BumperSensor.h"
#include "cs132_JPDRoomba_sucky02_Sensor.h"
#include "cs132_JPDRoomba_sucky02_DirtSensor.h"
#include "cs132_JPDRoomba_sucky02_CentralOperations.h"
#include "cs132_JPDRoomba_sucky02_Display.h"

#include "cs132_SeaMonkeys_sucky02_Zone.h"
#include "cs132_SeaMonkeys_sucky02_Room.h"



using namespace std;

void sounds();

//Generates new map and positions Roomba and base on map. Saves display onto a file and outputs display in console window.
void main()
{
	//seed the random number generator
	srand(unsigned(time(NULL)));

	
	Environment *e = new Environment;
	CentralOperations *c = new CentralOperations;
	DirtSensor *d = new DirtSensor;
	FloorSensor *f = new FloorSensor;
	ProximitySensor *p = new ProximitySensor;
	Sensor *s = new Sensor;
	Zone *z = new Zone;
	Room *r = new Room;

	e->makeLoadDisplayEnvironment();
	cout << endl << endl << endl;
	r->printRoomFloor(*e);
	r->printRoomMess(*e);
	cout << endl;
	cout << "Press Enter for Automatic Vacuuming!" << endl;
	system("pause");

	thread t2 (sounds);
	thread t1 (c->run, *e, *d, *s, *f, *p, *r);

	/*try
	{
		thread t1 (c->run,*e, *d, *s, *f, *p, *r);
	}
	catch (CentralOperations::ErrorFound)
	{
		cout << "Error found...Closing program" << endl;
	}
		*/
	e->deletion();

	delete d;
	delete s;
	delete f;
	delete p;
	delete r;
	delete z;

	system("pause");
}

void sounds()
{
	Beep(330, 100); Sleep(100);
	Beep(330, 100); Sleep(300);
	Beep(330, 100); Sleep(300);
	Beep(262, 100); Sleep(100);
	Beep(330, 100); Sleep(300);
	Beep(392, 100); Sleep(700);
	Beep(196, 100); Sleep(700);
	Beep(262, 300); Sleep(300);
	Beep(196, 300); Sleep(300);
	Beep(164, 300); Sleep(300);
	Beep(220, 300); Sleep(100);
	Beep(246, 100); Sleep(300);
	Beep(233, 200);
	Beep(220, 100); Sleep(300);
	Beep(196, 100); Sleep(150);
	Beep(330, 100); Sleep(150);
	Beep(392, 100); Sleep(150);
	Beep(440, 100); Sleep(300);
	Beep(349, 100); Sleep(100);
	Beep(392, 100); Sleep(300);
	Beep(330, 100); Sleep(300);
	Beep(262, 100); Sleep(100);
	Beep(294, 100); Sleep(100);
	Beep(247, 100); Sleep(500);
	Beep(262, 300); Sleep(300);
	Beep(196, 300); Sleep(300);
	Beep(164, 300); Sleep(300);
	Beep(220, 300); Sleep(100);
	Beep(246, 100); Sleep(300);
	Beep(233, 200);
	Beep(220, 100); Sleep(300);
	Beep(196, 100); Sleep(150);
	Beep(330, 100); Sleep(150);
	Beep(392, 100); Sleep(150);
	Beep(440, 100); Sleep(300);
	Beep(349, 100); Sleep(100);
	Beep(392, 100); Sleep(300);
	Beep(330, 100); Sleep(300);
	Beep(262, 100); Sleep(100);
	Beep(294, 100); Sleep(100);
	Beep(247, 100); Sleep(900);
	Beep(392, 100); Sleep(100);
	Beep(370, 100); Sleep(100);
	Beep(349, 100); Sleep(100);
	Beep(311, 100); Sleep(300);
	Beep(330, 100); Sleep(300);
	Beep(207, 100); Sleep(100);
	Beep(220, 100); Sleep(100);
	Beep(262, 100); Sleep(300);
	Beep(220, 100); Sleep(100);
	Beep(262, 100); Sleep(100);
	Beep(294, 100); Sleep(500);
	Beep(392, 100); Sleep(100);
	Beep(370, 100); Sleep(100);
	Beep(349, 100); Sleep(100);
	Beep(311, 100); Sleep(300);
	Beep(330, 100); Sleep(300);
	Beep(523, 100); Sleep(300);
	Beep(523, 100); Sleep(100);
	Beep(523, 100); Sleep(1100);
	Beep(392, 100); Sleep(100);
	Beep(370, 100); Sleep(100);
	Beep(349, 100); Sleep(100);
	Beep(311, 100); Sleep(300);
	Beep(330, 100); Sleep(300);
	Beep(207, 100); Sleep(100);
	Beep(220, 100); Sleep(100);
	Beep(262, 100); Sleep(300);
	Beep(220, 100); Sleep(100);
	Beep(262, 100); Sleep(100);
	Beep(294, 100); Sleep(500);
	Beep(311, 300); Sleep(300);
	Beep(296, 300); Sleep(300);
	Beep(262, 300); Sleep(1300);
	Beep(262, 100); Sleep(100);
	Beep(262, 100); Sleep(300);
	Beep(262, 100); Sleep(300);
	Beep(262, 100); Sleep(100);
	Beep(294, 100); Sleep(300);
	Beep(330, 200); Sleep(50);
	Beep(262, 200); Sleep(50);
	Beep(220, 200); Sleep(50);
	Beep(196, 100); Sleep(700);
	Beep(262, 100); Sleep(100);
	Beep(262, 100); Sleep(300);
	Beep(262, 100); Sleep(300);
	Beep(262, 100); Sleep(100);
	Beep(294, 100); Sleep(100);
	Beep(330, 100); Sleep(700);
	Beep(440, 100); Sleep(300);
	Beep(392, 100); Sleep(500);
	Beep(262, 100); Sleep(100);
	Beep(262, 100); Sleep(300);
	Beep(262, 100); Sleep(300);
	Beep(262, 100); Sleep(100);
	Beep(294, 100); Sleep(300);
	Beep(330, 200); Sleep(50);
	Beep(262, 200); Sleep(50);
	Beep(220, 200); Sleep(50);
	Beep(196, 100); Sleep(700);
	/*Intro*/
	Beep(330, 100); Sleep(100);
	Beep(330, 100); Sleep(300);
	Beep(330, 100); Sleep(300);
	Beep(262, 100); Sleep(100);
	Beep(330, 100); Sleep(300);
	Beep(392, 100); Sleep(700);
	Beep(196, 100); Sleep(700);
	Beep(196, 100); Sleep(125);
	Beep(262, 100); Sleep(125);
	Beep(330, 100); Sleep(125);
	Beep(392, 100); Sleep(125);
	Beep(523, 100); Sleep(125);
	Beep(660, 100); Sleep(125);
	Beep(784, 100); Sleep(575);
	Beep(660, 100); Sleep(575);
	Beep(207, 100); Sleep(125);
	Beep(262, 100); Sleep(125);
	Beep(311, 100); Sleep(125);
	Beep(415, 100); Sleep(125);
	Beep(523, 100); Sleep(125);
	Beep(622, 100); Sleep(125);
	Beep(830, 100); Sleep(575);
	Beep(622, 100); Sleep(575);
	Beep(233, 100); Sleep(125);
	Beep(294, 100); Sleep(125);
	Beep(349, 100); Sleep(125);
	Beep(466, 100); Sleep(125);
	Beep(587, 100); Sleep(125);
	Beep(698, 100); Sleep(125);
	Beep(932, 100); Sleep(575);
	Beep(932, 100); Sleep(125);
	Beep(932, 100); Sleep(125);
	Beep(932, 100); Sleep(125);
	Beep(1046, 675);

}
Last edited on
closed account (SECMoG1T)
Did your program compile? your need either to join or detach your threads otherwise your program should terminate.

Also these is risk you just don't do this without additional synchronization
1
2
3
4
5
6
7
8
e->deletion();

	delete d;
	delete s;
	delete f;
	delete p;
	delete r;
	delete z;


Your main thread might get here even before this thread 't1' accomplishes anything
 
	thread t1 (c->run, *e, *d, *s, *f, *p, *r);

leaving it to use invalid pointers , i would rather pass copies of objects to this thread coz using pointers might prove difficult , the additional synchronization required here to avoid data races is way higher as compared to passing the thread copies of the objects.
Last edited on
It never compiled. I get the error: error C3867: 'CentralOperations::run': function call missing argument list; use '&CentralOperations::run' to create a pointer to member
Am i passing my parameters to my function correctly? I have changed my variables to static except for Environment e because that needs to be dynamic.
closed account (SECMoG1T)
1
2
	thread t1 (c->run, *e, *d, *s, *f, *p, *r);	[/code ]
you should pass  a function pointer to a thread [code]&c->run
but that is just one error , i have also updated my previous post with some do's and don'ts .
Last edited on
It's not letting me do this:

thread t2 (&c.run,*e, d, s, f, p, r);
Last edited on
closed account (SECMoG1T)
but your variable c is a pointer so using '.' is illegal use '->' operator , would you post the definition of your function 'run' just to be sure.
its kinda long...it's in a different class though
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
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
void run(Environment e, DirtSensor d, Sensor s, FloorSensor f, ProximitySensor p, Room r)
	{
		f.setBareFloor(0);
		f.setLowPileCarpetFloor(0);
		f.setHighPileCarpetFloor(0);

		d.setDirtBin();
		while ((batteryCharge > 500) && (d.getDirtBin() < 97) && (!e.getError()))
		{
			speed = 100;
			p.proximitySensor(e);

			if (d.checkDirt(e))
			{
				e.setBlockCode(0, 0, e.getBlockCode(0, 0, e.getEnv()) - 1, e.getEnv());
				d.setDirtBin();
				d.dirtBinSensor();

				if (f.checkFloor(e) == 1)
				{
					drainBattery(7);
				}

				else
				{
					drainBattery(4);
				}
			}

			while ((p.getSpacesForward()[1] == 0) || ((p.getSpacesForward()[1] == 11 || (p.getSpacesForward()[1] == 12))))
			{
				e.helperRandomOrientation();
				p.proximitySensor(e);
			}

			if ((p.getSpacesForward()[2] == 0) || (p.getSpacesForward()[2] == 11) || (p.getSpacesForward()[2] == 12))
			{
				speed = 50;
			}
			else
			{
				speed = 100;
			}

			for (int i = 0; i < 2; i++)
			{
				e.moveHelperPos();
				if (suction == 70)
				{
					drainBattery(7);
				}
				else
				{
					drainBattery(4);
				}
				if (i < 1 && speed == 50)
				{
					//system("pause");
					system("cls");
					e.showEnvironment(e.getHeight(), e.getWidth(), e.getEnv());
					e.saveEnvironment(e.getHeight(), e.getWidth(), e.getFirst(), e.getEnv());
					disp.set(getSuction(), f.getElevation(), getBatteryCharge(), d.getDirtBin(), e.getError(), getSpeed(), e.getFirst());
					disp.setDisplay();
					disp.updateDisplay();
					r.printRoomFloor(e);
					r.printRoomMess(e);
					//system("pause");
					
					//e.loadOriginal(e.getHeight(), e.getWidth(), e.getEnv(), getSuction(), f.getElevation(), getBatteryCharge(), d.getDirtBin(), e.getError(), getSpeed());
					//system("pause");
				}
			}

			if (f.checkFloor(e) == 1)
			{
				f.amountOf(1);
				suction = 40;
				f.setElevation(0);
			}

			if (f.checkFloor(e) == 2)
			{
				f.amountOf(2);
				suction = 70;
				f.setElevation(1);
			}

			else
			{
				f.amountOf(3);
				f.setElevation(2);
			}


			int errChance = 500000;
			if (errChance == 420)
			{
				e.setError(true);
				checkError(420);
			}



			//system("pause");
			system("cls");
			e.showEnvironment(e.getHeight(), e.getWidth(), e.getEnv());
			e.saveEnvironment(e.getHeight(), e.getWidth(), e.getFirst(), e.getEnv());
			disp.set(getSuction(), f.getElevation(), getBatteryCharge(), d.getDirtBin(), e.getError(), getSpeed(), e.getFirst());
			disp.setDisplay();
			disp.updateDisplay();
			r.printRoomFloor(e);
			r.printRoomMess(e);
			
			//e.loadOriginal(e.getHeight(), e.getWidth(), e.getEnv(), getSuction(), f.getElevation(), getBatteryCharge(), d.getDirtBin(), e.getError(), getSpeed());
			
			
		}

		do
		{
			p.proximitySensor(e);
			suction = 40;
			speed = 100;

			if (e.getHelperPosition()[0] > e.getBasePosition()[0])
			{
				e.setHelperOrientation(0, -1);
			}

			else if (e.getHelperPosition()[0] < e.getBasePosition()[0])
			{
				e.setHelperOrientation(0, 1);
			}

			if (e.getHelperPosition()[1] > e.getBasePosition()[1])
			{
				e.setHelperOrientation(1, -1);
			}

			else if (e.getHelperPosition()[1] < e.getBasePosition()[1])
			{
				e.setHelperOrientation(1, 1);
			}


			while ((p.getSpacesForward()[1] == 0) || (p.getSpacesForward()[1] == 11) || (p.getSpacesForward()[1] == 12))
			{
				e.helperRandomOrientation();
				p.proximitySensor(e);
			}

			if ((p.getSpacesForward()[3] == 0) || (p.getSpacesForward()[3] == 11) || (p.getSpacesForward()[3] == 12))
			{
				speed = 50;
			}

			else
			{
				speed = 100;
			}

			for (int i = 0; i < 2; i++)
			{
				e.moveHelperPos();
				drainBattery(4);
				if (i < 1 && speed == 50)
				{
					//system("pause");
					system("cls");
					e.showEnvironment(e.getHeight(), e.getWidth(), e.getEnv());
					e.saveEnvironment(e.getHeight(), e.getWidth(), e.getFirst(), e.getEnv());
					disp.set(getSuction(), f.getElevation(), getBatteryCharge(), d.getDirtBin(), e.getError(), getSpeed(), e.getFirst());
					disp.setDisplay();
					disp.updateDisplay();
					r.printRoomFloor(e);
					r.printRoomMess(e);
					
					//e.loadOriginal(e.getHeight(), e.getWidth(), e.getEnv(), getSuction(), f.getElevation(), getBatteryCharge(), d.getDirtBin(), e.getError(), getSpeed());
					
					
				}
			}
			//system("pause");
			system("cls");
			e.showEnvironment(e.getHeight(), e.getWidth(), e.getEnv());
			e.saveEnvironment(e.getHeight(), e.getWidth(), e.getFirst(), e.getEnv());
			disp.set(getSuction(), f.getElevation(), getBatteryCharge(), d.getDirtBin(), e.getError(), getSpeed(), e.getFirst());
			disp.setDisplay();
			disp.updateDisplay();
			r.printRoomFloor(e);
			r.printRoomMess(e);
			
			//e.loadOriginal(e.getHeight(), e.getWidth(), e.getEnv(), getSuction(), f.getElevation(), getBatteryCharge(), d.getDirtBin(), e.getError(), getSpeed());
		
			

		} while ((getBatteryCharge() > 0 && (e.getHelperPosition()[0] != e.getBasePosition()[0])) || (e.getHelperPosition()[1] != e.getBasePosition()[1]));

		//system("pause");
		//system("cls");
		e.showEnvironment(e.getHeight(), e.getWidth(), e.getEnv());
		e.saveEnvironment(e.getHeight(), e.getWidth(), e.getFirst(), e.getEnv());
		
		//system("pause");
		//system("cls");

		disp.set(getSuction(), f.getElevation(), getBatteryCharge(), d.getDirtBin(), e.getError(), getSpeed(), e.getFirst());
		disp.setDisplay();
		disp.updateDisplay();
		r.printRoomFloor(e);
		r.printRoomMess(e);
		e.loadOriginal(e.getHeight(), e.getWidth(), e.getEnv(), getSuction(), f.getElevation(), getBatteryCharge(), d.getDirtBin(), e.getError(), getSpeed());

		cout << endl;
		cout << "FINAL STATS:" << endl;
		disp.set(getSuction(), f.getElevation(), getBatteryCharge(), d.getDirtBin(), e.getError(), getSpeed(), e.getFirst());
		disp.setDisplay();
		disp.updateDisplay();

		cout << endl;
		cout << "Dirt spaces collected: " << d.getDirtCollected() << endl;
		cout << "Bare floor spaces traversed: " << f.getNumBareFloor() << endl;
		cout << "low pilecarpet spaces traversed: " << f.getNumLowPileCarpetFloor() << endl;
		cout << "high pile carpet spaces traversed: " << f.getNumHighPileCarpetFloor() << endl;
		cout << "Total spaces traversed: " << f.totalSpacesCovered() << endl;

		system("pause");
		//end*/
	   //e.deletion();
	}
closed account (SECMoG1T)
i agree it's really big hehe, i hope it's infact a member function
 
void run(Environment e, DirtSensor d, Sensor s, FloorSensor f, ProximitySensor p, Room r);


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
        Environment e;
	CentralOperations c;
	DirtSensor d ;
	FloorSensor f ;
	ProximitySensor p ;
	Sensor s;
	Zone z;
	Room r;

	e.makeLoadDisplayEnvironment();
	cout << endl << endl << endl;
	r.printRoomFloor(e);
	r.printRoomMess(e);
	cout << endl;
	cout << "Press Enter for Automatic Vacuuming!" << endl;
	system("pause");

	thread t2 (sounds);
	thread t1 (&c.run, e, d, s, f, p, r);
        t2.join();
        t1.join();

       /*e->deletion();

	delete d;
	delete s;
	delete f;
	delete p;
	delete r;
	delete z;*/
       /////others
 


does that work?
Last edited on
NO :( I get error C2276: '&' : illegal operation on bound member function expression on line 19
closed account (SECMoG1T)
ooh sorry i used the wrong syntax for member functions this is the way to go,
please use this
1
2
3
4
thread t1 (&c::run,&c, e, d, s, f, p, r);///for member function you have to provide a * to a 
                                                          ///class instance on which that function should be 
                                                        /// be called thread constructors work similarly to 
                                                        /// std::bind 
Last edited on
Doesn't seem to work.
closed account (SECMoG1T)
1
2
3
4
5
6
thread t1 (&c::run,&c, e, d, s, f, p, r);/// is c a class 


///should be like this 

thread t1 (&centralOperations::run,&c, e, d, s, f, p, r);
It crashes right after i press a key for line 16.

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
      Environment e;
	CentralOperations c;
	DirtSensor d ;
	FloorSensor f ;
	ProximitySensor p ;
	Sensor s;
	Zone z;
	Room r;

	e.makeLoadDisplayEnvironment();
	cout << endl << endl << endl;
	r.printRoomFloor(e);
	r.printRoomMess(e);
	cout << endl;
	cout << "Press Enter for Automatic Vacuuming!" << endl;
	system("pause");

	thread t2 (sounds);
	thread t1 (&CentralOperations::run,&c, e, d, s, f, p, r);

        t2.join();
        t1.join();

       /*e->deletion();

	delete d;
	delete s;
	delete f;
	delete p;
	delete r;
	delete z;*/
       /////others 
Last edited on
closed account (SECMoG1T)
It would crash if either of your function threw an exemption, or either of the thread executed and the destructor was called before the call to join.


Just a question is that function run a members function?
1
2
3
4
5
void run(Environment e, DirtSensor d, Sensor s, FloorSensor f, ProximitySensor p, Room r)


///shouldn't it be like this
void centralOperations::run(Environment e, DirtSensor d, Sensor s, FloorSensor f, ProximitySensor p, Room r)


Last edited on
run is a member function of CentralOperations which is declared as c
Last edited on
My function doesn't give me any errors if I call it normally.
An object (this pointer) is required to invoke a non-static member function. Pass the address of the object as the first argument.

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
#include <iostream>
#include <thread>
#include <future>
#include <mutex>

struct A
{
    double run( int a, long b, float c ) const
    {
        static std::mutex stdout_guard ;
        {
            std::lock_guard<std::mutex> lock(stdout_guard) ;

            std::cout << "thread: " << std::this_thread::get_id() 
                      << "  function: A::run  args: " << this << " (this)  "
                      << a << " (a)  " << b << " (b)  "  << c << " (c)\n" << std::flush ;
        }
        
        return a+b+c+v ;          
    }
    
    int v = 10 ;
};

int main()
{
    A a ;
    A* pa = std::addressof(a) ;
    std::cout << "thread: " << std::this_thread::get_id()<< " (main)  address of a: " << pa << '\n' << std::flush ; 
    
    auto future = std::async( std::launch::async, &A::run /* function */, pa /* pointer to object */, 1, 2, 3.4 ) ;
    
    std::thread thread( &A::run /* function */, pa /* pointer to object */, 1, 2, 3.4 ) ;

    thread.join() ;
    
    future.wait() ;
    std::cout << "async result: " << future.get() << '\n' ;
}

http://coliru.stacked-crooked.com/a/ec7dd56b00535d83
Yeah I think I'm just going to give up on this. This was just going to be something extra for my project. Thanks to those who tried to help.
Topic archived. No new replies allowed.