<?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[Rückgabe von dynamisch erzeugten Objekten]]></title><description><![CDATA[<p>Hallo Forum,<br />
ich bin neu hier und komme aus der schön einfachen Welt der JAVA Programmierung. Diesen Nachmittag habe ich damit verbracht zu überlegen, wie ich es schaffen könnte ein Objekt mit dynamischer Klassenvariable aus einer Funktion zurückzugeben.<br />
Hier die vereinfachte Version meines Codes (ich lasse die Header Dateien weg):</p>
<pre><code class="language-cpp">//main.cpp
#include &lt;iostream&gt;
#include &lt;string&gt;
#include &quot;stringarray.h&quot;

int main(int argc, char **argv) {
    StringArray cubeFiles = getBRTFiles(CUBE_DIRECTORY);
    return 0;
}

StringArray getBRTFiles(string directory) {
    string directoryEntries[2];
    for(unsigned int i = 0; i&lt; 2; i++) {
       directoryEntries[i] = &quot;Test&quot;;
    }
    StringArray files(directoryEntries, 2);
}
</code></pre>
<p>Die Klasse mit dem dynamisch erzeugten Klassenelement sieht folgendermaßen aus:</p>
<pre><code class="language-cpp">#include &lt;string&gt;
#include &lt;iostream&gt;
#include &quot;stringarray.h&quot;
using namespace std;

/**
 * Konstruktor
 */
StringArray::StringArray(string newData[], unsigned int newLength) {
	cout &lt;&lt; &quot;Erstelle StringArray \n&quot;;
	data = new string[newLength];
	length = newLength;
	for(unsigned int i = 0; i &lt; newLength; i++) {
		data[i] = newData[i];
	}
	length = newLength;
}
/**
 * Destruktor
 */
StringArray::~StringArray() {
	cout &lt;&lt; &quot;StringArray wurde zerstört \n&quot;;
	delete data;
}
/**
 * Überladen des = Operators um Fehler mit den dynamisch 
 * erzeugten Objekten zu vermeiden.
 */
StringArray&amp; StringArray::operator=(StringArray&amp; array) {
	cout &lt;&lt; &quot;Objekt wird kopiert&quot;;
	//Auf Selbstzuweisung überprüfen
	if(this == &amp;array) {
		return *this;
	} else {
		length = array.length;
		data = new string[length];
		/*
		for(unsigned int i = 0; i &lt; length; i++) {
			data[i] = array.data[i];
		}*/
		return *this;
	}
}

/**
 * Überschreiben des kompletten Daten Arrays
 */
void StringArray::setData(string newData[]) {
	if(sizeof(data) != sizeof(newData)) {
		cerr &lt;&lt; &quot;Wrong data length for array copy \n&quot;;
	} else {
		for(unsigned int i = 0; i &lt; length; i++) {
			data[i] = newData[i];
		}
	}
}

/**
 * Setzen eines einzelnen String Wertes im Daten Array
 * @param &amp;entry	Referenz auf den neuen Wert (keine Kopie nötig)
 */
void StringArray::setDataEntry(string &amp;entry, unsigned int index) {
	data[index] = entry;
}

string StringArray::getDataEntry(unsigned int index) {
	return data[index];
}
</code></pre>
<p>Vor Beendigung des Programms erhalte ich die Fehlermeldung:</p>
<pre><code>malloc: *** error for object 0x1001001c8: pointer being freed was not allocated
*** set a breakpoint in malloc_error_break to debug
</code></pre>
<p>Das liegt daran, dass das Objekt vom Typ StringArray zweimal zerstört wird. Einmal am Ende der Funktion getBRTFiles und einmal am Ende der main Methode. Beim zweiten Zerstören zeigt data nicht mehr auf einen gültigen Speicherbereich. Ich dachte das Überladen des = Operators behebt das Problem bereits. Allerdings wird die Methode zum Überladen beim Zurückgeben des Wertes nicht aufgerufen (</p>
<pre><code class="language-cpp">cout &lt;&lt; &quot;Objekt wird kopiert&quot;;
</code></pre>
<p>wird nicht ausgeführt).</p>
<p>Kann mir hier jemand einen Tip geben, wie ich Objekte mit dynamisch erstellten Klassenelmenten, sicher als Rückgabewerte von Funktionen verwende?</p>
<p>Danke<br />
Martin</p>
]]></description><link>https://www.c-plusplus.net/forum/topic/272865/rückgabe-von-dynamisch-erzeugten-objekten</link><generator>RSS for Node</generator><lastBuildDate>Fri, 28 Aug 2026 12:27:50 GMT</lastBuildDate><atom:link href="https://www.c-plusplus.net/forum/topic/272865.rss" rel="self" type="application/rss+xml"/><pubDate>Thu, 26 Aug 2010 14:34:56 GMT</pubDate><ttl>60</ttl><item><title><![CDATA[Reply to Rückgabe von dynamisch erzeugten Objekten on Thu, 26 Aug 2010 14:34:56 GMT]]></title><description><![CDATA[<p>Hallo Forum,<br />
ich bin neu hier und komme aus der schön einfachen Welt der JAVA Programmierung. Diesen Nachmittag habe ich damit verbracht zu überlegen, wie ich es schaffen könnte ein Objekt mit dynamischer Klassenvariable aus einer Funktion zurückzugeben.<br />
Hier die vereinfachte Version meines Codes (ich lasse die Header Dateien weg):</p>
<pre><code class="language-cpp">//main.cpp
#include &lt;iostream&gt;
#include &lt;string&gt;
#include &quot;stringarray.h&quot;

