1)什么是int
?它与struct
System.Int32
有什么不同?我理解前者是CLR类型typedef
的C#别名(#define
或System.Int32
等效物)。这种理解是否正确?
2)当我们说:
IComparable x = 10;
就像说:
IComparable x = new System.Int32();
但我们不能new
结构,对吗?
或C语法:
struct System.In32 *x;
x=>someThing = 10;
3){em>大写S 的String
是什么?我在Reflector中看到它是sealed
String
类,当然,它是一个引用类型,与上面的System.Int32
不同,它是一个值类型。
什么是string
,虽然没有资本化?这也是这个类的C#别名吗?
为什么我在Reflector中看不到别名定义?
4)如果你愿意的话,试着跟着我这个微妙的思路。我们知道特定类型的存储位置只能访问其接口上的属性和成员。这意味着:
Person p = new Customer();
p.Name = "Water Cooler v2"; // legal because as Name is defined on Person.
但
// illegal without an explicit cast even though the backing
// store is a Customer, the storage location is of type
// Person, which doesn't support the member/method being
// accessed/called.
p.GetTotalValueOfOrdersMade();
现在,通过该推断,请考虑以下情况:
int i = 10;
// obvious System.object defines no member to
// store an integer value or any other value in.
// So, my question really is, when the integer is
// boxed, what is the *type* it is actually boxed to.
// In other words, what is the type that forms the
// backing store on the heap, for this operation?
object x = i;
更新
感谢您的回答,Eric Gunnerson和Aaronought。我担心我无法很好地表达我的问题以吸引非常令人满意的答案。麻烦的是,我确实知道表面问题的答案,而且我绝不是新手程序员。
但我不得不承认,只要我是程序员,即使我编写了正确的代码,对于语言及其底层平台/运行时如何处理类型存储的复杂性的深刻理解也一直困扰着我。
答案 0 :(得分:5)
int
是System.Int32
的别名。类型相同。
IComparable x = 10
类似于撰写var i = 10; IComparable x = i
。编译器选择它认为最常用的常量类型,然后隐式转换为IComparable
。
string
是System.String
的别名,类似于#1。您无法在Reflector中看到别名定义,因为别名是C#编译器的一部分,而不是.NET Framework本身。 (例如,在VB.NET中有所不同。)
盒装整数或其他值类型是对值的引用。您可能会将其视为附加了某些类型信息的指针。但是,实际的支持类型只是System.Object
。
答案 1 :(得分:2)
答案 2 :(得分:1)
1)是的。 “int”只是C#为System.Int32定义的别名。
2)你的第一个答案。
3)string是System.String类型的C#别名。因为几乎每个人都有“使用系统”;在他们的程序中,您可以使用“string”或“String”。
4)您可以将其视为存储在引用类型框中的int。即使框的类型仅作为“对象”可见,运行时也知道它内部有一个int。
这就是你不能写的原因:
int i = 10;
object x = i;
short j = (short) x; // this is an error because you can only unbox x as an int.
大部分内容都在C#语言参考或其中一本入门书中。
答案 3 :(得分:0)
1)int是System.Int32结构的别名。您可以在C#中为类型定义所需的任何别名。为此,您需要使用与您通常用于导入名称空间的使用语句类似的using语句。例如,如果我想创建一个System.Int64的别名并将其命名为number,我将在代码文件的开头使用statment编写以下内容:
using number = System.Int64;
然后,每次在代码中使用别名 number 时,编译器和intellisense都会将其视为System.Int64。
2)使用System.Int32的默认构造函数与将0赋值给整数变量相同。
IComparable x = new System.Int32();
与代码
相同IComparable x = 0;
可以将new运算符与结构一起使用。 new 的语义,用于分配对象所需的内存并调用构造函数。定义为结构的对象与定义为类的对象之间的差异是它的分配方式。 struct intances在堆栈中分配,而类实例在堆分配。
一些有趣的事实是C#not everything derivates from object。
3) string 是C#编译器的关键字(作为int关键字),这就是使用Reflector无法看到其定义的原因。实际上,编译器生成的IL代码现在甚至都不存在这些别名,因为它们在编译过程中仅由编译器使用。编译完成后,所有字符串引用都将成为已编译代码中的System.String。
4)这个问题的答案太长了,所以我建议你阅读以下文章:Representation and Identity