Polymorphism - Initializing objects from abstract and behaviour classes in C++

I'm creating a program that will simulate a race between various runners, using behavior classes to implement different types of runner movements.

To do this, an abstract MoveBehaviour class will be implemented, along with several other concrete sub-classes (etc. WalkBehaviour, JumpBehaviour).

The abstract MoveBehaviour class will require a pure virtual move() function, and the appropriate behaviour will be implemented in the concrete sub-classes. This move() function computes a new position newPos for the runner, given its current position oldPos, and the move() function will return a short, text description of the move in the log parameter (Etc. "walk forward 1 step") , which will be printed to the screen in a later step.

I believe I have my behaviour classes set fine, but I'm struggling with my Runner.cc class.

The Runner constructor's goal is to basically take a name, avatar, bib number, and lane number as parameters, and initializes all the data members in this class. This would include initializing the runner’s current position to the row indicated by the lane number, and a column set to zero to represent the left-hand side of the screen, as well as initializing the move behaviour to walking behaviour.

I think I initialized the runner's current position with the lane number and column set to 0 correctly, but I'm a little confused as to how I would initialize the move behaviour to the walking behaviour. Am I supposed to declare a WalkBehaviour object or something?

In the update() function in Runner.cc, I'm also supposed to randomly select the runner’s next move behaviour, such as a new walking behaviour 40% of the time. I'm pretty sure I got the "40%" of the time component correct, but again, I'm not sure how I'm supposed to select a new walking behaviour specifically. I assume this is similar to what I'm supposed to do in the constructor, and would appreciate some help.

Runner.cc
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

	#include <iostream>
	using namespace std;
	#include <string>
	#include "Runner.h"
	
	int random(int);
	Runner::Runner(string s1, char c1, int i1, int i2) : name(s1), avatar(c1), bibNumber(i1), laneNumber(i2){ 
		currPos = Position(laneNumber, 0);
		//current = WalkBehaviour;
	}

	Position Runner::getCurrPos() { 
		return currPos;
	}

	void Runner::setCurrPos(Position c){
		currPos = c;
	}	
	
	void Runner::update(Position& newPos){
		int r;
		r = random(10) + 1;	
		if(r == 4){ //40% of the  time
			//new walking behaviour
		}

	}


Runner.h

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20

	#ifndef RUNNER_H
	#define RUNNER_H

	#include "MoveBehaviour.h"
	#include "Position.h"

	class Runner{
		public:
			Runner(string = "Unknown", char = ' ', int = 0, int = 0); 
			Position getCurrPos();
			void setCurrPos(Position);
			void update(Position& newPos);
			
		private:
			Position currPos;
			MoveBehaviour* behaviour;
			
	};
	#endif 


Position.cc

1
2
3
4
5
6
7
8
9
10
11
	#include <iostream>
	using namespace std;
	#include <string>
	#include "Position.h"

	Position::Position(int i1, int i2) : row(i1), column(i2){ 
	}
	Position::getRow(){ return row; }
	Position::getColumn(){ return column; }
	void Position::setRow(int r){ row = r; }
	void Position::setColumn(int c){ column = c; }


MoveBehaviour.h

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
	#ifndef MOVEBEHAVIOUR_H
	#define MOVEBEHAVIOUR_H

	#include <iostream>
	using namespace std;

	class MoveBehaviour
	{
	  public:
		virtual void move(Position&, Position&, string&) = 0;
	};

	class WalkBehaviour : public MoveBehaviour{
	  public:
		virtual void move(Position&, Position&, string&);
	};


	#endif 


WalkBehaviour.cc

1
2
3
4
5
6
7
8
9
10
	#include <iostream>
	using namespace std;
	#include <string>
	#include "MoveBehaviour.h"

	void WalkBehaviour::move(Position& oldPos, Position& newPos, string& log) { 
		newPos.setColumn(oldPos.getColumn() + 1);
		newPos.setRow(oldPos.getRow());
	} 


Random.cc

1
2
3
4
5
6
7
8
	#include <iostream>
	#include <cstdlib>

	int random(int max){
		double r = ( (double)rand() / ((double)(RAND_MAX)+(double)(1)) ); 
		return (int)(r * max);
	}
	
Last edited on
> if(r == 4){ //40% of the time
No, this is 10% of the time.

r <= 4
This is 40%

Write it like
1
2
r = random(100) + 1;  // 100 because, you know, percent.
if ( r <= 40 ) // the first 40 of them is 40% 


> //current = WalkBehaviour;
This would be
behaviour = new WalkBehaviour;
Hi, so I added behaviour = new WalkBehaviour; in the constructor but I keep getting the error undefined reference to `vtable for WalkBehaviour' collect2: error: ld returned 1 exit status."

Additionally in the update() function when I need to make a new walking behaviour 40% of the time, do I just do WalkBehaviour walk = new WalkBehaviour in the if ( r <= 40 ) statement?
Last edited on
Where's the definition for your WalkBehaviour class?
I don't have a seperate header file for any of the behaviour classes. I put them all in MoveBehaviour.h. I updated MoveBehaviour.h with the functions from WalkBehaviour.cc. All it has right now is just the move function.
Last edited on
That's a linker error you're getting. Are you sure your project/makefile is set up to correctly link WalkBehaviour.cc with the rest of your code?
Topic archived. No new replies allowed.