<?xml version="1.0" encoding="UTF-8"?><rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:content="http://purl.org/rss/1.0/modules/content/" xmlns:atom="http://www.w3.org/2005/Atom" version="2.0"><channel><title><![CDATA[Array einer eigenen Klasse dynamisch erweitern -&amp;gt;Frage zum  Destruktor [GELÖST]]]></title><description><![CDATA[<p>Hiho,</p>
<p>ich hab folgende Klasse:</p>
<pre><code class="language-cpp">class Personenliste{
	Person* p;
	size_t gr;
	int anzahl;
public:
	Personenliste(size_t s=1);
	~Personenliste();

	int getGröße();
	int getAnzahl();
	Person getPerson(int index);
	void addPerson(Person per);
};
</code></pre>
<p>Und die addPerson Funktion schaut so aus:</p>
<pre><code class="language-cpp">void Personenliste::addPerson(Person per){
	p[anzahl]=per;
	anzahl++;
	if(anzahl==gr){
		Person* neu=new Person[gr=gr+1];
		~Personenliste();
		p=neu;

	}
	cout &lt;&lt; &quot;Person eingefuegt&quot; &lt;&lt; endl;
}
</code></pre>
<p>Diese Funktion soll immer wenn das Feld von Personen p voll ist, neuen Speicherplatz mit der bisherigen Feldgröße +1 bereitstellen und den alten nicht mehr gebrauchten freigeben.<br />
Ist mein Ansatz hier richtig, benutze ich den Destruktor hier richtig?</p>
<p>Hier noch Kon- und Destruktor</p>
<pre><code class="language-cpp">Personenliste::Personenliste(size_t s){
	p=new Person[gr=s];
	anzahl=0;
}

Personenliste::~Personenliste(){
	delete[] p;
}
</code></pre>
<p>edit: Mir fällt grad auf, dass der Aufruf des Destruktors</p>
<pre><code class="language-cpp">~Personenliste()
</code></pre>
<p>in der Funktion addFunktion mir eine Fehlermeldung auswirft:</p>
<blockquote>
<p>error C2675: Unärer Operator '~': 'Personenliste' definiert diesen Operator oder eine Konvertierung in einen für den vordefinierten Operator geeigneten Typ nicht</p>
</blockquote>
<p>Nur mit &quot;delete[] p&quot; funktionierts, was ja eigentlich der einzige Inhalt von<br />
&quot;~Personenliste()&quot; ist.<br />
Woran liegt das?</p>
]]></description><link>https://www.c-plusplus.net/forum/topic/301465/array-einer-eigenen-klasse-dynamisch-erweitern-gt-frage-zum-destruktor-gelöst</link><generator>RSS for Node</generator><lastBuildDate>Wed, 12 Aug 2026 00:00:42 GMT</lastBuildDate><atom:link href="https://www.c-plusplus.net/forum/topic/301465.rss" rel="self" type="application/rss+xml"/><pubDate>Wed, 28 Mar 2012 08:15:30 GMT</pubDate><ttl>60</ttl><item><title><![CDATA[Reply to Array einer eigenen Klasse dynamisch erweitern -&amp;gt;Frage zum  Destruktor [GELÖST] on Thu, 29 Mar 2012 04:50:35 GMT]]></title><description><![CDATA[<p>Hiho,</p>
<p>ich hab folgende Klasse:</p>
<pre><code class="language-cpp">class Personenliste{
	Person* p;
	size_t gr;
	int anzahl;
public:
	Personenliste(size_t s=1);
	~Personenliste();

	int getGröße();
	int getAnzahl();
	Person getPerson(int index);
	void addPerson(Person per);
};
</code></pre>
<p>Und die addPerson Funktion schaut so aus:</p>
<pre><code class="language-cpp">void Personenliste::addPerson(Person per){
	p[anzahl]=per;
	anzahl++;
	if(anzahl==gr){
		Person* neu=new Person[gr=gr+1];
		~Personenliste();
		p=neu;

	}
	cout &lt;&lt; &quot;Person eingefuegt&quot; &lt;&lt; endl;
}
</code></pre>
<p>Diese Funktion soll immer wenn das Feld von Personen p voll ist, neuen Speicherplatz mit der bisherigen Feldgröße +1 bereitstellen und den alten nicht mehr gebrauchten freigeben.<br />
Ist mein Ansatz hier richtig, benutze ich den Destruktor hier richtig?</p>
<p>Hier noch Kon- und Destruktor</p>
<pre><code class="language-cpp">Personenliste::Personenliste(size_t s){
	p=new Person[gr=s];
	anzahl=0;
}

