Du bist nicht angemeldet.

Stilllegung des Forums
Das Forum wurde am 05.06.2023 nach über 20 Jahren stillgelegt (weitere Informationen und ein kleiner Rückblick).
Registrierungen, Anmeldungen und Postings sind nicht mehr möglich. Öffentliche Inhalte sind weiterhin zugänglich.
Das Team von spieleprogrammierer.de bedankt sich bei der Community für die vielen schönen Jahre.
Wenn du eine deutschsprachige Spieleentwickler-Community suchst, schau doch mal im Discord und auf ZFX vorbei!

Werbeanzeige

CBenni::O

1x Contest-Sieger

  • »CBenni::O« ist der Autor dieses Themas

Beiträge: 1 145

Wohnort: Stuttgart

  • Private Nachricht senden

11

03.02.2010, 21:34

Mal ne kurze Frage: was sind denn die Nachteile von Speicherreservierung mit new (und der Freigabe mit delete)?

mfg CBenni::O
Ein Mitglied der VEGeiCoUndGraSonMaWiGeS Bewegung.
42!
Aufräumen kann jeder, nur das Genie überblickt das Chaos!
Metal will never die!
1. Sppro Gamecontest - mein Beitrag

12

03.02.2010, 21:47

Es dauert länger, Speicher mit new zu reservieren, als ihn am Stack anzufordern. Außerdem muss man sich selbst darum kümmern, wann er wieder freigegeben wird.
Im Gegenzug ist die Größe des Stacks beschränkt, große Arrays kann man also nur am Heap (also mit new) erzeugen. Außerdem kann man Speicher am Heap freigeben, sobald man ihn nicht mehr braucht, wogegen man beim Speicher auf dem Stack den Codeblock verlassen muss, in dem er erstellt wurde.
Lieber dumm fragen, als dumm bleiben!

CBenni::O

1x Contest-Sieger

  • »CBenni::O« ist der Autor dieses Themas

Beiträge: 1 145

Wohnort: Stuttgart

  • Private Nachricht senden

13

03.02.2010, 22:14

Ja, das ist schon klar. Ich meinte, im vergleich zu z.B. boost::shared_ptr etc.

Sry für meine unklare Frage :oops:

mfg CBenni::O
Ein Mitglied der VEGeiCoUndGraSonMaWiGeS Bewegung.
42!
Aufräumen kann jeder, nur das Genie überblickt das Chaos!
Metal will never die!
1. Sppro Gamecontest - mein Beitrag

14

03.02.2010, 22:20

Ok, also der Vorteil bei smartpointern ist natürlich, dass es schwerer wird, zu vergessen, etwas freizugeben. Außerdem kann man damit auch prima so Probleme abfangen wie "Wenn eine Exception geworfen wird, wird das delete am Ende des Codeblocks nie ausgeführt".
Benutzt man smartpointer hat man eben je nach benutzter Klasse ein wenig Overhead. Außerdem muss man sich Gedanken darüber machen, welchen Pointertyp man benutzt und auf sowas wie zyklische Referenzen achten (ist auf der boost Seite erklärt).
Lieber dumm fragen, als dumm bleiben!

15

04.02.2010, 00:28

Zitat von »"CBenni::O"«

Ja, das ist schon klar. Ich meinte, im vergleich zu z.B. boost::shared_ptr etc.
Wie schon angetönt ist new einfach sehr heikel, sobald mehrere Ablaufpfade vorhanden sind, ein Wert von einer Funktion zurückgegeben werden muss, oder für Wertsemantik im Allgemeinen. Es stellt sich immer die Frage, wann wer freizugeben hat, jedes return in einer Funktion mit Speicheranforderung muss von deletes begleitet werden und jeder Code, der Exceptions werfen kann (und das ist mehr als du denkst), erfordert hässliche try-catch-Blöcke mit Aufräumarbeiten und Exception-Weiterwerfen. Um diese Probleme zu umgehen, sieht man teilweise Verzicht auf Exceptions, Konzepte wie Single-Entry-Single-Exit und andere fragwürdige Angelegenheiten.

Doch das ist der falsche Ansatz, schliesslich programmieren wir C++ und nicht C. Mit Klassen haben wir die Möglichkeit, Kopier- und Zerstörsemantik nach den eigenen Wünschen einzurichten und alles in Objekte zu stopfen, die sich selbst verwalten. Das ermöglicht einem, sich den wirklich wichtigen Dingen zuzuwenden, während Sprachmittel wie dynamische Speicherverwaltung gekapselt und automatisiert werden können. Ein sehr schönes Beispiel für diese Abstraktion stellen neben den Smart-Pointers die STL-Container dar.

