Err C2228 - Possible Most Vexing Parse?

Hello I am trying to recreate a system I made in Python. Here is the error I am getting: error C2228: left of '.onPoison' must have class/struct/union

Here is the whole project:
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
#include "stdafx.h"
#include <iostream>
#include <string>
#include <vector>

using namespace std;
class Entity;

enum EffectTypes {
	POISON_BASIC,
};

class _Effect {
public:
	void applyEffect(Entity& e) {}
};

class PoisonEffect : public _Effect {
	int duration = 5;
	int mod = 1;

public:
	void applyEffect(Entity& e) {
		e.onPoison(duration, mod);
	}
};

class _Buff {
	EffectTypes type;
	int duration;
	int mod;

public:
	EffectTypes getType() {
		return type;
	}
	int getDuration() {
		return duration;
	}
	int getMod() {
		return mod;
	}

	_Buff() {}

	virtual void updateBuff() {};
};

class PoisonDamage : public _Buff {
private:
	EffectTypes type = POISON_BASIC;
	int duration;
	int mod;
	
public:
	PoisonDamage(int d, int m) : duration(d), mod(m) {}

	void updateBuff() {
		cout << "You've been poisoned!" << endl;
	}
};

class Entity {
private:
	vector<_Buff*> buffs;

public:
	void onPoison(int duration, int mod) {
		buffs.push_back(new PoisonDamage(duration, mod));
	}
	~Entity() {
		for (auto p : buffs) {
			delete p;
		}
	}
};

int main()
{
	Entity me;
	//me.print;
	PoisonEffect p;
//	p.applyEffect(me);
	//me.print;
	cin.ignore();
    return 0;
}
The compiler doesn't know what members Entity has at that point. You need to move the definition of PoisonEffect::applyEffect() after the definition of Entity.
> Possible Most Vexing Parse?

No. The type Entity is an incomplete type on line 24.

Move the definition of the function to after Entity becomes a complete type and you would be ok.

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
class PoisonEffect : public _Effect {
	int duration = 5;
	int mod = 1;

public:
        // implemented after Entity becomes a complete type
	void applyEffect(Entity& e) ; /*{
		e.onPoison(duration, mod);
	}*/
};

class _Buff {

// ...

class Entity {

   // ...
};

// at this point, Entity is complete type
void PoisonEffect::applyEffect(Entity& e) {

		e.onPoison(duration, mod);
}


Also, do not use a name like _Buff; this is wrong on two counts:

In addition, some identifiers are reserved for use by C++ implementations and shall not be used otherwise; no diagnostic is required.

Each identifier that contains a double underscore __ or
begins with an underscore followed by an uppercase letter
is reserved to the implementation for any use.

Each identifier that begins with an underscore is reserved to the implementation for use as a name
in the global namespace.
http://eel.is/c++draft/lex.name


For a vector of non-polymorphic types, strongly favour creating a vector of values:
1
2
// vector<Buff*> buffs; // avoid
std::vector<Buff> buffs ; // this is a good idea 
Thanks guys. Just figured out the problem a little bit before the responses. Split up all the files and created headers and everything is working now :)

Will change the Buff class name and vector, thanks for the tips
Topic archived. No new replies allowed.