Das Buch Game Coding Complete, 4. Auflage , Kapitel 5 ( Game Initialization and Shutdown ), Abschnitt Überprüfung des Speichers, enthält dieses interessante Codebeispiel:
bool CheckMemory(const DWORDLONG physicalRAMNeeded, const DWORDLONG virtualRAMNeeded)
{
MEMORYSTATUSEX status;
GlobalMemoryStatusEx(&status);
if (status.ullTotalPhys < physicalRAMNeeded)
{
// you don’t have enough physical memory. Tell the player to go get a
// real computer and give this one to his mother.
GCC_ERROR("CheckMemory Failure: Not enough physical memory.");
return false;
}
// Check for enough free memory.
if (status.ullAvailVirtual < virtualRAMNeeded)
{
// you don’t have enough virtual memory available.
// Tell the player to shut down the copy of Visual Studio running in the
// background, or whatever seems to be sucking the memory dry.
GCC_ERROR("CheckMemory Failure: Not enough virtual memory.");
return false;
}
char *buff = GCC_NEW char[virtualRAMNeeded];
if (buff)
{
delete[] buff;
}
else
{
// even though there is enough memory, it isn't available in one
// block, which can be critical for games that manage their own memory
GCC_ERROR("CheckMemory Failure: Not enough contiguous memory.");
return false;
}
}
Dies wirft einige Fragen auf.
Der erste Teil fragt nur das Betriebssystem (Windows), wie viel physischer RAM verfügbar ist. Der merkwürdige Teil ist der zweite, der einen großen Teil des Speichers zuweist und ihn sofort freigibt:
char *buff = GCC_NEW char[virtualRAMNeeded];
if (buff)
{
delete[] buff;
}
Der Autor erklärt weiter:
... diese Funktion reserviert und gibt sofort einen riesigen Speicherblock frei. Dies bewirkt, dass Windows alle im Speichermanager angesammelten Abfälle bereinigt und überprüft, ob Sie einen zusammenhängenden Block so groß wie nötig zuordnen können. Wenn der Anruf erfolgreich ist, haben Sie im Wesentlichen das Äquivalent einer Zamboni-Maschine im Speicher Ihres Systems ausgeführt, um es für Ihr Spiel auf Eis zu legen ...
Aber ich habe meine Vorbehalte dazu.
Msgstr "Müll säubern, der sich im Speichermanager angesammelt hat?" "Ja wirklich?" Wenn das Spiel gerade erst begonnen hat, sollte es dann keinen Müll geben?
Msgstr "Sicherstellen, dass Sie einen zusammenhängenden Block zuordnen können?" In dem speziellen Fall, in dem Sie den Speicher selbst verwalten möchten, ist dies sinnvoll. Wenn Sie jedoch auf Anhieb viel Speicher zuweisen, können Sie praktisch keine andere Anwendung ausführen das System, während Ihr eingeschaltet ist.
Erzwingt dies wahrscheinlich nicht das Festschreiben des gesamten Arbeitsspeichers durch das Betriebssystem und folglich das Entfernen einer großen Menge Arbeitsspeichers auf den Swap-Speicher, wodurch der Start Ihrer App erheblich verlangsamt wird?
Ist das wirklich eine gute Übung?
operator new
auf überprüfend nullptr
), wenn Sie mir erlauben sagen. Das Beste, was Sie mit diesem Buch anfangen können, ist, Ihren Schornstein anzuzünden. Das Zuweisen und Freigeben eines großen Speicherblocks " räumt " natürlich nicht den Speicher auf.
new
Operator zumindest überladen , um null zurückzugeben, anstatt zu werfen bad_alloc
. Wenn nicht, dann ist dieser Code noch unsinniger: P
operator delete
ist, muss es akzeptiert nullptr
und als No-Op behandelt werden. Jede globale Überladung, die das nicht tut, ist kaputt. Das heißt, es ist so oder so unsinnig. Genauso wie man annimmt, dass das Zuweisen und Freigeben eines riesigen Speicherblocks "magisch" etwas Gutes bewirkt. Im besten Fall schadet es nicht (höchstwahrscheinlich, da die Seiten nicht einmal berührt werden ... andernfalls werden möglicherweise einige Seiten aus Ihrem Arbeitsbereich ausgetauscht, die Sie später neu laden müssen).