Under C++ I usually ran into an error.
Suppose I have the following classes:
class ClassData
{
public:
ClassData() { a=-1; }
public:
int a;
};
class MyClass
{
public:
MyClass() { m_classData = 0; }
MyClass(ClassData* classData) { m_classData = new ClassData(*classData); m_classData->a=1; }
inline bool getClassData(ClassData* classData) {
if (m_classData) { classData = m_classData; return true; }
else return false;
}
private:
ClassData* m_classData;
};
Now in the main I run this test code:
ClassData cdata;
MyClass* m_myClass = new MyClass(&cdata);
int value = 0;
ClassData classData;
if (m_myClass->getClassData(&classData))
value = classData.a;
If the code is run, value is equal to -1 (instead of 1).
First question: why I've not been able to take a reference to ClassData in MyClass? While I'm thinking to have the ClassData object of m_myClass (like doing m_myClass->m_classData if it would be public), in reality I'm calling the member a on local ClassData object.
I was thinking that the cause was that I cannot change the local variable address, but if I change the code into this:
ClassData* classData=0;
if (m_myClass->getClassData(classData))
value = classData->a;
I get my program crashing.
Second question: what is the correct way to manage this situation? Is the issue located in the program main function or in how getClassData is defined giving room for mistakes?
Here:
bool getClassData(ClassData* classData) {
if (m_classData) { classData = m_classData; return true; }
else return false;
}
Notice that classData is a local variable. It dies when the function terminates, so the function really does nothing except report whether its m_classData is null or not.
So in the first case:
ClassData classData; // <-- classData.a is -1
if (m_myClass->getClassData(&classData))
value = classData.a; // <-- classData.a is still -1
In the second case:
ClassData* classData=0; // classData is null
if (m_myClass->getClassData(classData))
value = classData->a; // classData is still null
you dereference a null pointer, which is Undefined Behavior. You're lucky all it does is crash.
A correct (but still unsafe) way to do it is like this:
bool getClassData(ClassData* classData) {
if (m_classData!=0 && classData!=0)
{ classData->a = m_classData->a; return true; }
else return false;
}
I say "still unsafe" because this function cannot really verify that these pointers point to valid data structures. To avoid this danger you must refrain from using pointers so much, and look into references.
Using values instead of pointers simplifies things and will also remove your memory leak. See live example
#include <iostream>
class ClassData
{
public:
ClassData() { a=-1; }
public:
int a;
};
class MyClass
{
public:
MyClass() { }
explicit
MyClass(ClassData const& classData) {
m_classData = classData;
m_classData.a=1;
}
ClassData const& getClassData() const {
return m_classData;
}
private:
ClassData m_classData;
};
int main()
{
ClassData classData;
MyClass myClass( classData );
classData = myClass.getClassData();
int value = classData.a;
std::cout << value;
}
Related
For the life of me I cannot understand at all why this program is getting a segmentation error. The issue is that it retrieves an object within the vector container uses a function within the menu class using the get_command() and for some reason after testing the main function line by line this one results in a segmentation fault:
menu->get_command()->execute();
I have tried changing the syntax to create a new command object that stores the returned object from get_command() and changed the index between 0 and -1 and still nothing fixes the error. I have spent at least a couple of hours trying to figure out why but I cannot seem to find a solution.
class Base {
public:
/* Constructors */
Base() { };
/* Pure Virtual Functions */
virtual double evaluate() = 0;
virtual std::string stringify() = 0;
};
class op : public Base
{
public:
op() { };
op(double op1) { operand = op1; }
double evaluate() { return operand; }
string stringify() {
string value = to_string(operand);
return value;
}
private:
double operand;
};
class Command {
protected:
Base* root;
public:
Command() { this->root = nullptr; }
double execute() { return root->evaluate(); }
std::string stringify() { return root->stringify(); }
Base* get_root() { return root; }
};
class Menu {
private:
int history_index; // Indexes which command was last executed, accounting for undo and redo functions
std::vector<Command*> history; // Holds all the commands that have been executed until now
public:
Menu() {
// Constructor which initializes the internal members
history_index = -1;
}
std::string execute() {
// Returns the string converted evaluation of the current command
return to_string(history[history_index - 1]->execute());
}
std::string stringify() {
// Returns the stringified version of the current command
return history[history_index]->stringify();
}
bool initialized() {
// Returns if the history has an InitialCommand, which is necessary to start the calculation
if (history[history_index] != nullptr)
return true;
else
return false;
}
void add_command(Command* cmd) {
// Adds a command to the history (does not execute it), this may require removal of some other commands depending on where history_index is
history.push_back(cmd);
history_index++;
}
Command* get_command() {
// Returns the command that the history_index is currently referring to
return history[history_index];
}
void undo() {
// Move back one command (does not execute it) if there is a command to undo
history_index--;
}
void redo() {
// Moves forward one command (does not execute it) if there is a command to redo
history_index++;
}
};
class InitialCommand : public Command {
protected:
Base* root;
public:
InitialCommand(Base* b) { this->root = b; }
double execute() { return root->evaluate(); }
std::string stringify() { return root->stringify(); }
Base* get_root() { return root; }
};
void main()
{
Menu* menu = new Menu();
InitialCommand* temp = new InitialCommand(new op(7));
menu->add_command(temp);
EXPECT_EQ(menu->get_command()->execute(), 7);
system("PAUSE");
}
You're not doing inheritance right, as you are duplicating fields between Command and InitialCommand that lead to the error.
Both command classes have a Base *root member, and non-virtual execute methods. When you construct a new InitialCommand object, the InitialCommand::root object points at the op that was created for it, while Command::root remains NULL because of the default constructor for Command. Then, when you call menu->get_command(), it will call Command::execute because execute is non-virtual and menu is a Command *. Command::execute will then dereference a NULL root, causing your segmentation error.
Remove the Base *root member from InitialCommand, and pass the parameter to a constructor in Command. You probably want to make some methods like execute virtual.
The problem is that your Command and InitialCommand both have root variable.
InitialCommand* temp = new InitialCommand(new op(7)); will according to your constructor set InitialCommand::root. So Command::root remains uninitialized. Then Menu holds std::vector<Command*>, so InitialCommand* is implicitly converted to Command*.
At alst calling Command::execute will indeed call Command:execute because the method is not virtual. So, the uninitialized Command::root is used -> seg. fault.
Please don't use new. Use smart pointers - std::unique_ptr should be the default way to manage dynamic memory.
That said, your code seems too Java/C# like. This is C++, use value semantics if you can. There's no reason for Menu* menu = new Menu();. Menu menu; is simpler and works the same in your case. Here's a code I would've written
#include <memory>
#include <vector>
#include <string>
using namespace std;//Not a good practice and definitely a big no in header files.
class Base {
public:
/* Constructors */
Base() { };
/* Pure Virtual Functions */
virtual double evaluate() = 0;
virtual std::string stringify() = 0;
};
class op : public Base
{
public:
op() { };
op(double op1) { operand = op1; }
double evaluate() { return operand; }
string stringify() {
string value = to_string(operand);
return value;
}
private:
double operand;
};
class Command {
protected:
std::unique_ptr<Base> root;
public:
Command(std::unique_ptr<Base>&& root):root(std::move(root)) { }
//Be const-correct
double execute() const { return root->evaluate(); }
std::string stringify() const { return root->stringify(); }
Base* get_root() const { return root.get(); }
};
class Menu {
private:
int history_index; // Indexes which command was last executed, accounting for undo and redo functions
std::vector<std::unique_ptr<Command>> history; // Holds all the commands that have been executed until now
public:
Menu() {
// Constructor which initializes the internal members
history_index = -1;
}
std::string execute() const{
// Returns the string converted evaluation of the current command
return to_string(history[history_index - 1]->execute());
}
std::string stringify() const{
// Returns the stringified version of the current command
return history[history_index]->stringify();
}
bool initialized() const{
// Returns if the history has an InitialCommand, which is necessary to start the calculation
if (history[history_index] != nullptr)
return true;
else
return false;
}
void add_command(std::unique_ptr<Command>&& cmd) {
// Adds a command to the history (does not execute it), this may require removal of some other commands depending on where history_index is
history.emplace_back(std::move(cmd));
history_index++;
}
Command* get_command() const {
// Returns the command that the history_index is currently referring to
return history[history_index].get();
}
void undo() {
// Move back one command (does not execute it) if there is a command to undo
history_index--;
}
void redo() {
// Moves forward one command (does not execute it) if there is a command to redo
history_index++;
}
};
class InitialCommand : public Command {
protected:
public:
InitialCommand(std::unique_ptr<Base>&& b): Command(std::move(b)){}
};
// There's no such thing as void main
int main()
{
Menu menu;
auto temp = std::make_unique<InitialCommand>(std::make_unique<op>(7));
menu.add_command(std::move(temp));
//EXPECT_EQ(menu.get_command()->execute(), 7);
system("PAUSE");
}
It uses move semantics which used to not be a beginners concept, but it's such integral part of modern C++ that every C++ programmer must learn it sooner rather than later.
i'm new here in c++ and RTOS, so don't blame me or laugh at me pls
i have:
typedef struct
{
//... 10 uint8 and 2 enums
} tStruct1;
typedef struct
{
//... slightly different, but completely different enums
} tStruct2;
class someClass
{
private:
struct
{
//...
union
{
tStruct1 s1;
tStruct2 s2;
} data;
} node[10];
//...
public:
unsigned int length;
tStruct1 Get1(void);
tStruct2 Get2(void);
//...
}
tStruct1 someClass::Get1(void)
{
//...
length--;
return node[length].data.s1;
}
tStruct2 someClass::Get2(void)
{
//...
length--;
return node[length].data.s2;
}
and in someOtherClass:
someClass * inst1 = new someClass();
this works fine:
inst1->Get1(void); //useless...
and this:
tStruct1 something = inst1->Get1(void);
moves inst1 somewhere else. It happens 3 instructions before branch to the function, stack pointer decrements by 0x14 (sizeof structure elements is probably 0x12 + alignment -> I think it's ok), and increments back. Function itself seems to work allright. Returned value is some uninitialized value.
bool result = instance_of_someOtherClass->inst1->Set(tStruct1);
works also fine.
Those 2 calls are done from different threads. Anyway, I'm going to throw this class away because the project changed, but I want to know what I'm doing wrong.
Apologies ahead of time, as I am not even sure how to phrase the question, but I was working on a homework assignment (to which the question is unrelated except that I ran into the problem working on the assignment) and came across certain problem (this is just an extraction and generalization, I left out destructors, etc...):
class idType {
int _id;
public:
int getID() { return _id; }
idType(int in = -1) : _id(-1) {}
};
class Foo {
static int _count;
idType* _id; //int wrapper just for examples sake
public:
Foo() { _id = new idType(_count); ++_count; }
idType* getID() { if(_id) return _id; return NULL; } //ERROR WHEN CALLED FROM BELOW
};
class Bar {
Foo* _foo;
public:
Bar(Foo* foo = NULL) : _foo(foo) {}
Foo* getFoo() { if(_foo) return _foo; return NULL; }
};
int foo::_count = 0;
int main() {
Bar BAR;
if(BAR.getFoo()->getID() && BAR.getFoo()); //RUN TIME ACCESS VIOLATION ERROR
return 0;
};
As I mentioned, this is not the code I am working with, but I believe it more clearly identifies what is happening. BAR passes the getFoo() check, so _foo isn't(?) NULL but getFoo()->getID() faults at if(_id).
Is the static variable somehow preventing any NULL instance of a pointer to that class type from existing?
The reason I asked that at first was because when I commented out the static variable lines in my original program, the program worked fine. HOWEVER, after trying this code (which more or less emulates what I am doing) removing the static variable lines makes no difference, it still faults the same.
This may be simple, but I am at a loss as to what is wrong. Thank you much for any help.
Check pointers before using them.
int main()
{
Bar BAR;
Foo *pFoo = BAR.getFoo();
if (pFoo && pFoo->getID())
{
// do something
}
return 0;
};
You are not creating a Foo instance anywhere, and not passing a Foo* to the Bar constructor, so Bar::_foo gets initialize to NULL, which is what Bar::getFoo() returns. And then your if statement crashes due to your backwards use of short-circuit logic (you are trying to access Foo::getID() before first validating that Bar::getFoo() returns a non-NULL Foo* pointer).
You have to pass pointer to Foo object to BAR
int main() {
Bar BAR(new Foo);
//Reverse the condition, check for pointer validity first
if(BAR.getFoo() && BAR.getFoo()->getID());
return 0;
};
Provide the destructor to cleanup _foo after usage
~Bar() { if(_foo) delete _foo; _foo=NULL; }
Say I have a class with a couple of data members, and I want a class method that returns one, and the next time it is called returns the value of the other. Something like:
class MyClass
{
public:
MyClass():switch(0){};
int get();
private:
int intA, intB;
int sw;
};
int MyClass::get()
{
if ( (++sw)%2 )
return intA;
else
return intB;
}
What would a more elegant way of doing it be? I don't like the if...else statement very much. It's fine for something like return, but if I'm actually using more complex operations, I end up duplicating a ton of code. Or having to create a second method within each method that is called after I resolve what element I'm pointing to.
What I'd prefer to do, ideally, is to use some form of pointer, so I can do
class MyClass
{
public:
MyClass():switch(&intA){};
int get();
void toggleSwitch();
private:
int intA, intB;
int * sw;
};
int MyClass::get()
{
return *sw;
}
void MyClass::toggleSwitch()
{
if ( sw == &intA )
sw = &intB;
else
sw = &intA;
}
Or something to that effect. I could call toggleSwitch(), and have my class operate on either one or the other value easily.
I still don't like it though. I prefer to avoid if's when possible, and I shouldn't need one in this case. This use of a naked pointer should be pretty safe, but I was thinking I could have something like std::unique_ptr holding each element and then std::swap them. But then the pointers would own the elements, and they'd be dynamic memory instead.
So is there a better way to do it?
Well, switch is a keyword, but I'll roll with it. How about an array of pointers?
int *fields[] = {&intA, &intB};
int MyClass::get()
{
return *fields[++switch % 2];
}
This would expand nicely if you could have additional variables later.
Or maybe:
int MyClass::get()
{
return *fields[switch = 1 - switch];
}
If you return a reference then you could use get() internally.
int &MyClass::get()
{
return *fields[switch = 1 - switch];
}
I would encapsulate the concept of a toggling value:
template<typename T>
class Toggleable {
T first;
T second;
T* current;
T* other;
public:
Toggleable(const T& first, const T& second)
: first(first),
second(second),
current(&first),
other(&second) {
}
bool toggle() {
std::swap(current, other);
}
const T& get() const {
return *current;
}
}
Then use as:
class MyClass
{
Toggleable<int> value;
public:
MyClass()
: value(42, 1729)
{
}
const int& get() {
value.toggle();
return value.get();
}
};
I have a class called Object which stores some data.
I would like to return it by reference using a function like this:
Object& return_Object();
Then, in my code, I would call it like this:
Object myObject = return_Object();
I have written code like this and it compiles. However, when I run the code, I consistently get a seg fault. What is the proper way to return a class object by reference?
You're probably returning an object that's on the stack. That is, return_Object() probably looks like this:
Object& return_Object()
{
Object object_to_return;
// ... do stuff ...
return object_to_return;
}
If this is what you're doing, you're out of luck - object_to_return has gone out of scope and been destructed at the end of return_Object, so myObject refers to a non-existent object. You either need to return by value, or return an Object declared in a wider scope or newed onto the heap.
You can only use
Object& return_Object();
if the object returned has a greater scope than the function. For example, you can use it if you have a class where it is encapsulated. If you create an object in your function, use pointers. If you want to modify an existing object, pass it as an argument.
class MyClass{
private:
Object myObj;
public:
Object& return_Object() {
return myObj;
}
Object* return_created_Object() {
return new Object();
}
bool modify_Object( Object& obj) {
// obj = myObj; return true; both possible
return obj.modifySomething() == true;
}
};
You can only return non-local objects by reference. The destructor may have invalidated some internal pointer, or whatever.
Don't be afraid of returning values -- it's fast!
I will show you some examples:
First example, do not return local scope object, for example:
const string &dontDoThis(const string &s)
{
string local = s;
return local;
}
You can't return local by reference, because local is destroyed at the end of the body of dontDoThis.
Second example, you can return by reference:
const string &shorterString(const string &s1, const string &s2)
{
return (s1.size() < s2.size()) ? s1 : s2;
}
Here, you can return by reference both s1 and s2 because they were defined before shorterString was called.
Third example:
char &get_val(string &str, string::size_type ix)
{
return str[ix];
}
usage code as below:
string s("123456");
cout << s << endl;
char &ch = get_val(s, 0);
ch = 'A';
cout << s << endl; // A23456
get_val can return elements of s by reference because s still exists after the call.
Fourth example
class Student
{
public:
string m_name;
int age;
string &getName();
};
string &Student::getName()
{
// you can return by reference
return m_name;
}
string& Test(Student &student)
{
// we can return `m_name` by reference here because `student` still exists after the call
return stu.m_name;
}
usage example:
Student student;
student.m_name = 'jack';
string name = student.getName();
// or
string name2 = Test(student);
Fifth example:
class String
{
private:
char *str_;
public:
String &operator=(const String &str);
};
String &String::operator=(const String &str)
{
if (this == &str)
{
return *this;
}
delete [] str_;
int length = strlen(str.str_);
str_ = new char[length + 1];
strcpy(str_, str.str_);
return *this;
}
You could then use the operator= above like this:
String a;
String b;
String c = b = a;
Well, it is maybe not a really beautiful solution in the code, but it is really beautiful in the interface of your function. And it is also very efficient. It is ideal if the second is more important for you (for example, you are developing a library).
The trick is this:
A line A a = b.make(); is internally converted to a constructor of A, i.e. as if you had written A a(b.make());.
Now b.make() should result a new class, with a callback function.
This whole thing can be fine handled only by classes, without any template.
Here is my minimal example. Check only the main(), as you can see it is simple. The internals aren't.
From the viewpoint of the speed: the size of a Factory::Mediator class is only 2 pointers, which is more that 1 but not more. And this is the only object in the whole thing which is transferred by value.
#include <stdio.h>
class Factory {
public:
class Mediator;
class Result {
public:
Result() {
printf ("Factory::Result::Result()\n");
};
Result(Mediator fm) {
printf ("Factory::Result::Result(Mediator)\n");
fm.call(this);
};
};
typedef void (*MakeMethod)(Factory* factory, Result* result);
class Mediator {
private:
Factory* factory;
MakeMethod makeMethod;
public:
Mediator(Factory* factory, MakeMethod makeMethod) {
printf ("Factory::Mediator::Mediator(Factory*, MakeMethod)\n");
this->factory = factory;
this->makeMethod = makeMethod;
};
void call(Result* result) {
printf ("Factory::Mediator::call(Result*)\n");
(*makeMethod)(factory, result);
};
};
};
class A;
class B : private Factory {
private:
int v;
public:
B(int v) {
printf ("B::B()\n");
this->v = v;
};
int getV() const {
printf ("B::getV()\n");
return v;
};
static void makeCb(Factory* f, Factory::Result* a);
Factory::Mediator make() {
printf ("Factory::Mediator B::make()\n");
return Factory::Mediator(static_cast<Factory*>(this), &B::makeCb);
};
};
class A : private Factory::Result {
friend class B;
private:
int v;
public:
A() {
printf ("A::A()\n");
v = 0;
};
A(Factory::Mediator fm) : Factory::Result(fm) {
printf ("A::A(Factory::Mediator)\n");
};
int getV() const {
printf ("A::getV()\n");
return v;
};
void setV(int v) {
printf ("A::setV(%i)\n", v);
this->v = v;
};
};
void B::makeCb(Factory* f, Factory::Result* r) {
printf ("B::makeCb(Factory*, Factory::Result*)\n");
B* b = static_cast<B*>(f);
A* a = static_cast<A*>(r);
a->setV(b->getV()+1);
};
int main(int argc, char **argv) {
B b(42);
A a = b.make();
printf ("a.v = %i\n", a.getV());
return 0;
}
It isn't really good practice to return an initiated object as it does go out of scope. There are rare instances that this is the desired option. It actually can be done if the class is a referencing counting smart pointer or some other smart pointer.
How does a reference-counting smart pointer's reference counting work?