Delphi2010的RTTI增强

Delphi编译的文件体积增大了很多.很大一部分原因是因为Delphi2010默认提供了全信息的RTTI.

每一个数据类型都有全部运行时信息.例如可以在运行时获得结构体的成员以及成员类型等.

这个功能带来的方便就是我们可以写很多通用的序列化方法.也可以做一些类似OR的东西.

相反这个功能带来的缺点就是文件体积将增大.

不过有一个解决方案.就是把运行时信息的编译开关关掉.但是编译期间连接的库在Lib目录下.这些DCU文件却都是带RTTI信息的.所以编译出来的内容也会是非常大的.就只有修改VCL源代码,全部关掉运行时信息的编译开关.然后把代码编译成DCU.放在LibNORTTI目录下.然后把Delphi项目的Lib路径指向这里.就可以达到去掉RTTI信息缩小可执行文件体积的目的了.不过貌似CodeGear应该在Delphi上加上一个选项,然后编译出两套VCL的DCU.根据不同选项连接不同目录下的DCU文件.我想CodeGear之所以没有这样做的原因应该是怕影响编译出来程序的一致性吧.

好了我们初步探索一下增强的RTTI吧.说起来很简单.

第一步uses RTTI;

然后照搬模式:

var
  r : TRttiContext;
begin
  r := TRttiContext.Creat();

写获取RTTI信息的代码

r.Free;
end;

TRttiContext的方法

GetTypes是获取系统内全部类型的类型信息数组.返回值类型是TArray<TRttiType>.(用到了从Delphi2009以来增加的泛型)

FindType是按名字找查找类型信息.

GetPackages是返回运行时包

GetType有两个重载方法.

function GetType(ATypeInfo: Pointer): TRttiType; overload;可以返回任何指定类型的类型嘻嘻
    function GetType(AClass: TClass): TRttiType; overload;仅仅对Class有效.

下面就举个例子:

type
  TTestRecord = record
    a:string;
    b:Integer;
    c:Double;
  end;

TTestClass = class
  private
    a:string;
    b:Integer;
    c:Double;
  end;

var
  r : TRttiContext;
  rt : TRttiType;
  f : TRttiField;
begin
  r := TRttiContext.Create();

rt := r.GetType(TTestClass);
  for f in rt.GetFields() do
  begin
    OutputDebugString(PChar(Format(‘%s.%s:%s‘,[rt.Name, f.Name, f.FieldType.Name])));
  end;

r.Free;
end;

在Delphi的EventLog中就可以看到TTestClass的成员,不关它是私有还是公有的.

结构体和其他类型则可以用function GetType(ATypeInfo: Pointer): TRttiType;这个方法,当然这个方法也可以处理Class类型

所区别就在于要加上TypeInfo操作符取回类型信息指针.

var
  r : TRttiContext;
  rt : TRttiType;
  f : TRttiField;
begin
  r := TRttiContext.Create();

rt := r.GetType(TypeInfo(TTestClass));
  for f in rt.GetFields() do
  begin
    OutputDebugString(PChar(Format(‘%s.%s:%s‘,[rt.Name, f.Name, f.FieldType.Name])));
  end;

rt := r.GetType(TypeInfo(TTestRecord));
  for f in rt.GetFields() do
  begin
    OutputDebugString(PChar(Format(‘%s.%s:%s‘,[rt.Name, f.Name, f.FieldType.Name])));
  end;

r.Free;
end;

http://blog.csdn.net/wr960204/article/details/4584503

时间: 2024-12-22 20:54:30

Delphi2010的RTTI增强的相关文章

Delphi XE的RTTI增强,动态Hook某些内部事件

Delphi2010之后的RTTI做了很大休整,现在用起来很爽了哦.甚至可以获取某些类的内部私有单元,然后为其赋值!讲这个RTTI增强的,可以参考网上的多个博客内容,我列举一下: Delphi2010RTTI的增强 Delphi的Anymouse方法探秘 万一的Rtti系列 我这里的主要目的是挂钩某些内部私有事件,然后增加上一些自己的处理过程,这里我以TMenuItem的私有内部事件FOnChange作为例程. 这个私有事件在菜单内部绑定,我们平常状态下,在外部无法更改!但是XE之后这个问题不在

Delphi里的RTTI与反射(举例换掉FOnChange)

