我对Delphi有些新意,这个问题只是让我很好奇.(我也只是偶然尝试使用它才发现我不应该这样做.)
如果您查看文档,TObject.InitInstance它会告诉您不要使用它,除非您重写NewInstance.该方法也是公开的.如果用户永远不应该打电话给它,为什么不让它受到保护?
All*_*uer 28
因为我在整个Delphi的事情在1992年中期开始时就已经出现了,所以这个问题可能有几个答案.如果你在Delphi 1中查看TObject的原始声明,TObject上没有任何受保护/私有成员.这是因为在Delphi开发的早期阶段,并且在引入语言异常的同时,异常是从与其他对象不同的堆中分配的.这是NewInstance/InitInstance/CleanupInstance/FreeInstance函数的起源.重写你的类类型这些功能你可以从字面上控制,其中一个对象被分配.
近年来,我使用此功能创建了一个字面上"循环"的对象实例缓存.通过拦截NewInstance和FreeInstance,我创建了一个系统,其中实例在取消分配时不会返回到堆,而是放在无锁/低锁链表上.这使得分配/释放特定类型的实例的速度更快,并消除了大量进入内存管理器的偏移.
通过公开InitInstance(其中相反的是CleanupInstance),这将允许从其他实用程序函数调用这些方法.在我提到的上述情况中,可以在现有的内存块上调用InitInstance,而不必仅从NewInstance调用.假设NewInstance调用管理上述缓存的通用函数.类实例的"范围"已丢失,因此调用InitInstance的唯一方法是公共.
有一天,我们可能会发布执行上述描述的代码......现在它是内部"研究"项目的一部分.
哦,作为一个旁边,还有一点历史课...在Delphi 1发布之前,如何分配/释放Exception实例的设计被返回到使用与所有其他对象相同的堆.由于整体的集体失误,我们假设我们需要分配所有Exception对象实例以"保护"内存不足的情况.我们推断如果因为内存管理器"内存不足"而尝试引发异常,那么我们如何分配异常实例!?我们已经知道那时没有记忆了!因此我们决定在所有异常中都需要一个单独的堆...直到Chuck Jazdzewski或Anders Heijlsberg(我确切地忘记了哪一个),找出一个简单,相当聪明的解决方案......只需预先分配内存不足异常在启动时!我们仍然需要控制是否应该实际释放异常(异常实例在处理后自动释放),因此整个NewInstance/FreeInstance机制仍然存在.