You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Delphi中使用RTTI判断控件只读且避免抛出异常?

更优雅的Delphi RTTI判断控件只读状态实现方式

你的原代码通过try-except捕获属性不存在的异常来实现功能,虽然能正常运行,但依赖异常处理的方式不够优雅,且存在不必要的性能开销。以下是两种无需捕获异常的更优实现:

方式一:使用GetPropInfo提前检查属性(兼容旧版Delphi)

function ControlIsReadOnly(const Control: TControl): Boolean;
var
  PropInfo: PPropInfo;
begin
  PropInfo := GetPropInfo(Control.ClassInfo, 'ReadOnly');
  // 同时检查属性存在且类型为布尔型,避免类型不匹配问题
  if Assigned(PropInfo) and (PropInfo^.PropType^.Kind = tkBoolean) then
    Result := GetPropValue(Control, PropInfo)
  else
    Result := False;
end;

这种方式先通过GetPropInfo获取属性的元信息,确认属性存在且类型符合预期后,再安全获取属性值,完全不需要依赖异常处理来兜底。

方式二:使用现代RTTI单元(Delphi 2010及以上版本)

uses
  Rtti;

function ControlIsReadOnly(const Control: TControl): Boolean;
var
  Context: TRttiContext;
  Prop: TRttiProperty;
begin
  Result := False;
  Context := TRttiContext.Create;
  try
    Prop := Context.GetType(Control.ClassType).GetProperty('ReadOnly');
    // 验证属性存在且为布尔类型
    if Assigned(Prop) and (Prop.PropertyType.TypeKind = tkBoolean) then
      Result := Prop.GetValue(Control).AsBoolean;
  finally
    Context.Free;
  end;
end;

借助TRttiContext可以更灵活地访问类型元数据,代码逻辑更清晰,同样通过提前检查避免了异常的抛出,性能和可读性都更优。

补充:异常处理的性能成本较高,尤其是在频繁调用该函数的场景下,提前检查属性存在性的方式能有效提升代码效率,同时让逻辑更直观。

内容的提问来源于stack exchange,提问作者Alister

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.22 11:36:05