I am working on a circuit simulator/pathfinding system, but I keep getting these weird compilation errors. I am not yet that experienced with OO C++ to figure it out myself...
Object Tree
The objects in my project are implemented in this way:
Object
Component
Wire
Switch
Ciruit
My Object class is the base class for everything in my project, this is great for debugging by giving everything a name and an id.
I required that every component needs a Circuit to with (see it as a parent for components). I implemented this by creating a constructor in the Component class that requires a reference to a Circuit object.
At first, everything worked and compiled fine, but when I introduced the Circuit class and when I added a constructor in Component with a Circuit reference parameter, everything went wrong...
Compilation errors
Now I keep getting these seemingly random syntax and missing tokens errors. (Intellisense does not mark them?)
The first four errors that pop up are:
C2238: unexpected token(s) preceding ';'.
At line 10 of Component.hpp. And at line 12 in file Circuit.hpp.
Both just after the constructor definition. (See in code below)
The next four errors point tot the same locations, but it notes:
C2143: syntax error: missing ';' before '*'.
Then, 30 more errors follow, but I think they are a result of these errors, to be sure, here they are:
(Lol, cannot embed image, caused by not having enough reputation, so a link instead...)
Click here for errors
What I tried
I tried the following:
Using a reference instead of pointer. (changed Circuit* c to Circuit& c)
Removing the name string concationation thing in constructor initializer list. (changed ... : Object(name + "blah") to ... : Object(name))
Rewriting the whole Visual Studio project to a new Visual Studio project.
Placing the constructor initializer list in the header file.
Lots of googling... and not lots of solving...
How to fix?
This frustrating problem is stopping me from working further on this project, what is causing it and how do I fix it? I would be pretty happy to know.
Object.hpp
#pragma once
#include <string>
using std::string;
class Object
{
public:
Object();
Object(string name);
string name;
const int id;
virtual string toString();
private:
static int currentId;
};
Object.cpp
#include "Object.hpp"
int Object::currentId = 0;
Object::Object() : id(++Object::currentId), name("Object")
{ }
Object::Object(string name) : id(++Object::currentId), name(name)
{ }
string Object::toString()
{
return name + "#" + std::to_string(id);
}
Component.hpp
#pragma once
#include "Object.hpp"
#include "Circuit.hpp"
class Component : public Object
{
public:
Component(std::string name, Circuit* container);
Circuit *container; // <- Error points to the beginning of this line
};
Component.cpp
#include "Component.hpp"
Component::Component(string name, Circuit* container) : Object(name), container(container)
{ }
Switch.hpp
#pragma once
#include "Component.hpp"
#include "Wire.hpp"
class Switch : public Component
{
public:
Switch(string name, Circuit* container, Wire& wire1, Wire& wire2);
Wire* wire1;
Wire* wire2;
void setEnabled(bool enabled);
bool getEnabled();
private:
bool enabled;
};
Switch.cpp
Switch::Switch(string name, Circuit* container, Wire& wire1, Wire& wire2) : Component(name + "-Switch", container), wire1(&wire1), wire2(&wire2), enabled(false)
{ }
...
Circuit.hpp
#pragma once
#include "Object.hpp"
#include "Wire.hpp"
class Circuit : public Object
{
public:
Circuit(std::string name);
Wire* powerWire; // <- Error points to the beginning of this line
bool isPowered(Wire& wire);
bool getActive();
void setActive(bool active);
private:
bool active;
};
Circuit.cpp
#include "Circuit.hpp"
#include "Util.hpp"
Circuit::Circuit(string name) : Object(name + "-Circuit")
{
active = false;
powerWire = new Wire(name + "-PowerWire", this);
}
...
You haven't shown Wire.hpp, but my guess is that it includes Component.hpp, which gives you a cycle in header inclusion (because Component.hpp includes Circuit.hpp, and Circuit.hpp includes Wire.hpp).
You will have to replace some of these inclusions with forward declarations to break the cycle.
Related
I have been looking for a solution to this for a few days now. I will spare the details and just display the code:
#include "Mesh/GEdge.h"
//class GEdge;
class GEdgeSigned
{
public:
int _sign;
GEdge *ge;
GEdgeSigned(int i, GEdge *g) : _sign(i), ge(g) {}
GVertex *getBeginVertex() const
{
return (_sign == 1) ? ge->getBeginVertex() : ge->getEndVertex();// Error here
}
GVertex *getEndVertex() const
{
return (_sign != 1) ? ge->getBeginVertex() : ge->getEndVertex(); // Error Here
}
void print() const;
int getSign() const { return _sign; }
};
So basically, I have the invalid error at the locations marked. I clearly have the #include header at top and when you look into the header (the GEdge.h) there is no circular reference.
However, if you open a few more header files that are included in the GEdge.h file, you will end up with a circular reference.
So my question is this, if Edge.h is included 4 files deep, would this still be a circular reference causing the error?
If not, what are some other common issues that cause the invalid type error?
Beginner here - but i was uncertain what exactly to search for this (presumably common) question.
I am working on a program where I have a given class (Dictionary). I am supposed to make a concrete class (Word) which implements Dictionary. I should mention that I am not to change anything in Dictionary.
After making a header file for Word, I define everything in word.cpp.
I am unsure if I am doing this correctly, but I make the constructor read from a given file, and store the information in a public member of Word.
(I understand that the vectors should be private, but I made it public to get to the root of this current issue)
dictionary.h
#ifndef __DICTIONARY_H__
#define __DICTIONARY_H__
#include <iostream>
#include <string>
#include <vector>
#include <fstream>
using namespace std;
class Dictionary
{
public:
Dictionary(istream&);
virtual int search(string keyword, size_t prefix_length)=0;
};
#endif /* __DICTIONARY_H__ */
word.h
#ifndef __WORD_H__
#define __WORD_H__
#include "dictionary.h"
class Word : public Dictionary{
public:
vector<string> dictionary_words;
vector<string> source_file_words;
Word(istream &file);
int search(string keyword, size_t prefix_length);
void permutation_search(string keyword, string& prefix, ofstream& fout, int& prefix_length);
};
#endif /* __WORD_H__*/
word.cpp
#include "word.h"
Word(istream& file) : Dictionary(istream& file)
{
string temp;
while (file >> temp)
{
getline(file,temp);
dictionary_words.push_back(temp);
}
}
In word.cpp, on the line "Word::Word(istream& file)", I get this error :' [Error] no matching function for call to 'Dictionary::Dictionary()'.
I've been told this is error is due to "Word's constructor invoking Dictionary's ", but I still don't quite grasp the idea well. I am not trying to use Dictionary's constructor, but Word's.
If anyone has an idea for a solution, I would also appreciate any terms related to what is causing this issue that I could look up - I wasn't even sure how to title the problem.
Your child class should invoke parent constructor, because parent object are constructed before child. So you should write something like:
Word::Word(isteam& file) : Dictionary(file)
{
...
}
Seems its better described here What are the rules for calling the superclass constructor?
I'm working on Blake algorithm in Visual but I have small problem.
My Block.h file
#pragma once
#include<string>
#include<bitset>
#include<iostream> // DEBUG
#include"BlocksContainer.h"
using namespace std;
class Block {
public:
static void CreateBlocks(string);
static string CreatePadding(int);
Block(string);
protected:
string BlockContent;
};
My BlocksContainer.h file
#pragma once
#include"Block.h"
class BlocksContainer {
public:
int GetLength(void);
Block* GetNBlock(int);
BlocksContainer(Block**, int);
protected:
Block** Blocks;
int Length;
};
I don't know why but Visual throw me blockscontainer.h(7): error C2143: syntax error : missing ';' before '*'
I'm newby in C++ and I can't find error. In Stack I found solutions like missing ; after class declaration, but I have semicolons.
You dont need:
#include"BlocksContainer.h"
inside block.h, this line causes Block to be undefined inside BlocksContainer.h because it was not yet visible to compiler.
In case you really need such inter dependent headers you can declare class like this:
class Block;
after such statement you are allowed to use Block class but only in compound statements like pointers or references - that means Block* GetNBlock(int); would compile.
I'm currently trying to make a game in C++. In my code I'm trying to nest my variables so that my main doesn't have a lot of includes. My problem right now though is that the value of my variables in my class aren't changing. Stepping through the code it shows it setting the value, but it doesn't work. Anyone know what's going on? Thank you in advance.
This is what I have so far:
Location.h
#ifndef LOCATION_H
#define LOCATION_H
#include <string>
class Location
{
public:
Location(void);
Location(std::string name);
~Location(void);
std::string GetName();
void SetName(std::string value);
private:
std::string m_Name
};
#endif
Location.cpp
#include "Location.h"
Location::Location(void): m_Name("") {}
Location::Location(std::string name): m_Name(name) {}
Location::~Location(void)
{
}
std::string Location::GetName()
{return m_Name;}
void Location::SetName(std::string value){m_Name = value;}
PlayerStats.h
#ifndef PLAYERSTATS_H
#define PLAYERSTATS_H
#include "Location.h"
class PlayerStats
{
public:
PlayerStats(void);
~PlayerStats(void);
Location GetLocation();
void SetLocation(Location location);
private:
Location m_Location;
};
#endif
PlayerStats.cpp
#include "PlayerStats.h"
PlayerStats::PlayerStats(void): m_Location(Location()) {}
PlayerStats::~PlayerStats(void)
{
}
Location PlayerStats::GetLocation(){return m_Location;}
void PlayerStats::SetLocation(Location location){m_Location = location;}
main.cpp
#include <iostream>
#include "PlayerStats.h"
using namespace std;
PlayerStats playerStats = PlayerStats();
int main()
{
playerStats.GetLocation().SetName("Test");
cout<< playerStats.GetLocation().GetName()<<endl;
return 0;
}
Your immediate issue is that
Location GetLocation();
returns a copy of the location, so when you call SetName here:
playerStats.GetLocation().SetName("Test");
You're changing the name of the temporary copy, and the change is lost as soon as the semicolon is hit.
More broadly, this kind of design (nesting classes and nesting includes so that main doesn't have a lot of includes, and using a.b.c() style code to access nested members) isn't great C++ style:
Having a bunch of source files that (transitively) include a bunch of header files means that changing a single header file will trigger recompilations of a bunch of source files. Compile times can be a significant issue in larger C++ projects, so reducing compile times by controlling #include's is important. Read up on "forward declarations" for more information.
Writing code like a.b.c() is considered bad object-oriented design, because it reduces encapsulation: not only does the caller have to know about a's details, it has to know about b's also. Sometimes this is the most expedient way to write code, but it's not something to be blindly done just to reduce #include's. Read up on "Law of Demeter" for more information.
If you want to set the result of playerStats.GetLocation(), you could make GetLocation() pass-by-reference (use ampersand, &, on the return argument). Otherwise you are just setting values in a temporary copy of PlayerStats::m_Location.
Alternatively, you could use the SetLocation() function.
My code will be similar to the below code:
class DMLGroup
{
public:
DMLGroup();
~DMLGroup();
void SetName(string name);
private:
string mName;
};
void DMLGroup::SetName(string nm){
mName.assign( nm );
}
int main()
{
string api="API_DML";
DMLGroup * dmlGr = new DMLGroup();
dmlGr->SetName(api.c_str()); //Getting link error with this statement
}
I could able to compile the above code but failed to link using MS visual studio 9 on windows 7 32-bit OS.
Note: I am able to compile, link and run successfully on suselinux-x8664 platform. The problem is only with windows
Please tell me how to resolve this?
The following code compiles & links fine:
#include "stdafx.h"
#include <string>
class DMLGroup
{
public:
DMLGroup() {}
~DMLGroup(){}
void SetName(std::string name);
private:
std::string mName;
};
void DMLGroup::SetName(std::string nm){
mName.assign( nm );
}
int main()
{
std::string api="API_DML";
DMLGroup * dmlGr = new DMLGroup();
dmlGr->SetName(api.c_str()); //Getting link error with this statement
}
What I changed:
#included stdafx.h because it's VS standard - you can turn it off
#includes because it was missing
decorated every use of string with std:: - because most probably you'll use your class definition in a header file and there you simply don't use "using namespace"
supplied default implementation for constructor & destructor
That's all. Check what from the above part is missing or supply an example that exposes the problem & supply the linker error message.