function without a definition

T

thomas

//-----------------------------------------------------------
#include<iostream>
#include<cstring>
using namespace std;

class B1{
public:
virtual void fun() = 0;
};

class B2{
public:
void fun();
};

class A:public B1, private B2{
public:
A(){
B1::fun();
B2::fun();
}
};

int main(){}
//-------------------------------------------

The above code links well but B1::fun() and B2::fun() are not defined.

//----------------------------------------------
#include<iostream>
#include<cstring>
using namespace std;

class B2{
public:
B2(){}
void fun();
};

int main(){
B2 b;
b.fun();
}
//---------------------------------------

In this case, the func() definition miss causes a link error.

Any explanation?
 
M

Maxim Yegorushkin

//-----------------------------------------------------------
#include<iostream>
#include<cstring>
using namespace std;

class B1{
public:
virtual void fun() = 0;
};

class B2{
public:
void fun();
};

class A:public B1, private B2{
public:
A(){
B1::fun();
B2::fun();
}
};

int main(){}
//-------------------------------------------

The above code links well but B1::fun() and B2::fun() are not defined.

//----------------------------------------------
#include<iostream>
#include<cstring>
using namespace std;

class B2{
public:
B2(){}
void fun();
};

int main(){
B2 b;
b.fun();
}
//---------------------------------------

In this case, the func() definition miss causes a link error.

Any explanation?

This is due to the way linkers work. Linkers resolve symbols (functions
and objects) that are actually used (and not inlined). In the first case
A::A() is not being used by main(), so that the linker does not need to
resolve it. If it were used, the linker would resolve A::A() and then
proceed to resolve symbols that are being used by A::A() and fail
because there are no definitions for functions B1::fun() and B2::fun()
provided.

In the second case main() does use B2::fun() which needs to be resolved
but there is no definition of B2::fun() provided, therefore linking fails.
 
J

Johannes Schaub (litb)

thomas said:
//-----------------------------------------------------------
#include<iostream>
#include<cstring>
using namespace std;

class B1{
public:
virtual void fun() = 0;
};

class B2{
public:
void fun();
};

class A:public B1, private B2{
public:
A(){
B1::fun();
B2::fun();
}
};

int main(){}
//-------------------------------------------

The above code links well but B1::fun() and B2::fun() are not defined.

//----------------------------------------------
#include<iostream>
#include<cstring>
using namespace std;

class B2{
public:
B2(){}
void fun();
};

int main(){
B2 b;
b.fun();
}
//---------------------------------------

In this case, the func() definition miss causes a link error.

Any explanation?

This is entirely dependent on the implementation. It may diagnose it, and it
may not. In your case, it diagnoses the second case, but not the first.

From the language point of view, both are ill-formed, but without requiring
a diagnostic from the implementation. Since the definition of A::A happens
in-class, it's inline and the compiler knows that inline functions must be
defined in any TU in that they are used. So it can define it according to
the TU's needs as long as you don't observe the difference. And therefor, it
can optimize out both calls. Try changing to this:

class A : public B1, private B2 {
public:
A();
};
A::A() {
B1::fun();
B2::fun();
}

You may have more luck getting a diagnostic with that.
 
J

James Kanze

//-----------------------------------------------------------
#include<iostream>
#include<cstring>
using namespace std;
class B1{
public:
virtual void fun() = 0;
};
class B2{
public:
void fun();
};
class A:public B1, private B2{
public:
A(){
B1::fun();
B2::fun();
}
};
int main(){}
//-------------------------------------------
The above code links well but B1::fun() and B2::fun() are not defined.

It's undefined behavior. The compiler/linker aren't required to
detect the error. Typically, most will *if* the constructor of
A is not inline, or if it is ever used.
//----------------------------------------------
#include<iostream>
#include<cstring>
using namespace std;
class B2{
public:
B2(){}
void fun();
};
int main(){
B2 b;
b.fun();
}
//---------------------------------------
In this case, the func() definition miss causes a link error.
Any explanation?

Again, failing to provide a needed definition is undefined
behavior. Depending on what you do, it may or may not be
detected as an error.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,776
Messages
2,569,603
Members
45,200
Latest member
LaraHunley

Latest Threads

Top