Memory management patterns in C++

Started by
23 comments, last by Juliean 8 years, 9 months ago

One area I have been focusing on in my game engine recently is memory management. Up until now, I have pretty much just been using raw pointers, and simply keeping in mind what is supposed to clean up what. It's worked great so far, but it just isn't very scalable, and I'm now looking for alternatives.

I have been thinking about how a garbage collector could be implemented in C++, and I I've come up with a few ways. One thing I've always disliked about garbage collectors however is that they just don't tell you anything about the relationship between objects (you lose any sense of ownership with a garbage collector, which is one thing I really dislike when working with managed languages. Even when knowing what owns what is irreverent for memory management purposes, it just tells you so much more about how the application works at a glance). With that in mind, I've been thinking of developing a memory model similar to std::unique_ptr and std::weak_ptr.

In such a system, for every dynamically allocated block there would be one unique_ptr, and an unlimited number of weak_ptrs (obviously this doesn't work with the the standard library versions because you can't assign a weak_ptr to a unique_ptr, but that is one thing I plan on changing). Ownership cycles would have to be detected (make sure an object doesn't hold a unique_ptr to itself), but other than that everything could be tracked using normal c++ constructors and destructors. This system is appealing to me, because it would be much simpler to implement than a garbage collector, and possibly be more efficient. However, making such a system thread-safe may be more difficult, and may end up being just much more restricting and difficult to use than a garbage collector.

I've been trying to read about this online, but the vast majority of results for "Memory management in C++" lead to articles on the very basics of using new/delete, which I already understand.

How have you solved this problem in your projects?

Thanks

Advertisement

Garbage collection is a lazy process that lets you not be too concerned about where your memory goes and what objects are made. This doesn't really mesh well with games. In games you have to keep close track of everything. You can't risk say having some particle system going crazy and running in the background when you thought it was deleted a long time ago (dumb example but you get the idea).

Usually you want to do something like read a world file and precache every object the world file needs, then delete them if you close it, then separately handle dynamic stuff - which you will usually also want to delete whenever you change a world.

Reference counting is OK in general especially for something like GUI which you are likely to leave hanging around to pop up quickly without reloading. I don't think it's got much use in games though.

This is my thread. There are many threads like it, but this one is mine.

If you're doing garbage collection in games you can work around the lack of control if you implement the system yourself and keep control of when gc occurs.

For example you can do collection when you call a collect() method of your memory object. You can do this at points of your own choosing, e.g. when the player is in your "corridor" between two level sections and not much is going off, or during your loading screen.

You can have even more control by dictating what types of objects to free and when. e.g. It's usually O(1) to free plain old data but potentially more to free an object instance with destructors.

Plan it out carefully and you should be OK...

If you're doing garbage collection in games you can work around the lack of control if you implement the system yourself and keep control of when gc occurs.

For example you can do collection when you call a collect() method of your memory object. You can do this at points of your own choosing, e.g. when the player is in your "corridor" between two level sections and not much is going off, or during your loading screen.

You can have even more control by dictating what types of objects to free and when. e.g. It's usually O(1) to free plain old data but potentially more to free an object instance with destructors.

Plan it out carefully and you should be OK...

:rolleyes:

What's the point though? In a game you must manage things carefully. So there is no point to bother with GC (if there ever is in C++). GC can cause a lot of finicky bugs. It's arguably a bad practice in an circumstance, let alone in games.

This is my thread. There are many threads like it, but this one is mine.

...snip...


Memory management isn't my strong suit, but it would seem that std::shared_ptr would do most of what you want with few changes.

rolleyes.gif

What's the point though? In a game you must manage things carefully. So there is no point to bother with GC (if there ever is in C++). GC can cause a lot of finicky bugs. It's arguably a bad practice in an circumstance, let alone in games.


Why do you keep posting about things you clearly know nothing about? Garbage collection is really nothing more than making sure memory is disposed of properly and not only has use in games, but has been used in games for decades. Are you enjoying this death spiral?

What's the point though? In a game you must manage things carefully. So there is no point to bother with GC (if there ever is in C++). GC can cause a lot of finicky bugs. It's arguably a bad practice in an circumstance, let alone in games.


Both xna and monogame use a garbage collected memory model as does unity via mono.

In all instances you can write quite performant games in these frameworks and engines by planning carefully. When the engine and language collects and what it collects are very well documented and so long as you don't just dive in without thought you won't have problems. To say garbage collection isn't worth it is backwards and such sweeping statements don't really apply. You can't just get out the brush and paint an opinion across every type of game.

What about java games too? They seem to have worked well in a lot of instances. Minecraft anyone?

Why do you keep posting about things you clearly know nothing about? Garbage collection is really nothing more than making sure memory is disposed of properly and not only has use in games, but has been used in games for decades. Are you enjoying this death spiral?

Ah, the irony.

Yes GC is very easy to implement in C++. I think every newly minted game programmer should give that a try and nothing bad will happen.

You must be same staffer who argued with me about memory management before and had no idea what he was talking about. With the bad advice you give, you should not be posting at all, let alone trying to correct me. You really are delusional.

This is my thread. There are many threads like it, but this one is mine.

What's the point though? In a game you must manage things carefully. So there is no point to bother with GC (if there ever is in C++). GC can cause a lot of finicky bugs. It's arguably a bad practice in an circumstance, let alone in games.


Both xna and monogame use a garbage collected memory model as does unity via mono.

In all instances you can write quite performant games in these frameworks and engines by planning carefully. When the engine and language collects and what it collects are very well documented and so long as you don't just dive in without thought you won't have problems. To say garbage collection isn't worth it is backwards and such sweeping statements don't really apply. You can't just get out the brush and paint an opinion across every type of game.

What about java games too? They seem to have worked well in a lot of instances. Minecraft anyone?

What is your point?

There is a difference between using GC in a lnaguage that already has it, and implmenting it yourself. Think 2 seconds before you post, especially if it's aimed as a flame at me.

This is my thread. There are many threads like it, but this one is mine.

You must be same staffer who argued with me about memory management before and had no idea what he was talking about. With the bad advice you give, you should not be posting at all, let alone trying to correct me. You really are delusional.


I'm not staff. What gives you that idea? I have never had the opportunity to respond to you to date because every other thread I've come across has been closed.

All two of them?

I thought that's what GDNet+ red label meant, I guess not.

Well, if you implement reference counting GC some day, you will eventually curse to high heaven when things don't clean properly. I can't think of a worse idea than recommending to an apparent noob to implement their own reference counting.

This is my thread. There are many threads like it, but this one is mine.

This topic is closed to new replies.

Advertisement