String.Copy in C#



  • <font face="Verdana" size="2">Who has used this and why?  The code I'm looking at now uses String.Copy so that Replace can be called without modifying the origional string.  Something like:</font>

    <font face="Courier New" size="2">string x = "hello";
    string y = String.Copy(x);
    string z = y.Replace("e", "4");
    <font face="Verdana">
    </font><font face="Verdana" size="2">That's of course kinda dumb, but it makes me wonder where String.Copy should be used.
    </font></font>



  • Generally I think you'd only go here when you want to be explicit about how the memory is allocated.  For instance, take Copy's brother, Clone().  

    Clone() will return a reference to the same object, Copy will create a new object with the same value.  Most of the time we don't care.  But if you needed to re-use the same string (part of some pattern matching or text-assembly or word-processing system maybe) over and over again, you could save that memory by just using a reference.

    Of course, .NET strings are immutable, which means that regardless of how you do it, if you change the value of the string, it's going to create a new object and it'll break the reference, it won't propate the change through all the Clones....which does seem to make this pretty pointless unless you have one of those special cases...and unless it's a LOT of memory you'll be saving, it may not worth the extra code :)

    -cw



  • Hmm, that wasn't quite as clear as i wanted.  Oh well, one important missing point, the = operator does a clone (copies the reference). 

    Your coworker had the right idea, it was unnecessary because the Replace() function would have changed the string, causing a new object to be created anyway.



  • I can hardly think of a reason to use String.Copy, but maybe something along the lines of "unmanaged code modifying the unmodifyable" makes it desirable.



  • I wonder.

    Using server-side programming languages to build dynamic web-apps usually involves plenty of messing with strings: your output HTML is a string, and replace and concatenation operations are very common.

    So why don't they make a string-mutable version of these languages for web applications?

    Could it be because 95% of web scripts have a lifetime of 1 short page load and memory is cleared very quickly?



  • @dhromed said:

    I wonder.

    Using server-side programming languages to build dynamic web-apps usually involves plenty of messing with strings: your output HTML is a string, and replace and concatenation operations are very common.

    So why don't they make a string-mutable version of these languages for web applications?

    Could it be because 95% of web scripts have a lifetime of 1 short page load and memory is cleared very quickly?

    Nah, they did, it's called StringBuffer. 



  • StringBuilder in C#, which interestingly does not exactly have a Copy method.



  • @dhromed said:

    I wonder.

    Using server-side programming languages to build dynamic web-apps usually involves plenty of messing with strings: your output HTML is a string, and replace and concatenation operations are very common.

    So why don't they make a string-mutable version of these languages for web applications?

    Could it be because 95% of web scripts have a lifetime of 1 short page load and memory is cleared very quickly?

    You usually use mutable strings (StringBuffers/StringBuilders) and array joins (joins on String[] to concatenate several strings into a single one)



  • @CodeWhisperer said:

    Hmm, that wasn't quite as clear as i
    wanted.  Oh well, one important missing point, the = operator does
    a clone (copies the reference). 

    Your coworker had the right idea, it was unnecessary because the Replace() function would have changed the string, causing a new object to be created anyway.


    No and no:
    string aa="some string";
    string bb=aa.Replace("s", "a");
    Console.WriteLine("First \"{0}\", second \"{1}\"", aa, bb);

    Prints: First "some string", second "aome atring". String in c# behaves like int. It's value is copied with = operator, not reference. The code is a double WTF:
    String.Copy does the same as =
    string String.Replace(string, string) doesn't modify the original var


  • Actually, if you run the code below, you'll see that = does just copy the reference, and then the reference is broken after the replace:

    			
    <FONT color=#0000ff>String a = "some string";
    String b = a;
    

    bool same = Object.ReferenceEquals( a, b );
    Console.WriteLine("before replace, same = {0}", same ); // true here

    b = a.Replace("s", "a");
    same = Object.ReferenceEquals( a, b );
    Console.WriteLine("after replace, same = {0}", same ); // false now
    </FONT>

    -cw



  • Ok - I wasn't precise (or was... I wrote "behaves like").

    It copies value in <this case>. When you do
    a=some_string.Replace(...), then 'a' gets value of temporary result of
    some_string.Replace(...) (or becomes it's clone - whatever - 'a' is the
    only copy of the result in optimised code probably).

    Kind of CoW idea.



    However the first code is just lame. It makes useless copy of the first
    string. No idea why - it doesn't make any sense (out of context of
    course).

    And back to one of the first questions - as strings are using kind of
    CoW idea on every clone and don't do any modifications "in place", I
    think you could change every string.Copy() into = operator and it
    wouldn't change anything.



    Ok - maybe it would if you use some weird code checking for equal
    references of strings, but I don't see any use of it apart from
    "compressing" object dumps where you have many equal strings (either
    too time consuming typically, or you have strange coding style to have
    >50% of the strings equal)



  • @viraptor said:

    It copies value in <this case>.

    Actually, no, it doesn't.   It creates a new object with the new value, then it assignes the reference to that new string to the variable.   Ultimately it might 'appear' to be a copy, but you don't end up with two copies of the same string in memory -- which is the whole point. 

    -cw


Log in to reply