int main(int argc, char **argv) {
    StringArray cubeFiles = getBRTFiles(CUBE_DIRECTORY);
    return 0;
}

StringArray getBRTFiles(string directory) {
    string directoryEntries[2];
    for(unsigned int i = 0; i&lt; 2; i++) {
       directoryEntries[i] = &quot;Test&quot;;
    }
    StringArray files(directoryEntries, 2);
}
</code></pre>
<p>Die Klasse mit dem dynamisch erzeugten Klassenelement sieht folgendermaßen aus:</p>
<pre><code class="language-cpp">#include &lt;string&gt;
#include &lt;iostream&gt;
#include &quot;stringarray.h&quot;
using namespace std;

/**
 * Konstruktor
 */
StringArray::StringArray(string newData[], unsigned int newLength) {
	cout &lt;&lt; &quot;Erstelle StringArray \n&quot;;
	data = new string[newLength];
	length = newLength;
	for(unsigned int i = 0; i &lt; newLength; i++) {
		data[i] = newData[i];
	}
	length = newLength;
}
/**
 * Destruktor
 */
StringArray::~StringArray() {
	cout &lt;&lt; &quot;StringArray wurde zerstört \n&quot;;
	delete data;
}
/**
 * Überladen des = Operators um Fehler mit den dynamisch 
 * erzeugten Objekten zu vermeiden.
 */
StringArray&amp; StringArray::operator=(StringArray&amp; array) {
	cout &lt;&lt; &quot;Objekt wird kopiert&quot;;
	//Auf Selbstzuweisung überprüfen
	if(this == &amp;array) {
		return *this;
	} else {
		length = array.length;
		data = new string[length];
		/*
		for(unsigned int i = 0; i &lt; length; i++) {
			data[i] = array.data[i];
		}*/
		return *this;
	}
}

/**
 * Überschreiben des kompletten Daten Arrays
 */
void StringArray::setData(string newData[]) {
	if(sizeof(data) != sizeof(newData)) {
		cerr &lt;&lt; &quot;Wrong data length for array copy \n&quot;;
	} else {
		for(unsigned int i = 0; i &lt; length; i++) {
			data[i] = newData[i];
		}
	}
}

/**
 * Setzen eines einzelnen String Wertes im Daten Array
 * @param &amp;entry	Referenz auf den neuen Wert (keine Kopie nötig)
 */
