Du må være registrert og logget inn for å kunne legge ut innlegg på freak.no
X
LOGG INN
... eller du kan registrere deg nå
Dette nettstedet er avhengig av annonseinntekter for å holde driften og videre utvikling igang. Vi liker ikke reklame heller, men alternativene er ikke mange. Vær snill å vurder å slå av annonseblokkering, eller å abonnere på en reklamefri utgave av nettstedet.
  8 1175
Hei!

Jeg har en del problemer med virtuelle funksjoner. Vi tar for oss x.cpp:

Kode

#include <stdio.h>

class A
{
public:
        virtual int a() = 0;
        int b() { return 1; }
};

class B
{
public:
        int a() { return 0; };
};

class C : public A, public B
{
};

int main()
{
        C c;
        printf("%d, %d\n", c.a(), c.b());
}
Ønsket output:

Kode

0, 1
Problemet er at under kompilering av denne koden, får jeg feilmelding fra gcc:

Kode

x.cpp: In function ‘int main()’:
x.cpp:22: error: cannot declare variable ‘c’ to be of abstract type ‘C’
x.cpp:17: note:   because the following virtual functions are pure within ‘C’:
x.cpp:6: note:  virtual int A::a()
x.cpp:23: error: request for member ‘a’ is ambiguous
x.cpp:13: error: candidates are: int B::a()
x.cpp:6: error:                 virtual int A::a()
Hvordan kan jeg få disse klassene til å virke sammen?
Ser du har et par skrivefeil, men prøvde å få skrevet det oversiktlig og enkelt, se om du forstår det her, ellers si ifra :-)

Kode

#include <iostream>
using namespace std;

class A
{
private:
	int aa;
public:
	A()	{ aa=0; }		//Constructor til A, denne kalles når 'A' opprettes, eller instans av C opprettes som child.
	void skrivA()	{ cout << aa << endl;	}	//Skriver ut verdien 'aa'
};

class B 
{
private:
	int bb;
public:
	B()	{ bb=1;	}		//Constructor til B, se beskrivelse til A.
	void skrivB()	{ cout << bb << endl;	}	//Skriver ut verdien til 'bb'
};

class C : public A, public B	//Klasse C er barn av A og B, og inneholder dets funksjoner
{

};

int main()
{
        C c;
		c.skrivA();
		c.skrivB();
		system("pause");
		return 0;
}
Edit: Virtual brukes om andre funksjoner skal ha en 'kjøkkenvei'/tilgang til funksjon\variabel. Dette trenger du ikke å benytte deg av med klasser. Virtual kan bli sett på som griseprogrammering av noen :-)
Sist endret av prenix; 24. februar 2009 kl. 22:30.
pebkac
slicer's Avatar
Trådstarter
Hei,

Problemet med denne enkle løsningen uten virtuals er at det løser ikke problemet mitt.

Jeg har, i mitt program, flere klasser som skal kunne fungere sammen med hverandre, slik at jeg ikke trenger å vite hvilken klasse et objekt er, bare hvilken klasse det arver fra. Når jeg lager en pointer til A, og setter den til minneadressen på "c", så skal jeg kunne kalle både a() og b() i denne.

Jeg vil at (de eventuelle) funksjonene i B og C skal overstyre det som er i A.

Koden du skrev, illustrerer bare arving - ikke virtual.

Håper jeg forklarte meg godt nok her :/
Sist endret av slicer; 25. februar 2009 kl. 08:06.
Tror jeg skjønte hva du ville oppnå. Dette kan gjøres slik:

Kode

#include <iostream>
using namespace std;

class A
{
private:
	int aa;
public:
	virtual void skrivA() { aa = 0 ; cout << "aa: " << aa << endl; }
};

class B : public A
{
private:
	int bb;
public:
	void skrivB() { bb=1; cout << "bb: " << bb << endl; }
};
void main()
{
	B b;
	b.skrivA();
	b.skrivB();

	system("pause");
}
Var det slik du mente?

Edit: Eller var det noe slik du tenkte på?

Kode

#include <iostream>
using namespace std;

class A
{
private:
	int aa;
public:
	A() { cout << "Constructor A" << endl; }
	virtual void skrivA() { aa = 0 ; cout << "aa: " << aa << endl; }
};

class B : public A
{
private:
	int bb;
public:
	B() { cout << "Constructor B" << endl; A::skrivA();}
	void skrivB() { bb=1; cout << "bb: " << bb << endl; }
};
void main()
{
	B b;
	//b.skrivA();
	//b.skrivB();

	system("pause");
}
Hvorav skrivA() faktisk ikke trenger å være virtual, ettersom du kaller direkte funksjonen ifra A.

Om ikke, vis meg gjerne hvordan koden din ser ut, så blir det litt enklere å forstå :-)
Sist endret av prenix; 25. februar 2009 kl. 16:41. Grunn: Automatisk sammenslåing med etterfølgende innlegg.
Du må ha en klasse som arver fra A hvor du lager en a() funksjon.
I klasse A definerer du funksjonen a() som en "pure virtual" funksjon, du må da ha en annen klasse som arver fra A, hvor du definerer a() funksjonen.

Kode

class A
{
 virtual int a() = 0;
};

class B : public A
{
 int a() { return 1; }
 int b() { return 2; }
};
Sist endret av Nine; 25. februar 2009 kl. 20:13. Grunn: Semikolon!
Sitat av Nine Vis innlegg
Du må ha en klasse som arver fra A hvor du lager en a() funksjon.
I klasse A definerer du funksjonen a() som en "pure virtual" funksjon, du må da ha en annen klasse som arver fra A, hvor du definerer a() funksjonen.

Kode

class A
{
 virtual int a() = 0;
};

class B : public A
{
 int a() { return 1; }
 int b() { return 2; }
};
Vis hele sitatet...
Det du gjorde der er jo helt poengløst, men antagelig svaret som har vært nærmest det han leter etter til nå.

Kode

#include <stdio.h>

class A
{
public:
        virtual int a() = 0;
        int b() { return 1; }
};

class B : public A
{
public:
        int a() { return 0; };
};

int main()
{
        B foobar;
        printf("%d, %d\n", foobar.a(), foobar.b());
}
Sist endret av TanteSpiker; 25. februar 2009 kl. 20:30.
pebkac
slicer's Avatar
Trådstarter
Problemet mitt ligger i at jeg trenger en klasse C som arver funksjoner fra både A og B - men som ikke inneholder den som er pure virtual i klasse A. Klasse B inneholder denne funksjonen, men det ser ikke ut til å virke helt bra.

Er det noen måte å gjennomføre det på?
Er du i en situasjon hvor du trenger akkuratt dette? Kan du forklare hvorfor du trenger å gjøre det?
Jeg bare ser ikke når dette skulle være nødvendig.
pebkac
slicer's Avatar
Trådstarter
Jeg omgikk heller problemet med å implementere Bs funksjonalitet i A.