Sign in to follow this  
JeremyYox

(C#) Small question about calling variables

Recommended Posts

So, every example that I've seen until now when calling variables has been similar to say:


[code]Console.WriteLine("Hi there, " + userName + "!");[/code]

But today I came across someone using something like:

[code]Console.WriteLine("Hi there, {0}", userName);[/code]

I was just wondering if there were any real differences in application or if its essentially two ways of accomplishing the same thing? I haven't seen any other examples of the latter, so it interested me.

Thank you.

Share this post


Link to post
Share on other sites
The second is a quick and easy way to call string.Format. It should be preferred in most cases because it (should be) smarter about allocating memory, makes it easier to add formatting options in the future, and is more idiomatic to C#. That said, stuff that uses string.Format is the only place that you'll use that sort of string replacement behavior; everywhere else will be different.

Share this post


Link to post
Share on other sites
The latter approach allocates only one new string, while the former allocates [i]n[/i] strings depending on how many concatenations (+) you make.

If you make an excessive number of allocations, it will impact performance as the garbage collector has to deal with the temporary storage - even though you wouldn't store the allocated variables yourself.

Share this post


Link to post
Share on other sites
So you're saying that by using the first method, each concatenation references a new memory block, while the second points to the same reference and thereby the same block? Is that how its more memory friendly? Is there a name for this technique?

Thank you for the responses.

Share this post


Link to post
Share on other sites
Your code can be thought of as shorthand for this:
[code]
string temp1 = "Hi there, " + userName;
string temp2 = temp1 + "!";
Console.WriteLine(temp2);
[/code]
The first one requires new memory for the expression ("Hi there, " + userName), and another one for the result of the former concatenated with "!". So, inserting one variable in a string requires 2 additional memory allocations, and also copying the string contents.
[code]
Console.WriteLine("A: " + a + ", B: " + b + ", C: " + c);
[/code]
The above would require even more allocations and copies:
[code]
string temp1 = "A: " + a;
string temp2 = temp1 + ", B: ";
string temp3 = temp2 + b;
string temp4 = temp3 + ", C: ";
string temp5 = temp4 + c;
Console.WriteLine(temp5);
[/code]
There are 5 allocations here. The contents of the string "A: " and object/value "a" get copied 5 times here, once to each temporary, the contents of ", B: " gets copied 4 times, and so on.

In constrast, when you pass a format string to string.Format or Console.WriteLine, it knows the length of the static text, and it can deduce the maximum length of all the variables - by scanning the format string for references and using the argument's type. Given the maximum length, it could then create one large buffer and format the entire string into this without additional reallocation. Essentially, because you give all the information at once, so the implementation has lots of options for optimisation.

However, as you can probably imagine there is a runtime conditional and looping logic that is not involved than in the unconditional concatenations above. Remember that allocations and copies incur such logic too, I am not saying that it either way would be significantly worse or better, you would need to profile. In practise when you are writing to an I/O device the bottleneck is usually the device, not formatting the strings in memory.

There are some exceptions. You could imagine if the "userName" in your example was a couple of million characters long, copying this string multiple times would be very expensive, so you want to avoid doing it unnecessarily. While you could reasonably expect a user name to be short (and thus you might not bother to handle ridiculously long user names efficiently), if you were writing code that edited a document or something then you'd need to take such considerations into account.

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this