void StringArray::setDataEntry(string &amp;entry, unsigned int index) {
	data[index] = entry;
}

string StringArray::getDataEntry(unsigned int index) {
	return data[index];
}
</code></pre>
<p>Vor Beendigung des Programms erhalte ich die Fehlermeldung:</p>
<pre><code>malloc: *** error for object 0x1001001c8: pointer being freed was not allocated
*** set a breakpoint in malloc_error_break to debug
</code></pre>
<p>Das liegt daran, dass das Objekt vom Typ StringArray zweimal zerstört wird. Einmal am Ende der Funktion getBRTFiles und einmal am Ende der main Methode. Beim zweiten Zerstören zeigt data nicht mehr auf einen gültigen Speicherbereich. Ich dachte das Überladen des = Operators behebt das Problem bereits. Allerdings wird die Methode zum Überladen beim Zurückgeben des Wertes nicht aufgerufen (</p>
<pre><code class="language-cpp">cout &lt;&lt; &quot;Objekt wird kopiert&quot;;
</code></pre>
<p>wird nicht ausgeführt).</p>
<p>Kann mir hier jemand einen Tip geben, wie ich Objekte mit dynamisch erstellten Klassenelmenten, sicher als Rückgabewerte von Funktionen verwende?</p>
<p>Danke<br />
Martin</p>
]]></description><link>https://www.c-plusplus.net/forum/post/1944669</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/1944669</guid><dc:creator><![CDATA[skifidelity]]></dc:creator><pubDate>Thu, 26 Aug 2010 14:34:56 GMT</pubDate></item><item><title><![CDATA[Reply to Rückgabe von dynamisch erzeugten Objekten on Thu, 26 Aug 2010 14:47:56 GMT]]></title><description><![CDATA[<p>Hallo,</p>
<p>es gibt die Regel der grossen 3, die besagt, dass wenn man<br />
Destruktor,<br />
Copy-Ctor,<br />
oder Zuweisungsoperator</p>
<p>überschreibt, man dann alle 3 ändern muss (zumindest genau hinsehen).<br />
So auch hier. Die Funktion getBRTFiles nutzt ja den Copy-CTor, den du nicht angepasst hast.<br />
Es wird der default-Ctor genommen, der lediglich den Zeiger kopiert.</p>
<p>ps.: Im Destruktor musst du dein Array mit delete[] zerstören.</p>
]]></description><link>https://www.c-plusplus.net/forum/post/1944673</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/1944673</guid><dc:creator><![CDATA[Jockelx]]></dc:creator><pubDate>Thu, 26 Aug 2010 14:47:56 GMT</pubDate></item><item><title><![CDATA[Reply to Rückgabe von dynamisch erzeugten Objekten on Thu, 26 Aug 2010 15:04:50 GMT]]></title><description><![CDATA[<p>wenn <code>data = new string[]</code> dann auch <code>delete[] data</code></p>
<p>Warum machst du es dir nicht leichter und nimmst einen std::vector&lt;string&gt; und kapselst den ... dann kannst du dir das ganze new/delete gefummel spaaren <img
      src="https://www.c-plusplus.net/forum/plugins/nodebb-plugin-emoji/emoji/emoji-one/1f642.png?v=ab1pehoraso"
      class="not-responsive emoji emoji-emoji-one emoji--slightly_smiling_face"
      title=":)"
      alt="🙂"
    /></p>
]]></description><link>https://www.c-plusplus.net/forum/post/1944681</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/1944681</guid><dc:creator><![CDATA[padreigh]]></dc:creator><pubDate>Thu, 26 Aug 2010 15:04:50 GMT</pubDate></item><item><title><![CDATA[Reply to Rückgabe von dynamisch erzeugten Objekten on Fri, 27 Aug 2010 12:33:54 GMT]]></title><description><![CDATA[<p>Hallo Euch beiden. Vielen Dank für Eure Hilfe. Gerne werd ich auf Vektoren umsteigen (die werden wohl ähnlich funktionieren wie die Verktoren in Java). Ich bin leider in meinen Fachbüchern noch nicht soweit (1000 Seiten) und ich muss mich Schritt für Schritt vorarbeiten. Vorerst hier mal der Code von Destruktor, Kopierkonstruktor und Überladen des = Operators (muss man immer machen, wenn dynamische Klassenelemente benutzt werden. Vielleicht hilfts ja jemandem:</p>
<pre><code class="language-cpp">/**
 * Destruktor (nötig für dynamisch erzeugte Elemente)
 */
