How does a String object allocate memory without a new keyword or constructor?

In C #, if we want to create a variable of type string , we can use:

 string str="samplestring"; // this will allocate the space to hold the string 

In C #, string is a type of class, so if we want to create an object, usually we should use the new keyword. So how distribution happens without new or constructors ?

+6
source share
7 answers

It is just a C # compiler that gives you a shortcut by allowing string literals.

If you prefer, you can instantiate the string with any number of constructors. For instance:

  char[] chars = { 'w', 'o', 'r', 'd' }; string myStr = new String(chars); 
+5
source

According to MS documentation, you do not need to use a new command to use the default string constructor.

However, this does work.

 char[] letters = { 'A', 'B', 'C' }; string alphabet = new string(letters); 

C # Strings (from the MSDN Programming Guide)

+3
source

When you write

 string str="samplestring"; 
Compiler

generates two commands:

  • First, ldstr gets a string literal from metadata; allocates the required amount of memory; creates a new String object and pushes a link to it on the stack.
  • Then stloc (or one of its short forms, for example stloc.0 ) stores this link in the local variable str .

Note that ldstr will allocate memory only once for each character sequence.

So, in the example below, both variables will point to the same object in memory:

 // CLR will allocate memory and create a new String object // from the string literal stored in the metadata string a = "abc"; // CLR won't create a new String object. Instead, it will look up for an existing // reference pointing to the String object created from "abc" literal string b = "abc"; 

This process is known as string interning .

Also, as you know, in .NET strings are immutable. Thus, the contents of the String object cannot be changed after the creation of the object. That is, every time you concatenate a string, the CLR will create a new String object.

For example, the following lines of code:

 string a = "abc"; string b = a + "xyz"; 

It will be compiled into the following IL (not really, of course):

  • ldstr will allocate memory and create a new String object from "abc" literal
  • stloc store the reference to this object in the local variable a
  • ldloc will push this link ldloc stack
  • ldstr will allocate memory and create a new String object from "xyz" literal
  • call will call System.String::Concat for these String objects on the stack
  • The System.String::Concat will be decomposed into dozens of IL statements and internal calls. Which, in short, will check the lengths of both lines and allocate the required amount of memory to store the result of the concatenation, and then copy these lines to the newly allocated memory.
  • stloc save the link to the newly created line in local variable b
+3
source

Strings are reference types. The variable holds the reference to the value in memory. Therefore, you simply assign a link, not a value, to the object. I would recommend you watch this video from Pluralsight (you can get a free trial in 14 days).

Pluralsight C # Basics - Strings

Disclaimer: I am in no way affiliated with Pluralsight. I am a subscriber and I love the video there.

+2
source

As long as everything is an object in .net, there are still primitive types (int, bool, etc.) that do not require instantiation. as you can see here , the string is the address of 4 bytes of ref, indicating a vector / array structure that can extend up to 2 GB. remember that strings are immutable types, so when you change a string, you do not edit the existing variable, but instead allocate new memory for the literal value, and then change the pointer to the string to indicate the new memory structure. hope that helps

+1
source

When you create a string using literals, internally, depending on your assembly, the NoStringInterning flag is checked or not, it looks like this:

 String str = new String("samplestring"); // or with NoStringInterning String str = String.Intern("samplestring"); 
0
source

In java, if you write something like this:

 String s1 = "abc"; String s2 = "abc"; 

memory will be allocated for "abc" in the so-called string pool, and both s1 and s2 will refer to this memory. And s1 == s2 will return true ("==" compares the links). But if you write:

 String s1 = new String("abc"); String s1 = new String("abc"); 

s1 == s2 will return false. I think in C # it will be the same.

-4
source

Source: https://habr.com/ru/post/928126/


All Articles