As the title states, I'd like to know if coding style can cause or influence memory fragmentation in a native application, specifically one written using C++. If it does, I'd like to know how.
An example of what I mean by coding style is using std::string
to represent strings (even static strings) and perform operations on them instead of using the C Library (such as strcmp
, strlen
, and so on) which can work both on dynamic strings and static strings (the latter point is beneficial since it does not require an additional allocation to access string functions, which is not the case with std::string
).
A "forward-looking" attitude I have with C++ is to not use the CRT, since to do so would, in a way, be a step backwards. However, such a style results in more dynamic allocations, and especially for a long living application like a server, this causes some speculation that memory fragmentation might become a problem.
3 Answers 3
The question and the supporting text don't match up.
Your supporting text is talking about comparing two libraries' memory usage, which can be tested fairly directly and is orthogonal to coding style. Just wrap up the C string operators in a thin C++-style object and you can work with them the same with little-to-any memory impact, for instance.
The question title implies difference in actual style, such as allocating/destroying objects as needed versus using an object pool, or constructing strings with imperative loops of logic and concatenation intertwined versus building up an array of strings imperatively and then constructing the final string all at once.
The answer to both, however, is the same: yes, they can influence memory fragmentation -- the underlying libraries work in different ways so they probably affect the memory in different ways, and your usage of the libraries can also impact memory fragmentation, and the "proper" style probably depends on the library that you're using.
C-style string manipulation can be very light on memory and better controlled for fragmentation issues, but you will pepper your executable with variables to keep track of the state of your output string as you assemble it, and if you don't put a lot of effort into it, you probably won't beat std::string
's code for common use-cases. Of course, if you have no idea how std::string
works behind-the-scenes, you could also make it do something stupid, but that's for you to decide on how much you want to learn the internals of your tools and how much it actually impacts what you're trying to accomplish.
-
I could be wrong, but I had thought that most implementations would not allocate off the heap if you did
const std::string str("hello world");
A clever implementation ofstd::string
could also avoid this even withstd::string str("hello world")
until the string is modified.user53141– user531412012年05月23日 19:53:39 +00:00Commented May 23, 2012 at 19:53 -
1@StevenBurnap, that brings up part of my point: if you care about memory fragmentation, you have to either study your underlying libraries' code or benchmark them based on how you use them. You use libraries by telling them what to do, not how to do it, but worries about memory fragmentation deal with the how.user54720– user547202012年05月23日 20:01:12 +00:00Commented May 23, 2012 at 20:01
-
Yes, definitely. It's always a mistake to assume your library will cause problems without proof, especially one as widely used as the C++ standard libraries.user53141– user531412012年05月23日 20:18:26 +00:00Commented May 23, 2012 at 20:18
-
copy-on-write semantics for strings have mostly been removed because they perform poorly on multi-threaded systems (too much locking involved), but I guess they could be a very good optimisation for small-memory or single-thread systems.gbjbaanb– gbjbaanb2012年06月23日 15:58:22 +00:00Commented Jun 23, 2012 at 15:58
Sure, coding style can impact memory fragmentation since coding style will change your allocation/deallocation patterns which are the largest impact on fragmentation.
That said, using C++ vs C strings isn't a coding style. Further, different coding styles (especially in C++) exist to decrease complexity, increase readability, increase testability, increase robustness, increase correctness, or in C++'s case protect you from all of its landmines. All of which are far and away more important than memory fragmentation.
-
1Well, usually more important than memory fragmentation. If you are on a system with fixed memory and no virtual memory, fragmentation can be a bigger issue. That said, there are certainly ways to deal with this and still get the advantages of C++ strings, for instance, by using a different heap for the sort of small allocations that
string
and the STL tend to use.user53141– user531412012年05月23日 19:50:03 +00:00Commented May 23, 2012 at 19:50
It's pretty unlikely. Fragmentation, as far as I am aware, is not a significant issue in modern memory allocators.
Also, you can simply roll a custom allocator that uses an arena or pool to handle memory.
Of course, fragmentation is a complete non-issue with C strings, as your program will probably crash almost immediately at launch thanks to a missed NULL terminator, and exhibit plenty of security vulnerabilities and other fun things, all of which would be more important than a little fragmentation.
-
1This is true on PCs. It is not true on many non-PC devices. While I agree that no one should use C strings when they can possibly avoid it, I've certainly written tens of thousands of lines of code that did not crash using C strings back in the days when that's all we had.user53141– user531412012年05月23日 19:55:58 +00:00Commented May 23, 2012 at 19:55
-
2@DeadMG: You realise the Linux kernel is written in C, right? I think you're blinded by your love of C++ a bit.James– James2012年05月23日 20:11:23 +00:00Commented May 23, 2012 at 20:11
-
@James: In short, appeal to authority fallacy. In long, I need to write a blog post about how ridiculous that one is, because I meet it a lot.DeadMG– DeadMG2012年05月25日 18:34:12 +00:00Commented May 25, 2012 at 18:34
strlen
) would have eaten up any speed advantage. That said, string handling code (algorithm) can influence memory fragmentation, but not in the way you described. The solution is also not along the line you described. It is somewhat ironic that the managed world somehow managed to roll out the solution package better than in C++ world. Lock-free algorithms, arena allocator, small-object pool, interning and hashing,StringBuffer/StringBuilder
etc.