Search code examples
c++stringmutable

Performance on strings initialization in C++


I have following questions regarding strings in C++:

1>> which is a better option(considering performance) and why?

1.

string a;
a = "hello!";

OR

2.

string *a;
a = new string("hello!");
...
delete(a);

2>>

string a;
a = "less"; 
a = "moreeeeeee"; 

how exactly memory management is handled in c++ when a bigger string is copied into a smaller string? Are c++ strings mutable?


Solution

  • All the following is what a naive compiler would do. Of course as long as it doesn't change the behavior of the program, the compiler is free to make any optimization.

    string a;
    a = "hello!";
    

    First you initialize a to contain the empty string. (set length to 0, and one or two other operations). Then you assign a new value, overwriting the length value that was already set. It may also have to perform a check to see how big the current buffer is, and whether or not more memory should be allocated.

    string *a;
    a = new string("hello!");
    ...
    delete(a);
    

    Calling new requires the OS and the memory allocator to find a free chunk of memory. That's slow. Then you initialize it immediately, so you don't assign anything twice or require the buffer to be resized, like you do in the first version. Then something bad happens, and you forget to call delete, and you have a memory leak, in addition to a string that is extremely slow to allocate. So this is bad.

    string a;
    a = "less"; 
    a = "moreeeeeee";
    

    Like in the first case, you first initialize a to contain the empty string. Then you assign a new string, and then another. Each of these may require a call to new to allocate more memory. Each line also requires length, and possibly other internal variables to be assigned.

    Normally, you'd allocate it like this:

    string a = "hello";
    

    One line, perform initialization once, rather than first default-initializing, and then assigning the value you want.

    It also minimizes errors, because you don't have a nonsensical empty string anywhere in your program. If the string exists, it contains the value you want.

    About memory management, google RAII. In short, string calls new/delete internally to resize its buffer. That means you never need to allocate a string with new. The string object has a fixed size, and is designed to be allocated on the stack, so that the destructor is automatically called when it goes out of scope. The destructor then guarantees that any allocated memory is freed. That way, you don't have to use new/delete in your user code, which means you won't leak memory.