i made the following code where data and process are two classes and i m trying to use the variables of the object of data class in the functions of process class by making them friend to the data class.
class data;
class process
{
public:
void rarea(data ob);
void carea(data ob);
};
void process::rarea(data ob)
{
int a;
a=ob.l*ob.b;
cout<<a;
}
void process::carea(data ob)
{
int a;
a=3.14*ob.r*ob.r;
cout<<a;
}
class data
{
int l,b,r;
public:
void input()
{
cin>>l>>b>>r;
}
friend void process::carea(data);
friend void process::rarea(data);
};
int main()
{
data d;
process p;
d.input();
p.carea(d);
p.rarea(d);
}
but the compiler is giving errors.
error:'ob' has incomplete type
error:forward declaration of data
The definitions of rarea and carea need access to the definition of data, or they won't know what one looks like.
Their declarations don't, so it will work if you just rearrange a little:
class data;
class process
{
public:
void rarea(data ob);
void carea(data ob);
};
class data
{
int l,b,r;
public:
void input()
{
cin>>l>>b>>r;
}
friend void process::carea(data);
friend void process::rarea(data);
};
void process::rarea(data ob)
{
//...
}
void process::carea(data ob)
{
//...
}
Related
Is there a way to declare member4 that only visible to Function1 and it is not shared by all instances?
class Test
{
public:
void Function1()
{
???? int member4 //visble to Function1 (single instance)
}
void Function2()
{
static int member3;// visble to Function2 (all instances)
}
private:
int member1; // visble to Function1 and Function2 (single instance)
static int member2;//visble to Function1 and Function2 (all instances)
};
Your question looks like an XY Problem. Anyway, here are two possible solutions.
First, you could wrap the field into a class and declare the method as a friend:
class Test {
public:
// Don't forget to init Data:
Test();
void function1();
void function2();
private:
class Data;
Data *data;
};
class Test::Data {
int get() { return 42; }
friend void Test::function1();
};
void Test::function1() {
int secretData = data->get();
}
void Test::function2() {
// Will not compile:
// int secretData = data->get();
}
This solution smells. Much better would be to extract the entity that has this secret member into a separate class:
class AnotherEntity {
public:
void function1() {
// use secretData here;
}
private:
int secretData;
};
class Test : public AnotherEntity {
public:
void function2();
private:
};
Is it possible to achieve this code?
class apple;
class fruit{
public: int i;
void set(apple a){
}
};
class apple{
public: int j;
void set(fruit f){
}
};
I know this leads to error: 'a' has incomplete type. even I interchange classes, It always leads to incomplete type error. I have a question can this be achieved? Iam not sure. any help is greatly apprciated. Thanks
Update
class apple;
class fruit{
public: int i;
void set(apple* a);
};
class apple{
public: int j;
void set(fruit f){
}
};
void fruit::set(apple *a){
apple b = *a;
}
I Guess this workaround works. but is there any other solution?
It's possible, but you need to have method definitions outside of the class:
class apple;
class fruit {
public:
int i;
void set(apple a);
};
class apple {
public:
int j;
void set(fruit f);
};
void fruit::set(apple a)
{
i = a.j;
}
void apple::set(fruit f)
{
j = f.i;
}
Using pointers or references, since only the name needs to be known in that case:
class apple;
class fruit{
public:
int i;
void set(apple* a); // OK
void set(apple& a); // Also OK
};
And you need to move the implementation of the function to a place where the definition of apple is known.
You cannot have a circular reference like this. Only possibility is to have a pointer to object used instead of object, as in:
class apple;
class fruit{
public: int i;
void set(apple * a){
}
};
class apple{
public: int j;
void set(fruit * f){
}
};
and manage with de-referenced object within the functions, i.e. use *f within the implementation of these functions apple::set and fruit::set
If you would like to have the object non-modifiable when you pass as a pointer, use as:
class apple;
class fruit{
public: int i;
void set(const apple * a){
}
};
class apple{
public: int j;
void set(const fruit * f){
}
};
I'm currently reading C++ Primer and am at the point of class friends and member function friends and I'm having trouble figuring out how to get the code that has the following pseudoform to work:
class B;
class A {
public:
A(int i): someNum(i) { }
private:
int someNum;
friend void B::someMemberFunction(Args); // Compile error: Incomplete Type
};
class B {
public:
void someMemberFunction(Args) { /* doStuff */ }
private:
vector<A> someVector { A(5) };
};
If you try to compile in this form it gives the incomplete type error on the friend line. So the solution is to move the class B definition above class A:
class A;
class B {
public:
void someMemberFunction(Args) { /* doStuff */ }
private:
vector<A> someVector { A(5) }; // Compile error: Incomplete Type
};
class A {
public:
A(int i): someNum(i) { }
private:
int someNum;
friend void B::someMemberFunction(Args);
};
However now on the vector line, it doesn't know how to create an object of type A, since A has yet to be defined. So then A needs to be defined before B. But now we've arrived back at the original problem. I think this is called circular dependency? I don't know how to fix this with forward declarations.
Any help would be appreciated. Thanks.
I think you will either have to make the whole of class B a friend (which removes a dependency in A anyway so it's probably a good thing), or use a constructor instead of the in-class initializer.
class B;
class A {
public:
A(int i): someNum(i) { }
private:
int someNum;
friend class B;
};
class B {
public:
void someMemberFunction() { /* doStuff */ }
private:
vector<A> someVector { A(5) };
};
Or this
class A;
class B {
public:
B();
void someMemberFunction() { /* doStuff */ }
private:
vector<A> someVector;
};
class A {
public:
A(int i): someNum(i) { }
private:
int someNum;
friend void B::someMemberFunction();
};
B::B(): someVector{A(5)} { }
I need a class hierarchy in which the derived classes will have implementation of a virtual function that differs in the return type. How can i do it. What i have tried is the following code:
using namespace std;
class Base
{
public:
Base()
{
cout<<"Constructor of Base"<<endl;
}
virtual Base& Decode()=0;
virtual operator int(){return -1;}
virtual operator string(){return "WRONG";}
};
class Der1:public Base
{
int i;
public:
Der1(int j=0):Base(),i(j)
{
cout<<"COnstructor of Der1"<<endl;
}
Base& Decode()
{
cout<<"Decode in Der1"<<endl;
return *this;
}
operator int()
{
return i;
}
};
class Der2:public Base
{
string s;
public:
Der2(string temp="sajas"):Base(),s(temp)
{
cout<<"Constructor of Der2"<<endl;
}
Base& Decode()
{
cout<<"Decode in Der2"<<endl;
return *this;
}
operator string()
{
return s;
}
};
int main()
{
Base *p=new Der1();
int val=p->Decode();
}
I was thinking if it could work this way user would just have to equate the object to a valid variable. Is there any way to do it without including all the conversion operators in Base with some dummy implementatin?
I guess there is one problem, if it is a Pure virtual function you cannot create an object of the class base. But on the other hand to solve your problem you can try out using templates, something like below.
#include <iostream>
class Base{
public:
Base(){}
virtual ~Base(){}
virtual void show() const {
std::cout << "Base::show()!" << std::endl;
}
};
class A:public Base{
public:
A(){}
virtual ~A(){}
virtual void show() const{
std::cout << "A::show()!" << std::endl;
}
};
template<typename T>
class Factory{
public:
const T* operator()() const{
return &t;
}
private:
T t;
};
int main(){
const A* pA = Factory<A>()();
pA->show();
Factory<A>()()->show();
return 0;
}
I am trying to deal with friend class for the first time. I wrote the code below:
class Kind{
private:
friend class Type;
int x;
public:
Kind(){ x=0; }
void setX(int X) { x =X; }
int getX() { return x; }
};
class Type: public Kind {
public:
friend class Kind;
Type(){ }
Kind root;
root.x=3;
};
The compiler tells me that I can not do root.x=3;, What is the problem??
The problem is your trying to execute a statement in a place where the compiler is expecting member declarations. Try putting it into a method
class Type : public Kind {
...
void Example() {
Kind root;
root.x = 3;
}
};
You cannot do the assignment as part of the class declaration. Do it in a member function instead.