问题
The following is valid in c# as Char
can be implicitly cast to int
int i = 'a';
i am just curious about what .Net Framework do behind the scenes, i looked in to char
and int
types source code but unable to find where it's written.
Can any body explain what happens behind the scene?
回答1:
In C# we have something that is called a Single-Rooted unified type system. That means every existing type is a subtype of one root type. Object
in C#. So char
or int
is only short (alias) for System.Char
and System.Int32
. The conversion from an untyped Object
to long
or char
(value types) is called (un)boxing
.
This is a real difference compared to Java where there are the primitive types int
,char
.. and there is Object
. Java classes like Int
are wrapping the primitive types. https://en.wikipedia.org/wiki/Comparison_of_C_Sharp_and_Java
Because in C# everything is an Object
(I am Object, for we are many!), all the value types implement IConvertible
, as the others said.
And there is a mostly internally used enum TypeCode
that is the runtime reflection info that is assigned to value type object´s like int
. The Convert.To
method´s are using this type information to do their job.
http://referencesource.microsoft.com/#mscorlib/system/convert.cs
The mscorlib (System namespace) can be found on github under https://github.com/dotnet/coreclr/tree/master/src/mscorlib/src/System
Further because value types are full objects (struct) lots of type/meta information is available during runtime.
C# is a safe(er) language compared to c++ for example. It does not allow unsafe impilict casts.
The cast from char
to int
is a widening
. Int
is bigger/has more space than char
. It´s safe to cast.
But that´s why it is not the same as (int) 'a'
like Joanvo wrote.
This is an explicit cast and you are forcing .Net to do it, no matter it´s safe or not.
For int i = 'a';
it´s fine to do an implicit cast because of the widening.
But if you try char c = 42;
Visual Studio and the compiler will not allow it. Unless you force it with an explicit cast while being aware that maybe not all information from the int
will fit into the char
This is also the reason why you can not use something different than a boolean (expression) inside an if.
In C/C++ you can write if(1) { }
or if(0) {}
. That is not allowed in C#, where you have to write if(..==1) {}
. In C/C++ this is often used to check pointer for null.
You can overload the implicit
and explicit
operator for own types, which is useful sometimes. At least useful to know it is possible.
https://msdn.microsoft.com/en-us/library/z5z9kes2.aspx
回答2:
As @shahwat and @joanvo said its the ASCII value that will be stored in i.
See this,
char value = 'a';
Console.WriteLine(value);
Console.WriteLine((int)value);
Console.WriteLine(value == 'y');
Console.WriteLine(value.GetType());
Console.WriteLine(typeof(char));
Console.WriteLine((int)char.MinValue);
Console.WriteLine((int)char.MaxValue);
Out Put:
a
97 (Integer value of char)
False
System.Char
System.Char
0 (MinValue as an integer)
65535 (MaxValue as an integer)
Edit:
microsoft
On this microsoft reference you can find the implementation of every method.
Just need to click on specific method and you will be navigated to the defination of that method.
You can also add specific VS extension related to your requirement
For ex:
Download VS extensions
by this way you would have a functionality in your VS and you can see the implementation by just right cicking on the methods and selecting "Go to Defination"
For your scenario
int i ='a';
This is not really a method (in some sense).
To view its implementation you have to use
roslyn
I am not sure would this be possible in case of Resharper , but i have just provided a way by which you can get this done.Hope this would be some help to you.
Here is a step by step guide for your scenario:
1.Setup Environment (Install VS,Roslyn) here
roslyn
2.Enable .NET Framework Source debug (if its not enabled by default)
Enable Source Debug
3.Put a break point on your statement int i='a'
4.Press f11 to step through all the implementation which is written behind this statement.
Thats all you have to do.
Imp note:
I would like to add one more thing that if above method does not worked for you ,then it would be something related to MSIL.So in that case you need to analyse what Roslyn generates from this code.
And if this is the case then you can also check it with any Reflector tool that will show you the generated MSIL.
回答3:
The source code for the .NET primitive types is at http://referencesource.microsoft.com/, as indicated by @Sadaquat.
The specific implementation you're talking about is probably the implementation of IConvertable.ToInt32() from the Char struct.
That simply returns Convert.ToInt32(char value), which itself simply returns the value, since char
s are integer values behind the scenes.
来源:https://stackoverflow.com/questions/32094604/char-to-int-implicit-cast-behind-the-scenes