Delphi2010之后的RTTI做了很大休整,现在用起来很爽了哦.甚至可以获取某些类的内部私有单元,然后为其赋值!讲这个RTTI增强的,可以参考网上的多个博客内容,我列举一下:Delphi2010RTTI的增强Delphi的Anymouse方法探秘万一的Rtti系列 我这里的主要目的是挂钩某些内部私有事件,然后增加上一些自己的处理过程,这里我以TMenuItem的私有内部事件FOnChange作为例程.这个私有事件在菜单内部绑定,我们平常状态下,在外部无法更改!但是XE之后这个问题不在存在,使

减小Delphi2010程序的尺寸(关闭RTTI反射机制)

自从Delphi2010增强了RTTI反射机制后,编译出来的程序变得更大了,这是因为默认情况下 Delphi2010 给所有类都加上了RTTI信息(呵呵,不管你用不用它,好像实用价值确实不高,至少目前我不会去用的).虽说对程序的运行速度影响不大,但会增加安装程序的大小,这也是我们不愿看到的.有没有办法禁用RTTI信息,从而减小编译后程序的大小呢?,从文档中我们找到了方法. 一.在工程中用编译指令禁用RTTI 禁用的方法很简单,就是要在工程(dpr文件中.Delphi2010下项目文件是dproj

Delphi 的RTTI机制浅探&lt;一&gt;

目 录===============================================================================⊙ DFM 文件与持续机制(persistent)⊙ ReadComponentResFile / WriteComponentResFile 函数⊙ Delphi 持续机制框架简述⊙ 一个 TForm 对象的创建过程⊙ TStream Class 和 TStream.ReadComponent 方法⊙ TReader Class 和

c++中RTTI

RTTI 是"Runtime Type Information"的缩写,意思是:运行时类型信息.它提供了运行时确定对象类型的方法.本文将简略介绍 RTTI 的一些背景知识.描述 RTTI 的概念,并通过具体例子和代码介绍什么时候使用以及如何使用 RTTI:本文还将详细描述两个重要的 RTTI 运算符的使用方法,它们是 typeid 和 dynamic_cast.如何确定对象的动态类型呢?答案是使用内建的 RTTI 中的运算符:typeid 和 dynamic_cast. typeid的

[ ObjectListView ] - ListView的增强控件 - 前言 (翻译)

********************************************************************************** 原  标 题: A Much Easier to Use ListView 原文地址: https://www.codeproject.com/Articles/16009/A-Much-Easier-to-Use-ListView 翻       译: 于国栋 http://www.shannon.net.cn *********

Java Iterator和增强for循环 for each详解

Iterator是Java中的一个迭代器接口(Interface),用来提供标准的Java迭代器 Iterator支持泛型因为集合(Collection)类可以装入的类型是不确定的,从集合中取出的都是Object类型,加入泛型,就是告诉编译器确定要装入的对象类型,取值时就无需强制转换了. for each 是 Java 5 中新增的一个循环结构,本质上是一个Iterator,特点是可以用来遍历集合元素而不用考虑集合下标. 综合实例: package net.csdn.shf4715; impor

SAP第四代增强 BTE

SAP对FI模块真的做的非常透彻,所以称FI是SAP R/3 系统的中流砥柱啊,单就增强这块来看,之前有会计凭证的验证和替代,目前又出现了专为FI模块设计的增强方案BTE(OpenFI). BTE的设计思路还是比较简单,和BADI有点类似.在标准程序中留有OPEN_FI的出口(以函数OPEN_FI_PERFORM_eventid_type的形式存在),然后提供一个可配置的TABLE,可以在里面针对某个特定的Event维护自己定义的出口函数,标准程序走到这里,如果查出用户定义了出口函数,则会调用,

通过灰度线性映射增强图片对比度

Halcon中如何通过灰度线性映射增强图片对比度呢?不急,我先讲点其他的. 如果你用过Photoshop,那么想必对增强图像的对比度很熟悉.在Photoshop中,我们对下面这张图执行“色阶”调整: 执行“色阶”调整:可以观察到图片的对比度明显增强.(白的更白,黑的更黑了) 它的原理是这样的:将原图中灰度值小于55的点全部强制置为0,将灰度值高于140的点强制置为255,并且将55~140之间的色阶强行拓宽均匀映射到0~255之间,其效果是图像对比度增强了.如下图所示: 如果还不好理解,那么再看