我正在阅读有关拳击的内容,书中说"拳击可以正式定义为通过将变量存储在aSystem.Object中而将值类型显式转换为相应的引用类型的过程." (重点补充)
我的问题不是关于拳击,但这让我思考 - System.Object实例如何以及在何处存储分配给它的值/变量/对象.所以我不仅想知道
object objShort = 5;
Run Code Online (Sandbox Code Playgroud)
但是也
object someOtherObj = someReallyComplicatedObject;
Run Code Online (Sandbox Code Playgroud)
我一直在寻找,包括这里(MSDN System.Object),我没有看到任何描述System.Object实例如何实际存储其数据的地方.
对象只是简单地存储指向分配给它的对象的指针,或者在装箱的情况下,指向堆栈上值类型的指针?
(乔恩,请原谅我,如果这也出现在你的书中.我订购了它,它正在路上!)
拳击的描述是不准确的.创建的对象不仅仅是裸的实例System.Object; 每个值类型实际上都有自己的"隐藏"对应引用类型,它只是一个派生自ValueType实现与值类型相同的接口的类,并且具有值类型类型的字段.这当然是我对它的看法,至少,它大致是CLI规范描述它的方式.System.Object本身没有任何存储空间.
我还想纠正"存储变量"部分 - boxing将值存储在一个对象中.该值可能是变量的值,也可能是方法调用的结果,或者其他任何值.
当然,对于参考类型,根本不需要拳击.你真的需要区分一个引用和一个对象 - 一旦你在脑海中清楚地了解了这两个,大多数其他事情都很容易.然后记住,变量的值永远不是一个对象 - 它只是一个值类型值或引用(或指针:)
(哦,这在C#深度有所涉及,但不是很详细.你可能会对Eric Lippert的帖子"关于价值类型的真相"感兴趣.)
想象一下,有一个通用的引用类型,如下所示:
sealed class Box<T> : System.ValueType where T : struct
{
private T value;
public Box(T t)
{
this.value = t;
}
}
Run Code Online (Sandbox Code Playgroud)
还有一堆其他狡猾的东西:
Box<T>来T.T来Box<T>简单地调用构造函数.从概念上讲,从int到object的装箱转换只是将隐式转换运算符调用int到Box<int>.
当然,实际上没有这样的类型Box<T>,如果有的话,它必须充满古怪的东西; 你不能正常覆盖GetType,你不能正常地在一个类中扩展ValueType,它的可行类型的行为很奇怪,依此类推.所有这些细节都是CLR的实现细节,但它有助于想象CLR只是创建一个非常特殊类型的实例来完成装箱和拆箱的工作.
| 归档时间: |
|
| 查看次数: |
751 次 |
| 最近记录: |