Crashing on calling virtual methods [closed] - c++

Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 8 years ago.
Improve this question
I read about it in other questions but none of them was similar, some was about to call a virtual method in the constructor, others about pure virtuals, but the question here is about vituais methods that are not pure, but about virtual methods that doesn't need be implemented in all derivatives classes. If the class instantiated doesn't implements the method, if we call, it logically calls the method from the base and it crashes sometimes.
I was wondering, why? What is VTABLE (where it enters)? And what is the best way to solve it.
This is a simple example, (avoid answer like pure virtual).
#include <iostream>
class Foo
{
public:
virtual std::string myString() {}
};
class Bar : public Foo
{
public:
};
int main(int argc, char ** argv)
{
Foo * bar = new Foo;
bar->myString();
return 0;
}
What would be the best solution?
Throw an exception
Using assert(false)
Returning a default value
Avoid implementing a body and it will result in an error in
compilation time
None of the alternatives
The best answer will be the one that explains why this happen based on VTABLE and of course, that choose one solution and explain why. The idea is not to base it on opinions.

The base class does implement the function, it just implements it wrong. It is not related to vtables or anything sophisticated. Solution 4 preferred (since it prevents building wrong programs), if not possible/desired 1 or 2 in that order.
Note that the error is not at all related to virtual functions, or inheritance in general (you do not use Bar, did you notice?). It is not even related to classes at all but would happen with any freestanding function as well. Consider:
#include <iostream>
#include <string>
// Note: UB -- nothing returned
int getInt() {}
std::string getStr() {}
int main(int argc, char ** argv)
{
// This probably works (read access from an arbitrary
// location on the stack which is in the prog's address space)
std::cout << getInt() << std::endl;
// This will crash. operator<< will try to access memory through
// a pointer value which is some arbitrary byte pattern on the stack.
// Probably not in the prog's address space.
// Then the destructor for the temporary string will
// try to delete the same
// memory which will crash in any case, even if it happens to
// point to valid memory (which, alas, was never allocated).
std::cout << getStr();
std::cout << "Still alive?\n"; // never printed
std::cout.flush();
return 0;
}
In order to prevent the error from happening with your original code, just return a value. If you implement the function and don't throw or abort (which are the three alternatives), i.e. if you return, you must return a value:
#include <iostream>
class Foo
{
public:
virtual std::string myString() { return "test\n";}
};
class Bar : public Foo
{
public:
};
int main(int argc, char ** argv)
{
Foo * bar = new Foo();
std::cout << bar->myString();
return 0;
}

The VTABLE is a table of pointers to virtual methods. In general, the pointer to the VTABLE is hidden from view, but it is often implemented as the first element in an instance of a class.
When a derived class does not have a member function that its parent class does implement as virtual, the parent's method will be called.

Your mystring function should return a string.

Related

C++ Call child function from parent [duplicate]

