[C++] ctor & copy-ctor

Pagina: 1
Acties:

  • riezebosch
  • Registratie: Oktober 2001
  • Laatst online: 21:56
Is het mogelijk om vanuit de copy-constructor de constructor eerst aan te roepen? Zoals bij Java je als eerste regel this() kan doen. Heb al geprobeerd door MijnClass() aan te roepen, maar dan wordt na het voltooien van de constructor ook de destructor automatisch uitgevoerd...

Het idee is dat ik in de assignment-operator de destructor aanroep om het huidige object te legen, en vervolgens de copy-constructor met als argument de rhs. Waarna de copy-constructor eerst de constructor aanroept om het object opnieuw te initialiseren en daarna de elementen uit rhs kopieërt naar het huidige object. Hiermee wil ik dubbele code vermijden.

Canon EOS 400D + 18-55mm F3.5-5.6 + 50mm F1.8 II + 24-105 F4L + 430EX Speedlite + Crumpler Pretty Boy Back Pack


  • .oisyn
  • Registratie: September 2000
  • Laatst online: 15:32

.oisyn

Moderator Devschuur®

Demotivational Speaker

maar dan wordt na het voltooien van de constructor ook de destructor automatisch uitgevoerd...
Da's logisch, je creeert namelijk een nieuw temporary object.
En nee, het kan helaas niet zoals in java, dan heb je een extra functie nodig die je kan aanroepen.

Give a man a game and he'll have fun for a day. Teach a man to make games and he'll never have fun again.


  • riezebosch
  • Registratie: Oktober 2001
  • Laatst online: 21:56
Ok, duidelijk :) had daar ook al aan gedacht (als alternatief), maar heb er niet zo'n zin in... Laat de code dan maar beetje zelfde zijn :P

Canon EOS 400D + 18-55mm F3.5-5.6 + 50mm F1.8 II + 24-105 F4L + 430EX Speedlite + Crumpler Pretty Boy Back Pack


  • .oisyn
  • Registratie: September 2000
  • Laatst online: 15:32

.oisyn

Moderator Devschuur®

Demotivational Speaker

Even ter aanvulling, heeft niet echt te maken met je probleem:

Je kunt je object wel destructen en opnieuw constructen mbv placement new

C++:
1
2
3
4
5
6
7
8
9
10
#include <new>

struct A
{
    void reconstruct ()
    {
        this->~A ();
        new (this) A ();
    }
};


(dus wel even <new> includen)

[ Voor 3% gewijzigd door .oisyn op 04-12-2003 21:15 ]

Give a man a game and he'll have fun for a day. Teach a man to make games and he'll never have fun again.


  • riezebosch
  • Registratie: Oktober 2001
  • Laatst online: 21:56
maar dat kan dan toch ook vanuit de copy-constructor, maar moet je niet altijd met new gealloceerd geheugen ook weer vrijmaken met delete?

[ Voor 12% gewijzigd door riezebosch op 04-12-2003 21:30 ]

Canon EOS 400D + 18-55mm F3.5-5.6 + 50mm F1.8 II + 24-105 F4L + 430EX Speedlite + Crumpler Pretty Boy Back Pack


  • .oisyn
  • Registratie: September 2000
  • Laatst online: 15:32

.oisyn

Moderator Devschuur®

Demotivational Speaker

Het is een placement new, die geeft gewoon het adres terug dat je als parameter meegeeft (this dus in dit geval). Die constructie zorgt ervoor dat de contructor van het betreffende object op dat adres wordt aangeroepen. Dus er wordt geen geheugen gealloceerd, de constructor wordt slechts aangeroepen.

Je kunt het in feite ook doen vanuit je constructor, maar echt netjes is het niet, omdat je object dan nog niet in volledig geconstructe staat is. Bovendien loop je dan kans dat de constructoren van de base classes meerdere keren worden aangeroepen. Je moet dus eerst de destructor aanroepen voordat je de constructor aanroept dmv de placing new. Maar ja, de destructor is pas zinnig op het moment dat je object in geconstructe staat is en alle locale classvariabelen geinitialiseerd zijn (dus je moet het object sowieso eerst constructen voordat je de destructor aan kan roepen ;))

Give a man a game and he'll have fun for a day. Teach a man to make games and he'll never have fun again.


  • .oisyn
  • Registratie: September 2000
  • Laatst online: 15:32

.oisyn

Moderator Devschuur®

Demotivational Speaker

Je gaat overigens wel problemen krijgen als tussendoor een exception gegooid wordt, met name in de destructor. Maar de vraag is natuurlijk of het sowieso zinnig is om vanuit een destructor een exception te gooien ;)

Give a man a game and he'll have fun for a day. Teach a man to make games and he'll never have fun again.


  • MSalters
  • Registratie: Juni 2001
  • Laatst online: 09-04 22:08
Als je zo nodig je members default-initialzied wil hebben kun je natuurlijk *this=MyClass() doen.

Man hopes. Genius creates. Ralph Waldo Emerson
Never worry about theory as long as the machinery does what it's supposed to do. R. A. Heinlein


  • whoami
  • Registratie: December 2000
  • Laatst online: 15:14
Bedoel je nu dat je in C++ dit op een of andere manier niet kan doen:

code:
1
2
3
4
public MyClass(int i) : MyClass()
{
   miBlaat = i;
}


:?

https://fgheysels.github.io/


  • MSalters
  • Registratie: Juni 2001
  • Laatst online: 09-04 22:08
Ja, natuurlijk kan dat niet. De initializer list mag alleen members en base classes bevatten.
(Wordt overigens aan gewerkt)