Personenliste::~Personenliste(){
	delete[] p;
}
</code></pre>
<p>edit: Mir fällt grad auf, dass der Aufruf des Destruktors</p>
<pre><code class="language-cpp">~Personenliste()
</code></pre>
<p>in der Funktion addFunktion mir eine Fehlermeldung auswirft:</p>
<blockquote>
<p>error C2675: Unärer Operator '~': 'Personenliste' definiert diesen Operator oder eine Konvertierung in einen für den vordefinierten Operator geeigneten Typ nicht</p>
</blockquote>
<p>Nur mit &quot;delete[] p&quot; funktionierts, was ja eigentlich der einzige Inhalt von<br />
&quot;~Personenliste()&quot; ist.<br />
Woran liegt das?</p>
]]></description><link>https://www.c-plusplus.net/forum/post/2196084</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/2196084</guid><dc:creator><![CDATA[butterbemme]]></dc:creator><pubDate>Thu, 29 Mar 2012 04:50:35 GMT</pubDate></item><item><title><![CDATA[Reply to Array einer eigenen Klasse dynamisch erweitern -&amp;gt;Frage zum  Destruktor [GELÖST] on Wed, 28 Mar 2012 09:08:49 GMT]]></title><description><![CDATA[<p>butterbemme schrieb:</p>
<blockquote>
<p>Ist mein Ansatz hier richtig, benutze ich den Destruktor hier richtig?</p>
</blockquote>
<p>Nein. Es gibt nur gaaaaaaaaaanz wenige Fälle, wo es Sinn macht, den Destruktor ausdrücklich aufzurufen, so wenig, dass ich Dir keinen nennen kann. Merk Dir einfach: Das tut man nicht!<br />
Gib den Speicher mit delete[] frei.</p>
<p>Noch besser, benutze statt eines Arrays std::vector, der ist genau dafür gemacht!</p>
]]></description><link>https://www.c-plusplus.net/forum/post/2196100</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/2196100</guid><dc:creator><![CDATA[Belli]]></dc:creator><pubDate>Wed, 28 Mar 2012 09:08:49 GMT</pubDate></item><item><title><![CDATA[Reply to Array einer eigenen Klasse dynamisch erweitern -&amp;gt;Frage zum  Destruktor [GELÖST] on Wed, 28 Mar 2012 09:09:13 GMT]]></title><description><![CDATA[<p>butterbemme schrieb:</p>
<blockquote>
<p>Ist mein Ansatz hier richtig, benutze ich den Destruktor hier richtig?</p>
</blockquote>
<p>Nein. Destruktor hat da NICHTS zu suchen. Du willst da nur ein neues Array anlegen, das alte freigeben und den Member-Pointer umsetzen. Destruktor ist was anderes, das signalisiert &quot;Objekt wird zerstört&quot;, und das willst du ja nicht, oder?</p>
<p>Ansonsten: Ist das eine Übung, oder kennst du einfach std::vector noch nicht?</p>
]]></description><link>https://www.c-plusplus.net/forum/post/2196101</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/2196101</guid><dc:creator><![CDATA[arghonaut]]></dc:creator><pubDate>Wed, 28 Mar 2012 09:09:13 GMT</pubDate></item><item><title><![CDATA[Reply to Array einer eigenen Klasse dynamisch erweitern -&amp;gt;Frage zum  Destruktor [GELÖST] on Wed, 28 Mar 2012 09:23:19 GMT]]></title><description><![CDATA[<p>Normalerweise wird ein Objekt automatisch gelöscht, es sei denn es liegt auf dem Heap. Nur die Objekte, die mit new/<s>malloc</s> erzeugt wurden landen dort.<br />
Deswegen wird ein Destruktor nur bei Heap-Objekten explizit aufgerufen. Und zwar mit dem Schlüsslwort «delete».</p>
<pre><code class="language-cpp">Object* heapO = new Object;
delete heapO;
</code></pre>
<p>das bedeutet anstatt</p>
<pre><code class="language-cpp">~Personenliste();
</code></pre>
<p>muss Du</p>
<pre><code class="language-cpp">delete this
</code></pre>
<p>verwenden.</p>
<p>Das ist zu 99% der Fälle eine sehr schlechte Entscheidung. In dem Moment ist deine Instanz quasi sofort weg. Die gibt es nicht mehr!!<br />
Um «delete this» in eine Membermethode schreiben zu können muss Du viele Dinge sicherstellen:<br />
1. Die Instanz wurde mit new erzeugt.<br />
2. Die Methode greift nicht mehr auf die Member von der Instanz und ist die letzte für diese Instanz aufgerufene Methode.<br />
2. Es wird nie mehr auf diese Instanz zugegriffen. ( keine Querverweise ).</p>
<p>Dein Problem kannst du einfach lösen indem du anstatt eines Arrays einen von den STL-containern nimmst: z.B.</p>
<pre><code class="language-cpp">std::vector&lt; Person &gt; v;
p.push_back( p )