This question already has answers here:
call to pure virtual function from base class constructor
(8 answers)
Calling virtual functions inside constructors
(15 answers)
Closed 1 year ago.
I am trying to call an overriden function from the parent, and found out that it just crashes.
This is quite hard to describe, so here the minimal reproducible code:
#include <iostream>
class A
{
public:
A()
{
init1();
}
void init1()
{
printf("1");
init2();
printf("2");
}
virtual void init2() = 0;
};
class B : public A
{
public:
B()
: A()
{}
void init2() override
{
printf("hello");
}
};
int main()
{
B b;
return 0;
}
On MSVC 2019 it crashes, on http://cpp.sh/ it outputs "1" and then main() returns 0, but we never see "hello" or "2".
Why does it crash? What happens from a low level point of view? Is A trying to call its own init2()?
Is there a way of doing it, so I don't have to, in every derived class, add init2() in its constructor?
You can't call a derived class's overriden methods from within a base class constructor (or destructor). The derived class portion of the object doesn't exist yet.
So, to answer your questions:
yes A::A() is trying to call A::init2(), not B::init2(), and thus crashes from calling a pure virtual method.
There are ways (like via CRTP) for a base class constructor to call a derived class method, but doing so has limitations to it (ie, not being able to access any derived class data members since they still don't exist yet, only base class data members can be accessed). In your example, B::init2() doesn't access anyB data members, so it is possible for A::A() to call B::init2(), but in general you really need to wait for B to begin/finish constructing itself before you can safely call B::init2().

Virtual function, how does they work? [closed]

Closed. This question does not meet Stack Overflow guidelines. It is not currently accepting answers.
Closed 8 years ago.
This question appears to be off-topic because it lacks sufficient information to diagnose the problem. Describe your problem in more detail or include a minimal example in the question itself.
Questions asking for code must demonstrate a minimal understanding of the problem being solved. Include attempted solutions, why they didn't work, and the expected results. See also: Stack Overflow question checklist
Improve this question
In C++, i am not able to understand, when a base class pointer stores the address of derived class object it is not able to call the derived class member function?
#include <iostream>
using namespace std;
class Base
{
public:
virtual void show()
{
cout<<" In Base ";
}
};
class Derived: public Base
{
public:
int x;
void show()
{
cout<<"In Derived ";
}
Derived()
{
x = 10;
}
};
int main(void)
{
Base *bp, b;
Derived d;
bp = &d;
bp->show();
cout << bp->x;
return 0;
}
According to me:
derived d => allocates the memory to this object(therefore to x also ) say at address 200,
bp = &d; => it allocated the address 200 to bp. Now it should be able to call bp->x?
But it gives a error.
bp->x gives an error because bp is a pointer to an object of type Base, and Base doesn't have a variable called x, only Derived does.
If x was moved up into Base it would be accessible from both Base and Derived if it's public or protected.
Binding of names happens in run time. so at compilation bp is of type base. so compiler doesn't know anything about derived type assignment. so its saying there is no variable called x in base.
That's where concept of virtual functions come into picture. but hey are only for functions not variables.
In C++, i am not able to understand, when a base class pointer stores
the address of derived class object it is not able to call the derived
class member variable?
Well yes you can, you just need to cast the pointer to the class where the member variable is present
cout << dynamic_cast<Derived*>(bp)->x;
Why is bp->x is a error?
Because at compile time, the compiler can't tell what it points to. What if it was actually, a pointer to the base class? Then, x would be completely absent from the underlying object...
To answer the title question: when you have a pointer to base class that actually points to a derived class instance, then a call to a public functions declared virtual in the based class and reimplemented in the derived class will end up being a call to the derived class' implementation of that function (there are subtelties involved, with private/public access and name hiding that may interfere, but this is roughly how it works).

TIP: in C++, having a method where "this" is not used is not good design [closed]

Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 9 years ago.
Improve this question
Under the hood, a C++ method of a class is like a C function whose first parameter is an instance of the class - or struct.
For example:
void Foo::Do();
would be equivalent to this declaration in C:
void Do(Foo* this);
Hence, using a member m_someMember from within a method is like using this->m_someMember from inside the C function.
After so many years of C/C++ programming experience, I just recently asked myself: What if I call a method from an instance pointer that is NULL???
My guess was: If the method refers to no member at all, when why would it crash?
So I did a quick test (on a Windows platform, with Visual C++ 2008):
class Foo
{
public:
Foo() {}
virtual ~Foo() {}
void Do();
};
void Foo::Do()
{
cout << "Calling 'Do' for " << this << endl;
}
int _tmain(int argc, _TCHAR* argv[])
{
Foo foo;
foo.Do();
Foo* pNullFoo = 0;
pNullFoo->Do();
return 0;
}
Which gives an output like:
Calling 'Do' for 0038FE5C
Calling 'Do' for 00000000
This could be an hassle when doing post-mortem debugging of a crash over an instance pointer that is null. You might think that this method cannot be called if this is invalid.
On the other hand, if the method is declared virtual:
virtual void Foo::Do() { ... }
Then the line:
pNullFoo->Do();
will produce an page fault exception. Why? Because instances of a class with virtual methods have a pointer to the vtable to the child class virtual methods they belong to.
So the first thing the compiler would do is to make pNullFoo to access its vtable member, then bang!
In conclusion, this is better design to have non contextual functions like Do be implemented as procedural routines than methods, unless they are virtual.
Calling a member function on a NULL pointer invokes undefined behavior. Undefined doesn't mean it's going to crash, nor does it mean it's going to do the right thing - it's undefined. Anything could happen.
The only time I've seen this in production code is with Microsoft's CWnd::GetSafeHWND function. But since they wrote the compiler, they can get away with it.
The proper design for member functions that don't need to access any member data is to have them defined as static:
static void Do();
Then call it like:
Foo::Do();
And you don't even need to have an object or a pointer to do that.

Can a Constructor be Private in C++? [closed]

Closed. This question does not meet Stack Overflow guidelines. It is not currently accepting answers.
Questions asking for code must demonstrate a minimal understanding of the problem being solved. Include attempted solutions, why they didn't work, and the expected results. See also: Stack Overflow question checklist
Closed 9 years ago.
Improve this question
Can a constructor be private in C++? If yes then how can we call it?
class Puma
{
int a = 10;
Puma()
{
cout << a;
}
};
int main()
{
Puma pum;
return o;
}
Can this program run? If not then how can we call Puma() constructor as it is private?
Yes, a constructor can be private. And you can call it with member functions (static or non) or friend functions.
class Puma
{
public:
static Puma create(int a) { return Puma(a); }
private:
int age;
Puma(int a) :age(a) {}
friend Puma createPuma(int a);
};
Puma createPuma(int a) { return Puma(a); }
For possible use cases, see the Factory Pattern, or the Named Constructor Idiom.
Yes. Constructor may be private.
In this case you may create class
Using another (public) constructor
Calling constructor from the same class
Calling constructor from the friend class/function
In your code, the program cannot run since you have defined a constructor and it is private. Therefore, in your current code, there is no way to create objects of the class, making the class useless in a sense.
One way to do is that you can provide public static functions, those static functions call the private constructors to create objects of class.
One minor thing:
return o;
should be
return 0;
Yes a constructor can be private. It is useful when called by a static member function (or a friend), e.g.
class Even {
/// in practice, some more C++ code is probably needed
private:
int x;
Even(int a) : x(a) {};
public:
int get () const { return 2*x; };
static Even* make(int y) { return new Even(y); };
};
the example is not very realistic, but you get the idea. In the using code, do
Even* e = Even::make(3);
Be however aware of the C++ rule of five and do read a good C++ programming book and the documentation of your C++ compiler (e.g. GCC or Clang) and of your debugger (e.g. GDB). You may even want to use the Clang static analyzer.
For examples, download, then look inside the source code of Qt, of FLTK, of RefPerSys, of fish, of GCC or Clang.
Singleton can have a private constructor that will be called from a static method of a class.

Using class member functions without initialization [duplicate]

This question already has answers here:
Accessing class members on a NULL pointer
(8 answers)
Closed 9 years ago.
Why is it possible to use class member functions on an uninitialized object (at least I believe it's uninitialized). The following runs without error:
// A.h
class A {
public:
explicit A(int n) : n_(n) {};
~A() {};
int foo() {
return n_;
};
int bar(int i) {
return i;
};
private:
int n_;
};
with
// main.cc
#include <iostream>
#include "A.h"
int main(int argc, char **argv) {
A *myClass;
std::cout << myClass->bar(5) << "\n";
}
Now, certainly attempting myClass->foo();fails, but why can we even use bar() when all we've declared is that a pointer to A exists, and is called myClass? Is this acceptable coding style/is there ever a reason to use this approach?
why can we even use bar() when all we've declared is that a pointer to A exists, and is called myClass?
Because, in general, it's impossible for the compiler to tell whether a pointer will be valid at runtime; so it isn't required to diagnose this error. However, in this case, a decent compiler should be able to issue a warning, as long as you're not building with warnings disabled.
Is this acceptable coding style/is there ever a reason to use this approach?
Absolutely not. Dereferencing an invalid pointer gives undefined behaviour.
Because you can't know if the block of memory where myClass is pointing to is an initialized object, it have right syntax, but undefined behavior, however if want to prevent, you should use -Wall or a similar compiler option (depends on your compiler) and it will warn you about the uninitialized pointer.