Man hopes. Genius creates. Ralph Waldo Emerson
Never worry about theory as long as the machinery does what it's supposed to do. R. A. Heinlein


  • curry684
  • Registratie: Juni 2000
  • Laatst online: 12-05 22:23

curry684

left part of the evil twins

En mental note: als je een Initialize-functie maakt die vanuit iedere ctor wordt aangeroepen mag die *niet* virtual of pure virtual zijn omdat je vtable tijdens de construction nog niet beschikbaar is.

* curry684 heeft hier ooit eens per ongeluk tegen gezondigd en 3 dagen moeten zoeken naar het probleem.... |:(

Professionele website nodig?


  • whoami
  • Registratie: December 2000
  • Laatst online: 15:14
MSalters schreef op 05 december 2003 @ 11:14:
Ja, natuurlijk kan dat niet. De initializer list mag alleen members en base classes bevatten.
(Wordt overigens aan gewerkt)
:?
Als je de gewone, 0 argument constructor hebt gedefinieerd is 'ie toch ook een member van je class ?
curry684 schreef op 05 december 2003 @ 11:37:
En mental note: als je een Initialize-functie maakt die vanuit iedere ctor wordt aangeroepen mag die *niet* virtual of pure virtual zijn omdat je vtable tijdens de construction nog niet beschikbaar is.

* curry684 heeft hier ooit eens per ongeluk tegen gezondigd en 3 dagen moeten zoeken naar het probleem.... |:(
Da's in C# wel mogelijk. :P :Y)

[ Voor 42% gewijzigd door whoami op 05-12-2003 11:53 ]

https://fgheysels.github.io/


  • curry684
  • Registratie: Juni 2000
  • Laatst online: 12-05 22:23

curry684

left part of the evil twins

whoami schreef op 05 december 2003 @ 11:53:
[...]
Da's in C# wel mogelijk. :P :Y)
Daarom is C++ ook een 'iets' snellere en dichter-bij-assembler taal :z :+

Professionele website nodig?


  • .oisyn
  • Registratie: September 2000
  • Laatst online: 15:32

.oisyn

Moderator Devschuur®

Demotivational Speaker

curry684 schreef op 05 december 2003 @ 11:37:
En mental note: als je een Initialize-functie maakt die vanuit iedere ctor wordt aangeroepen mag die *niet* virtual of pure virtual zijn omdat je vtable tijdens de construction nog niet beschikbaar is.

* curry684 heeft hier ooit eens per ongeluk tegen gezondigd en 3 dagen moeten zoeken naar het probleem.... |:(
nou dat mag wel, het wordt alleen een directe call, en geen virtual call. Je kunt geen virtual methode implementeren in een derived class die door de base constructor wordt aangeroepen, want die roept dan gewoon z'n eigen implementatie aan (en als ie in de base pure was dan krijg je meestal sowieso een compile warning). Want in de constructor is de class ook gewoon van het type van de huidige constructor, en niet een van z'n subclasses. Hij wordt pas dat type als de constructor van dat type is aangeroepen

En ja, in een constructor wordt ook de vtable geinitializeerd naar dat type, dus het is vrij logisch :)

Give a man a game and he'll have fun for a day. Teach a man to make games and he'll never have fun again.


  • curry684
  • Registratie: Juni 2000
  • Laatst online: 12-05 22:23

curry684

left part of the evil twins

.oisyn schreef op 05 december 2003 @ 15:09:
[...]
nou dat mag wel, het wordt alleen een directe call, en geen virtual call. Je kunt geen virtual methode implementeren in een derived class die door de base constructor wordt aangeroepen, want die roept dan gewoon z'n eigen implementatie aan (en als ie in de base pure was dan krijg je meestal sowieso een compile warning). Want in de constructor is de class ook gewoon van het type van de huidige constructor, en niet een van z'n subclasses. Hij wordt pas dat type als de constructor van dat type is aangeroepen
Het verschil tussen 'mogen' en 'levert wild onvoorspelbare en idiote effecten' vind ik in dit geval dermate klein dat ik de term 'dat mag niet' zeer verantwoord vind :z
En ja, in een constructor wordt ook de vtable geinitializeerd naar dat type, dus het is vrij logisch :)
Tuurlijk is het logisch. Ook lullig :D

Professionele website nodig?


  • .oisyn
  • Registratie: September 2000
  • Laatst online: 15:32

.oisyn

Moderator Devschuur®

Demotivational Speaker

Nou ja ik vind er niets onvoorspelbaars aan, maar goed :)
Een Base is at construction time gewoon een Base, en geen Derived. Derhalve roept het ook geen virtual methoden aan van Derived, net als bij het geval dat je gewoon een Base instantieert.

En het heeft ook geen enkel zin als het wel zou kunnen. De constructor van Derived is nog niet aangeroepen, dus de members van Derived zijn ook nog niet geinitializeerd.

Give a man a game and he'll have fun for a day. Teach a man to make games and he'll never have fun again.


  • MSalters
  • Registratie: Juni 2001
  • Laatst online: 09-04 22:08
whoami schreef op 05 december 2003 @ 11:53:
[...]
:?
Als je de gewone, 0 argument constructor hebt gedefinieerd is 'ie toch ook een member van je class ?
Je weet vast wel wat ik bedoel; C::C ( args ) : Base(...), Base(...), datamember(...), datamember(...) { /***/ }

Dit is overigens een geval van geen bijzonder goede reden. Er zitten een paar subtiliteiten in (object compleet na ctor exit, maar als je 2 ctors gebruikt, wanneer is het object dan compleet?) en wat implementatie details (in theorie interactie met new), maar niks groots.

Man hopes. Genius creates. Ralph Waldo Emerson
Never worry about theory as long as the machinery does what it's supposed to do. R. A. Heinlein

Pagina: 1