// oder

std::deque&lt; Person &gt; d;
d.push_back( p );

// oder std::list&lt; Person &gt;, std::queue.. usw.
</code></pre>
<p>Hier ist ein Beispiel:</p>
<pre><code class="language-cpp">#include &lt;vector&gt;

class Personenliste
{
public:
	Personenliste( size_t anzahlElemente = 1 ) : leute() { leute.reserve( anzahlElemente ); }
    //~Personenliste();

    size_t Größe() const
	{
		return leute.capacity();
	}

    size_t Anzahl() const
	{
		return leute.size();
	}

    Person GetPerson( size_t index ) const		// checked.
	{
		return leute.at( index );
	}

	Person operator []( size_t index ) const	// unchecked
	{
		return leute[ index ];
	}

	void addPerson( Person&amp; const mensch )
	{
		leute.push_back( mensch );
	}

private:
    std::vector&lt; Person &gt; leute; // :)
};
</code></pre>
]]></description><link>https://www.c-plusplus.net/forum/post/2196106</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/2196106</guid><dc:creator><![CDATA[Travor]]></dc:creator><pubDate>Wed, 28 Mar 2012 09:23:19 GMT</pubDate></item><item><title><![CDATA[Reply to Array einer eigenen Klasse dynamisch erweitern -&amp;gt;Frage zum  Destruktor [GELÖST] on Wed, 28 Mar 2012 09:36:06 GMT]]></title><description><![CDATA[<p>butterbemme schrieb:</p>
<blockquote>
<p>Und die addPerson Funktion schaut so aus:</p>
<pre><code class="language-cpp">void Personenliste::addPerson(Person per){
	p[anzahl]=per;
	anzahl++;
	if(anzahl==gr){
		Person* neu=new Person[gr=gr+1];
		~Personenliste();
		p=neu;
		
	}
	cout &lt;&lt; &quot;Person eingefuegt&quot; &lt;&lt; endl;
}
</code></pre>
</blockquote>
<p>Auweia! <code>per</code> bitte per ref-auf-const übergeben. Die Puffergröße sollte sich verdoppeln und nicht immer nur ein Element größer werden. Damit erreichst Du dann beim wiederholten addPerson amortisiert konstante Laufzeit pro Aufruf statt eine Laufzeit, die abhängig von der Größe des Puffers ist. Destruktor ruft man (so gut wie) nie selbst auf! Jedenfalls nicht hier! Die alten Personen werden nirgenswo in den neuen Puffer kopiert. Du verletzt die Dreierregel und bekommst murksiges Verhalten, wenn Du so ein Personenliste Objekt kopierst.</p>
<p><code>class Personenliste</code> kannst du komplett gegen <code>std::vector&lt;Person&gt;</code> eintauschen. <code>std::vector</code> hat all diese genannten Probleme nicht.</p>
]]></description><link>https://www.c-plusplus.net/forum/post/2196107</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/2196107</guid><dc:creator><![CDATA[krümelkacker]]></dc:creator><pubDate>Wed, 28 Mar 2012 09:36:06 GMT</pubDate></item><item><title><![CDATA[Reply to Array einer eigenen Klasse dynamisch erweitern -&amp;gt;Frage zum  Destruktor [GELÖST] on Wed, 28 Mar 2012 11:06:14 GMT]]></title><description><![CDATA[<p>Also std::vector is mir bekannt.<br />
Ich versuch mich grade in selbstdefinierte Klassen einzuarbeiten und will ein bisschen mit new und delete rumspielen, deswegen mein etwas umständlicher Code.<br />
Ist also sozusagen eine Übung.</p>
<p><a class="plugin-mentions-user plugin-mentions-a" href="https://www.c-plusplus.net/forum/uid/22666">@Belli</a>: du meinst ich solle nur &quot;delete[] p&quot; benutzen. Aber genau das und zwar nur das, steht ja auch in meinem selbstdefinierten Destruktor ~Personenliste().<br />
Wo ist dann also der Unterschied? Oder wird da implizit noch etwas anderes im Hintergrund gemacht.</p>
<p>krümelkacker schrieb:</p>
<blockquote>
<p>... Die alten Personen werden nirgenswo in den neuen Puffer kopiert. Du verletzt die Dreierregel und bekommst murksiges Verhalten, wenn Du so ein Personenliste Objekt kopierst...</p>
</blockquote>
<p>Jo da hast du Recht. Um die Dreierregel hab ich mich noch nicht gekümmert, und auch das Kopieren der Personen aus dem alten Speicherbereich fehlt noch.</p>
<p>Dann lass ich wohl vorerst die Finger von selbstdefinierten Destruktor.<br />
Aber zu guter Letzt würd mich noch interessieren warum der direkte Destruktoraufruf (~Personenliste()) in der Funktion &quot;addPerson()&quot; nicht funktioniert hat.<br />
Ich bekomm da immer</p>
<blockquote>
<p>Unärer Operator '~': 'Personenliste' definiert diesen Operator oder eine Konvertierung in einen für den vordefinierten Operator geeigneten Typ nicht</p>
</blockquote>
<p>Muss ich diesen Operator erst für mein Vorhaben extra definieren. Dachte eigentlich Destruktoren haben diese Form und werden dann auch so aufgerufen</p>
]]></description><link>https://www.c-plusplus.net/forum/post/2196135</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/2196135</guid><dc:creator><![CDATA[butterbemme]]></dc:creator><pubDate>Wed, 28 Mar 2012 11:06:14 GMT</pubDate></item><item><title><![CDATA[Reply to Array einer eigenen Klasse dynamisch erweitern -&amp;gt;Frage zum  Destruktor [GELÖST] on Wed, 28 Mar 2012 11:49:58 GMT]]></title><description><![CDATA[<pre><code class="language-cpp">void Personenliste::addPerson( Person&amp; const person )
{
    if ( anzahl &gt;= gr )
    {
        Person* tmp = 0;
        size_t neuAnzahl = gr + gr/ 2;
        if ( neuAnzahl &lt; gr + 1  &amp;&amp;  gr + 1 &gt; gr )
        {
            neuAnzahl = gr + 1;
        }
        else throw std::bad_alloc( &quot;Speicher voll&quot; ); //  :) 

        Person* tmp = new ( nothrow ) Person[ neuAnzahl ];
        if ( tmp == 0 ) throw std::bad_alloc();

        memcpy( tmp, p, min( gr, neuAnzahl ) * sizeof ( Person ) );
        delete[] p;
        p = tmp;
        gr = newAnzahl;
    }
    p[ anzahl ] = person;
    ++anzahl;
}
</code></pre>
<p>vorausgesetzt Person ist POD..</p>
]]></description><link>https://www.c-plusplus.net/forum/post/2196160</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/2196160</guid><dc:creator><![CDATA[Travor]]></dc:creator><pubDate>Wed, 28 Mar 2012 11:49:58 GMT</pubDate></item><item><title><![CDATA[Reply to Array einer eigenen Klasse dynamisch erweitern -&amp;gt;Frage zum  Destruktor [GELÖST] on Wed, 28 Mar 2012 12:00:08 GMT]]></title><description><![CDATA[<p>Nimm statt <code>memcpy</code> lieber <code>std::copy</code> , das funktioniert auch mit non-POD Typen und ist etwas handlicher imho.</p>
<pre><code class="language-cpp">void Personenliste::add_person( const Person&amp; p )
{
   if( Anzahl &gt;= gr )
   {  
      size_t NewSize = gr * 2;
      Person* buffer = new Person*[NewSize];

      std::copy( p, p + gr, buffer );

      delete[] p;
      p = buffer;
      gr = NewSize;
   }
   p[Anzahl] = person;
   ++anzahl;   
}
</code></pre>
]]></description><link>https://www.c-plusplus.net/forum/post/2196167</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/2196167</guid><dc:creator><![CDATA[DocShoe]]></dc:creator><pubDate>Wed, 28 Mar 2012 12:00:08 GMT</pubDate></item><item><title><![CDATA[Reply to Array einer eigenen Klasse dynamisch erweitern -&amp;gt;Frage zum  Destruktor [GELÖST] on Wed, 28 Mar 2012 12:28:37 GMT]]></title><description><![CDATA[<p>butterbemme schrieb:</p>
<blockquote>
<p>[...]<br />
<a class="plugin-mentions-user plugin-mentions-a" href="https://www.c-plusplus.net/forum/uid/22666">@Belli</a>: du meinst ich solle nur &quot;delete[] p&quot; benutzen. Aber genau das und zwar nur das, steht ja auch in meinem selbstdefinierten Destruktor ~Personenliste().<br />
Wo ist dann also der Unterschied? Oder wird da implizit noch etwas anderes im Hintergrund gemacht.</p>
<p>[...]</p>
<p>Dachte eigentlich Destruktoren haben diese Form und werden dann auch so aufgerufen</p>
</blockquote>
<p>Ja, da wird - wie hier auch schon jemand schrieb - Dein Objekt zerstört.<br />
Destruktoren haben diese Form, aber wie auch schon jemand schrieb, sie werden nicht explizit aufgerufen.</p>
<pre><code class="language-cpp">{
   objekt a;
}// hier wird wegen des Verlassens des Scopes der Destruktor von a implizit aufgerufen.
objekt *b = new b(); // hier muss es natürlich: objekt *b = new objekt(); heißen,  :) 
delete b; // hier wird von delete der Destruktor von b implizit aufgerufen
</code></pre>
<p>Anders solltest Du bis auf Weiteres Destruktoren nicht aufrufen.</p>
]]></description><link>https://www.c-plusplus.net/forum/post/2196172</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/2196172</guid><dc:creator><![CDATA[Belli]]></dc:creator><pubDate>Wed, 28 Mar 2012 12:28:37 GMT</pubDate></item><item><title><![CDATA[Reply to Array einer eigenen Klasse dynamisch erweitern -&amp;gt;Frage zum  Destruktor [GELÖST] on Wed, 28 Mar 2012 12:25:48 GMT]]></title><description><![CDATA[<p>Okay, ich denke ich habs soweit verstanden.<br />
Danke für eure Hilfe.</p>
]]></description><link>https://www.c-plusplus.net/forum/post/2196176</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/2196176</guid><dc:creator><![CDATA[butterbemme]]></dc:creator><pubDate>Wed, 28 Mar 2012 12:25:48 GMT</pubDate></item><item><title><![CDATA[Reply to Array einer eigenen Klasse dynamisch erweitern -&amp;gt;Frage zum  Destruktor [GELÖST] on Wed, 28 Mar 2012 12:28:55 GMT]]></title><description><![CDATA[<p>hey arbeite dich erstmal durch ein klassen tut... so kommste nicht weit ^^</p>
<p>hier noch ne regel falls du weiter auf dem heap arbeiten möchtest</p>
<p>definierst du einen dieser drei selbst:<br />
destructor<br />
copy constructor<br />
zuweisungs operator</p>
<p>musst du in der regel alle selbst schreiben, aber naja kommt noch ;P</p>
]]></description><link>https://www.c-plusplus.net/forum/post/2196179</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/2196179</guid><dc:creator><![CDATA[realKoala]]></dc:creator><pubDate>Wed, 28 Mar 2012 12:28:55 GMT</pubDate></item><item><title><![CDATA[Reply to Array einer eigenen Klasse dynamisch erweitern -&amp;gt;Frage zum  Destruktor [GELÖST] on Wed, 28 Mar 2012 13:44:44 GMT]]></title><description><![CDATA[<p>Üblicherweise ruft man einen Dtor nur dann explizit auf, wenn das Element mit einer Form von placement-new erzeugt wurde.</p>
]]></description><link>https://www.c-plusplus.net/forum/post/2196204</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/2196204</guid><dc:creator><![CDATA[314159265358979]]></dc:creator><pubDate>Wed, 28 Mar 2012 13:44:44 GMT</pubDate></item><item><title><![CDATA[Reply to Array einer eigenen Klasse dynamisch erweitern -&amp;gt;Frage zum  Destruktor [GELÖST] on Wed, 28 Mar 2012 14:35:29 GMT]]></title><description><![CDATA[<p>DocShoe schrieb:</p>
<blockquote>
<p>Nimm statt <code>memcpy</code> lieber <code>std::copy</code> , das funktioniert auch mit non-POD Typen und ist etwas handlicher imho.</p>
<pre><code class="language-cpp">void Personenliste::add_person( const Person&amp; p )
{
   if( Anzahl &gt;= gr )
   {  
      size_t NewSize = gr * 2;
      Person* buffer = new Person*[NewSize];

      std::copy( p, p + gr, buffer );

      delete[] p;
      p = buffer;
      gr = NewSize;
   }
   p[Anzahl] = person;
   ++anzahl;   
}
</code></pre>
</blockquote>
<p>Was ist mit <code>gr == 0</code> ?<br />
Warum wird <code>new[]</code> mit dem falschen Typ benutzt?<br />
Was ist, wenn <code>copy</code> wirft?<br />
Was sind <code>anzahl</code> und <code>Anzahl</code> ?<br />
Warum nicht gleich vernünftig mit Allocator?</p>
]]></description><link>https://www.c-plusplus.net/forum/post/2196233</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/2196233</guid><dc:creator><![CDATA[TyRoXx]]></dc:creator><pubDate>Wed, 28 Mar 2012 14:35:29 GMT</pubDate></item><item><title><![CDATA[Reply to Array einer eigenen Klasse dynamisch erweitern -&amp;gt;Frage zum  Destruktor [GELÖST] on Thu, 29 Mar 2012 04:50:14 GMT]]></title><description><![CDATA[<p>Ich bin mal so frei und werde den Thread als &quot;gelöst&quot; markieren. Wenns noch Unstimmigkeiten unter den einzelnen Postern gibt, können die den Thread ja trotzdem weiterfürhen</p>
]]></description><link>https://www.c-plusplus.net/forum/post/2196449</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/2196449</guid><dc:creator><![CDATA[butterbemme]]></dc:creator><pubDate>Thu, 29 Mar 2012 04:50:14 GMT</pubDate></item></channel></rss>