Genau deshalb ist auch RAII (welches meistens auch das Gegenstück RRID einschliesst) so wertvoll. Und genau deshalb ist C++ keine Sprache, in der man Speicher manuell verwalten muss – zumindest im Grossteil der Fälle. Vorteil ist, dass dieses Konzept nicht nur für Speicher gilt, sondern für Ressourcen generell (es heisst ja "resource acquisition is initialization", bzw. "resource release is destruction"). Hier hat man in GC-verwalteten Sprachen wieder Probleme wegen probabilistischer Zerstörung und muss teilweise auf manuelle Freigabe zurückgreifen (finally, dispose etc.).

Also zusammengefasst: Schau dir diese Technik unbedingt an, sie wird deinen Code und deine Herangehensweise an Probleme grundlegend beeinflussen.

drakon

Supermoderator

Beiträge: 6 513

Wohnort: Schweiz

Beruf: Entrepreneur

  • Private Nachricht senden

16

04.02.2010, 17:06

Alleine schon ein std::auto_ptr ist oftmals eine gute Lösung.

CBenni::O

1x Contest-Sieger

  • »CBenni::O« ist der Autor dieses Themas

Beiträge: 1 145

Wohnort: Stuttgart

  • Private Nachricht senden

17

04.02.2010, 18:27

Ok, danke :)

Dann habe ich ja wieder genug zu tun... meine Liste ist ungefähr 20 Punkte lang...

mfg CBenni::O
Ein Mitglied der VEGeiCoUndGraSonMaWiGeS Bewegung.
42!
Aufräumen kann jeder, nur das Genie überblickt das Chaos!
Metal will never die!
1. Sppro Gamecontest - mein Beitrag

CBenni::O

1x Contest-Sieger

  • »CBenni::O« ist der Autor dieses Themas

Beiträge: 1 145

Wohnort: Stuttgart

  • Private Nachricht senden

18

17.02.2010, 16:17

Soo, nun habe ich eine neue Version!

Ich habe Versucht, möglichst viele Punkte zu berücksichtigen:
  • Konstruktoren statt Init
  • Destruktoren
  • Weniger (oder vllt auch keine?) Memoryleaks
  • const da eingesetzt, wo es ging
  • Einheitliche returnwerte, bzw. Überflüssige entfernt
  • Header in einen seperaten Ordner
Ich habe mich dagegen entschieden, RAII bzw. auto_ptr's einzusetzen, da damit zu viel arbeit für zu wenig Ergebnis anfällt.

Download

mfg CBenni::O
Ein Mitglied der VEGeiCoUndGraSonMaWiGeS Bewegung.
42!
Aufräumen kann jeder, nur das Genie überblickt das Chaos!
Metal will never die!
1. Sppro Gamecontest - mein Beitrag

idontknow

unregistriert

19

17.02.2010, 16:57

Ich würd das ganze nich Framework nennen :P. Nen Framework ist doch etwas mehr als 2 Klassen ;).

drakon

Supermoderator

Beiträge: 6 513

Wohnort: Schweiz

Beruf: Entrepreneur

  • Private Nachricht senden

20

17.02.2010, 16:59

Zitat von »"CBenni::O"«


Konstruktoren statt Init


(Link)

Zitat von »"CBenni::O"«


Destruktoren


(Link)

Zitat von »"CBenni::O"«


Weniger (oder vllt auch keine?) Memoryleaks

Dafür gibts Möglichkeiten das zu testen.. (das hier z.B)

Zitat von »"CBenni::O"«


const da eingesetzt, wo es ging

Besser dort, wo es nötig ist, aber für den Anfang kann man es durchaus mal übertreiben, damit man ein Gefühl dafür bekommt, wo es nötig ist und wo nicht.

Zitat von »"CBenni::O"«


Einheitliche returnwerte, bzw. Überflüssige entfernt


(Link)

Zitat von »"CBenni::O"«


Header in einen seperaten Ordner


(Link)

Zitat von »"CBenni::O"«


Ich habe mich dagegen entschieden, RAII bzw. auto_ptr's einzusetzen, da damit zu viel arbeit für zu wenig Ergebnis anfällt.


(Link)

Ich wüsste nicht, wie das mehrarbeit bedeuten könnte und der Vorteil ist meistens nicht unerheblich. (Exceptionsicherheit, Kopierbarkeit usw.)

Zitat

C-/C++-Quelltext

1
#define SAFE_DELETE(X){ if(X != NULL){delete (X); X=NULL;} }

Und es hält sich stetig.. Das überprüfen auf 0 wird korrekt von delete gemacht und ist somit nutzlos. Das 0 setzen kann ausserhalb eines Destruktors Sinn machen, aber innerhalb eines Destruktors spielt es keine Rolle, ob ein Zeiger auf Müll zeigt, weil sicher niemand mehr drauf zugreifen sollte ( ausser du machst keine Ahung was noch im Destruktor..)

btw:
Initialisierungsliste wäre auch ein Thema für dich!

Werbeanzeige