StringArray::~StringArray() {
	cout &lt;&lt; &quot;StringArray wurde zerstört \n&quot;;
	delete [] data;
}
/**
 * Kopierkonstruktor (nötig für dynamisch erzeugte Element)
 */
StringArray::StringArray(const StringArray&amp; array2) {
	cout &lt;&lt; &quot;Kopierkonstruktor \n&quot;;
	length = array2.getLength();
	data = new string[length];
	for(unsigned int i = 0; i &lt; length; i++) {
		data[i] = array2.data[i];
	}
}

/**
 * Überladen des = Operators um Fehler mit den dynamisch 
 * erzeugten Objekten zu vermeiden.
 */
StringArray&amp; StringArray::operator=(const StringArray&amp; array) {
	cout &lt;&lt; &quot;Objekt wird kopiert&quot;;
	//Auf Selbstzuweisung überprüfen
	if(this == &amp;array) {
		return *this;
	} else {
		length = array.getLength();
		data = new string[length];
		for(unsigned int i = 0; i &lt; length; i++) {
			data[i] = array.data[i];
		}
		return *this;
	}
}
</code></pre>
]]></description><link>https://www.c-plusplus.net/forum/post/1945027</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/1945027</guid><dc:creator><![CDATA[skifidelity]]></dc:creator><pubDate>Fri, 27 Aug 2010 12:33:54 GMT</pubDate></item><item><title><![CDATA[Reply to Rückgabe von dynamisch erzeugten Objekten on Fri, 27 Aug 2010 12:43:22 GMT]]></title><description><![CDATA[<p>skifidelity schrieb:</p>
<blockquote>
<p>Ich bin leider in meinen Fachbüchern noch nicht soweit...</p>
</blockquote>
<p>Es gibt leider viele Fachbücher die mehr C als C++ enthalten, sich aber als C++ Buch verkaufen.</p>
]]></description><link>https://www.c-plusplus.net/forum/post/1945029</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/1945029</guid><dc:creator><![CDATA[asc]]></dc:creator><pubDate>Fri, 27 Aug 2010 12:43:22 GMT</pubDate></item><item><title><![CDATA[Reply to Rückgabe von dynamisch erzeugten Objekten on Fri, 27 Aug 2010 12:59:56 GMT]]></title><description><![CDATA[<p>skifidelity schrieb:</p>
<blockquote>
<pre><code class="language-cpp">/**
 * Überschreiben des kompletten Daten Arrays
 */
void StringArray::setData(string newData[]) {
	if(sizeof(data) != sizeof(newData)) {
</code></pre>
</blockquote>
<p>Das geht so leider nicht. <code>newData</code> wird als einfacher Zeiger an <code>setData</code> übergeben, <code>sizeof(newData)</code> ist also abhängig vom System immer 4 bzw. 8 Bytes und <em>nicht</em> die Größe des Arrays. Beim Übergeben eines Arrays an eine Funktion muss immer auch dessen Länge übergeben werden, falls diese dynamisch ist.<br />
Das Ganze kannst du dir mit einer Array-Kapselung, z.B. <code>vector</code> sparen, denn der kennt seine Länge.</p>
]]></description><link>https://www.c-plusplus.net/forum/post/1945034</link><guid isPermaLink="true">https://www.c-plusplus.net/forum/post/1945034</guid><dc:creator><![CDATA[ipsec]]></dc:creator><pubDate>Fri, 27 Aug 2010 12:59:56 GMT</pubDate></item></channel></rss>