0

This has probably been asked before but I can't find it. I don't think my googlefu is good enough. Anyway,

Say I have this:

string cat = "meow"
cat = cat.replace("meow","purr");
cat = Regex.Replace(cat, "purr", "Meow!");

It seems extra to be setting the cat variable to a manipulated copy of it. Is there a way to do this in a pass by ref way so that I don't have to set the variable to the modified version of itself?

To be clear it's lines 2 and 3 above that I'm asking about here.

EDIT: I don't believe the marked dupe is an EXACT dupe of my question. My question is specific to the inquiry of the existence of such a thing. The linked post is specific to an explanation of why it DOESN'T exist. This question is probably still worth keeping for those who aren't familiar with the immutable concept.

Capn Jack
  • 1,201
  • 11
  • 28
  • You may directly use `cat = cat.replace("meow", "Meow!")`. I think the example is not a good one. Do you mean to ask how to swap two strings without creating a temporary variable? – Wiktor Stribiżew Jul 20 '17 at 18:25
  • @WiktorStribiżew Just providing multiple cases where you're setting the variable to itself. No end game goal with the above code. :P – Capn Jack Jul 20 '17 at 18:30

2 Answers2

2

In C#, strings are immutable. This means that you can't safely change a string value that a variable refers to. i.e. there is no method that looks like:

string cat = "meow";
cat.replace("meow", "purr");
Console.WriteLine(cat); // expected "purr", but output is still "meow"

You could write wrapper methods for each of the string operations you want to mutate a variable, like:

void replace(ref string value, string regex, string replaceString) {
    value = value.replace(regex, replaceString);
}

And then use it like:

replace(cat, "meow", "purr");

BUT, don't do that. It's messy and unmaintainable. Writing methods for each of the String operations you might want to perform, just so you can achieve the illusion of string mutability isn't good practice.

You can try using StringBuilder instead, which would look like:

string cat = "meow";
StringBuilder stringBuilder = new StringBuilder(cat);
stringBuilder.Replace("meow", "purr");
Console.WriteLine(stringBuilder.ToString());
Jace J McPherson
  • 450
  • 3
  • 13
1

From the documentation:

Because strings are immutable, it is not possible (without using unsafe code) to modify the value of a string object after it has been created. However, there are many ways to modify the value of a string and store the result in a new string object.

What you CAN do however is use the StringBuilder class:

StringBuilder builder = new StringBuilder();
builder.Append("Juan");
builder.Replace("Juan", "Javier");
Console.WriteLine(builder.ToString()); //This outputs "Javier"

StringBuilder also allows you to modify the string at the character level with an index:

builder[0] = 'X';
Console.WriteLine(builder.ToString()); //This outputs "Xavier"
JuanR
  • 7,405
  • 1
  • 19
  • 30
  • hmmm, any down sides to string builder? Why ever use `string` over `StringBuilder`? – Capn Jack Jul 20 '17 at 18:31
  • @CapnJack: The difference is precisely what you want. StringBuilder exists for situations like this where you DON'T want to create new instances. Because StringBuilder maintains an internal buffer of characters, it allows you to make changes without creating new instances. – JuanR Jul 20 '17 at 18:33
  • @CapnJack: This may not be a problem for a small number of operations but when performance is paramount and you have millions of them, having a buffer (which you can initialize to a known size, by the way) becomes very useful and much more performant. – JuanR Jul 20 '17 at 18:35
  • That makes a lot of sense. Also reading about the same string on different threads helped highlight the differences too. Thanks a lot man. – Capn Jack Jul 20 '17 at 18:38