Hoe ga je om met een fout “kan abstracte klasse niet instantiëren” in C++?

Hoe ga je om met een fout “kan abstracte klasse niet instantiëren” in C++?
Ik heb hier enkele van de soortgelijke fouten bekeken en geen van hen lijkt precies hetzelfde te zijn of het probleem dat ik heb. Maar nogmaals, ik geef toe dat er meerdere zijn om te bespreken. Hier is de compileerfout:

[img]http://i67.photobucket.com/albums/h292/athono/cannotinstantiateabstractclass.png[ /img]

Dit leidt me naar deze pagina:
http://msdn.microsoft.com/query/dev10.query?appId=Dev10IDEF1&l=EN-US&k=k(C2259);k(VS.ERRORLIST)&rd=true
Compileerfout C2259 is van een C++-programma, maar de pagina noemt de abstracte klasse een “interface”:

Telkens wanneer u afleidt van een interface en de interfacemethoden implementeert in de afgeleide klasse met andere toegangsrechten dan openbaar, kunt u C2259 ontvangen. Dit gebeurt omdat de compiler verwacht dat de interfacemethoden die in de afgeleide klasse zijn geïmplementeerd, openbare toegang hebben. Wanneer u de lidfuncties implementeert voor een interface met beperktere toegangsrechten, beschouwt de compiler ze niet als implementaties voor de interfacemethoden die in de interface zijn gedefinieerd, waardoor de afgeleide klasse een abstracte klasse wordt.

Er zijn twee mogelijke oplossingen voor het probleem:

Maak de toegangsrechten openbaar voor de geïmplementeerde methoden.

Gebruik de scope resolutie-operator voor de interfacemethoden die zijn geïmplementeerd in de afgeleide klasse om de naam van de geïmplementeerde methode te kwalificeren met de naam van de interface.

Het slechte nieuws is dat ik alle methoden in de klas al openbaar heb gemaakt:

class AmbientOccluder: public Light {
    public:
        AmbientOccluder(void); 

Antwoord 1, autoriteit 100%

De fout betekent dat er enkele methoden van de klasse zijn die niet zijn geïmplementeerd. Je kunt zo’n klasse niet instantiëren, dus je kunt niets anders doen dan allemethoden van de klasse implementeren.

Aan de andere kant is een algemeen patroon om een concrete klasse te instantiëren en deze toe te wijzen aan een pointer van een abstracte basisklasse:

class Abstract { /* stuff */ 4};
class Derived : virtual public Abstract { /* implement Abstract's methods */ };
Abstract* pAbs = new Derived; // OK

Even terzijde, om geheugenbeheerproblemen met de bovenstaande regel te voorkomen, kunt u overwegen een slimme aanwijzer, zoals een `std::unique_ptr:

std::unique_ptr<Abstract> pAbs(new Derived);

Antwoord 2, autoriteit 80%

Visual Studio’s Foutenlijst-paneel toont alleen de eerste regel van de fout. Roep View>Outputop en ik wed dat je zoiets ziet als:

c:\path\to\your\code.cpp(42): error C2259: 'AmbientOccluder' : cannot instantiate abstract class
          due to following members:
          'ULONG MysteryUnimplementedMethod(void)' : is abstract
          c:\path\to\some\include.h(8) : see declaration of 'MysteryUnimplementedMethod'

Antwoord 3, autoriteit 22%

Een abstracte klasse kan niet per definitie worden geïnstantieerd. Om deze klasse te gebruiken, moet u een concrete subklasse maken die alle virtuele functies van de klasse implementeert. In dit geval heeft u hoogstwaarschijnlijk niet alle virtuele functies geïmplementeerd die zijn gedeclareerd in Light. Dit betekent dat AmbientOccluderstandaard een abstracte klasse is. Om u verder te kunnen helpen, moet u de details van de Light-klasse vermelden.


Antwoord 4, autoriteit 9%

Geef implementatie voor alle pure virtuele functies die de klasse heeft.


Antwoord 5, autoriteit 2%

Waarom kunnen we Object of Abstract Class niet maken?
Wanneer we een pure virtuele functie maken in de klasse Abstract, reserveren we een slot voor een functie in de VTABLE (bestudeerd in het laatste onderwerp), maar plaatsen we geen adres in dat slot. Daarom zal de VTABLE onvolledig zijn.
Omdat de VTABLE for Abstract-klasse onvolledig is, zal de compiler het maken van een object voor een dergelijke klasse niet toestaan en een foutmelding weergeven wanneer u dit probeert.

Puur virtuele definities

Pure Virtual-functies kunnen een kleine definitie krijgen in de klasse Abstract, die u wilt dat alle afgeleide klassen hebben. U kunt nog steeds geen object van de klasse Abstract maken.
Ook moet de Pure Virtual-functie buiten de klassendefinitie worden gedefinieerd. Als u het binnen de klassedefinitie definieert, geeft complier een foutmelding. Inline pure virtuele definitie is illegaal.


Antwoord 6

Ik heb deze vraag hier beantwoord..Covariante virtuele functies retourtype probleem

Kijk of het voor iemand helpt.


Antwoord 7

In mijn geval heb ik een functie gedeclareerd in het COM Control .idl-bestand zoals

[id(1)] HRESULT MyMethod([in]INT param);

maar niet gedeclareerd in mijn interface .hbestand zoals dit

STDMETHOD(MyMethod)(INT param);

Probleem opgelost door bovenstaande regel toe te voegen aan mijn interface .h-bestand

dit kan iemand helpen.


Antwoord 8

Als iemand deze fout van een functie krijgt, probeer dan in plaats daarvan een verwijzing naar de abstracte klasse in de parameters te gebruiken.

void something(Abstract bruh){
}

naar

void something(Abstract& bruh){
}

Other episodes