(delphi11最新学习资料) Object Pascal 学习笔记---第11章第1节 (Weak 和 Unsafe 类型接口引用)

11.1.4 Weak 和 Unsafe 类型接口引用

​ 从 Delphi 10.1 Berlin 开始,Object Pascal 语言对接口引用的管理进行了优化。实际上,Object Pascal 语言提供了不同类型的引用:

  • 常规引用在分配和释放时分别递增和递减对象引用计数,最终在引用计数为零时释放对象。

  • 弱引用(标有[weak]修饰符)不会增加所引用对象的引用计数。这些引用是完全可管理的,因此如果被引用对象被销毁,它们会被自动设置为nil。

  • 不安全引用(标有[unsafe]修饰符)不会增加其引用对象的引用计数,并且不受管理–这与基本指针没有太大区别。

    注解 弱引用和不安全引用的使用最初是作为移动平台 ARC 内存管理支持的一部分引入的。由于 ARC 现已淘汰,因此该功能仅适用于接口引用。

​ 通常引用计数在处于激活状态的情况下,你可以使用如下代码,该代码依赖引用计数来释放临时对象:

procedure TForm3.Button2Click(Sender: TObject);
varOneIntf: ISimpleInterface;
beginOneIntf := TObjectOne.Create;OneIntf.DoSomething;
end;

​ 如果对象有一个标准的引用计数实现,而您想创建一个不计入引用总数的接口引用,该怎么办?现在,您可以通过在接口变量声明中添加 [unsafe] 属性来实现这一目的,将上面的代码更改为:

procedure TForm3.Button2Click(Sender: TObject);
var[unsafe] OneIntf: ISimpleInterface;
beginOneIntf := TObjectOne.Create;OneIntf.DoSomething;
end;

​ 这并不是一个好主意,因为上述代码会导致内存泄漏。通过禁用引用计数,当变量离开作用域时,什么也不会发生。在某些情况下,这样做是有好处的,因为你仍然可以使用接口,而不会触发额外的引用。换句话说,不安全引用就像指针一样,不需要额外的编译器支持。
​ 现在,在你打算使用[unsafe] 属性而不增加引用计数的时候,请考虑一下,在大多数情况下,还有另一种更好的选择:使用弱(weak)引用。弱引用也可以避免增加引用计数,但它们是受管理的。这意味着系统会跟踪弱引用,如果实际对象被删除,系统会将弱引用设置为nil。相反,如果使用不安全引用,则无法知道目标对象的状态(这种情况称为悬挂引用)。

​ 弱引用在哪些情况下有用?一个典型的情况是两个对象相互引用。事实上,在这种情况下,该对象会武断地增加其他对象的引用计数,并导致对象基本上会永远被保留在内存中(随着引用计数被设置为 1),即使对象变得不可访问也是如此。

​ 举例来说,下面的接口接受对另一个同类型接口的引用,而类通过内部引用实现这一个功能:

typeISimpleInterface = interfaceprocedure DoSomething;procedure AddObjectRef(Simple: ISimpleInterface); end;TObjectOne = class(TInterfacedObject, ISimpleInterface) privateAnotherObj: ISimpleInterface;publicprocedure DoSomething;procedure AddObjectRef(Simple: ISimpleInterface);end;

​ 如果创建两个对象并交叉引用,就会导致内存泄漏:

varOne, Two: ISimpleInterface;
beginOne := TObjectOne.Create;Two := TObjectOne.Create;One.AddObjectRef(Two);Two.AddObjectRef(One);

​ 现在,在Delphi中的解决方案是将私有字段 AnotherObj 标记为弱引用(weak interface reference):

private[weak] AnotherObj: ISimpleInterface;

​ 有了这一改动,在将对象作为参数传递给 AddObjectRef 调用时,引用计数不会被修改,而是保持为 1,当变量离开作用域时,引用计数会归零,从而将对象从内存中释放出来。

​ 现在有了这一功能,在许多其他类似情况下都变得非常方便,尽管底层实现非常复杂。弱引用是一项重要的功能,但要完全掌握它还需要进一步的努力。此外,由于弱引用是受管理的(而不安全引用则不受管理),因此在运行时也会产生一些代价。

​ 有关接口的弱引用及其工作原理的更多信息,请参阅第 13 章 "对象与内存 "中的 "内存管理与接口 "一节。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/bicheng/8022.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

控制元素隐藏

一、隐藏元素 在CSS中,有几种方法可以隐藏元素,每种方法都有其特定的用例和效果。以下是一些常用的CSS属性和技巧,用于隐藏元素: display: none; 这是最常用的隐藏元素的方法。它会将元素完全从文档流中移除,元素不会…

docker搭建代码审计平台sonarqube

docker搭建代码审计平台sonarqube 一、代码审计关注的质量指标二、静态分析技术分类三、sonarqube流程四、快速搭建sonarqube五、sonarqube scanner的安装和使用 一、代码审计关注的质量指标 代码坏味道 代码规范技术债评估 bug和漏洞代码重复度单测与集成 测试用例数量覆盖率…

node报错——解决Error: error:0308010C:digital envelope routines::unsupported——亲测可用

今天在打包vue2项目时,遇到一个报错: 最关键的代码如下: Error: error:0308010C:digital envelope routines::unsupportedat new Hash (node:internal/crypto/hash:80:19)百度后发现是node版本的问题。 在昨天我确实操作了一下node&…

Ansible——Playbook剧本

目录 一、Playbook概述 1.Playbook定义 2.Playbook组成 3.Playbook配置文件详解 4.运行Playbook 4.1Ansible-Playbook相关命令 4.2运行Playbook启动httpd服务 4.3变量的定义和引用 4.4指定远程主机sudo切换用户 4.5When——条件判断 4.6迭代 4.6.1创建文件夹 4.6.2…

[Linux][网络][TCP][四][流量控制][拥塞控制]详细讲解

目录 1.流量控制2.拥塞控制0.为什么要有拥塞控制,不是有流量控制么?1.什么是拥塞窗口?和发送窗口有什么关系呢?2.怎么知道当前网络是否出现了拥塞呢?3.拥塞控制有哪些算法?4.慢启动5.拥塞避免6.拥塞发生7.快…

劝退计算机?CS再过几年会没落!?

事实上,未来计算机不仅不会没落,国家还会大力发展 只不过大家认为的计算机就是什么Java web,真正的计算机行业是老美那样的,涉及到方方面面,比如: web,图形学,Linux系统开发&#…

pip 安装插件加速技巧: 修改为国内源

在国内,用 pip 安装 python 依赖包的时候,总是会遇到 Timeout 或者下载太慢的问题。 这是因为 pip 源在国外,解决方法就是把 pip 源改成国内的,就可以实现 pip install 加速。 1. 国内有哪些 pip 源? 国内有几个名气比…

2024DCIC海上风电出力预测Top方案 + 光伏发电出力高分方案学习记录

海上风电出力预测 赛题数据 海上风电出力预测的用电数据分为训练组和测试组两大类,主要包括风电场基本信息、气象变量数据和实际功率数据三个部分。风电场基本信息主要是各风电场的装机容量等信息;气象变量数据是从2022年1月到2024年1月份,…

Skywalking数据持久化与自定义链路追踪

学习本篇文章之前首先要了解一下Sky walking的基础知识 分布式链路追踪工具Skywalking详解 一,Sky walking数据持久化 Sky walking提供了es,MySQL等数据持久化方案,默认使用h2基于内存的数据库,重启之后数据即会丢失。 在实际工…

ORM框架在Java、Python、PHP中与MySQL的交互及优缺点比较

在现代软件开发中,对象关系映射(Object-Relational Mapping,简称ORM)框架已经成为连接应用程序与数据库的重要工具。ORM框架通过提供一组方法,将数据库中的表与应用程序中的对象进行映射,从而简化了数据访问…

博客园商业化之路-众包平台:从第一单看基于「开发任务」的定位

虽然我们一再强调我们做的是「开发任务」众包平台,还是被不少人误解为「项目」众包平台,正好我们遇到的第一单就是一个典型案例,简单发篇博文分享一下。 4月29日我们开始召集众包平台的早期合作开发者,先以手动挡方式&#xff08…

微信小程序下载文件详解

在微信小程序中,下载文件通常涉及使用 wx.downloadFile API。这个 API 可以将网络资源下载到本地临时文件路径,然后你可以使用 wx.saveFile 将临时文件保存到本地持久存储位置。下面是一个下载文件的详细过程: 使用 wx.downloadFile 下载文件…

【Git】Git学习-16:git merge,且解决合并冲突

学习视频链接: 【GeekHour】一小时Git教程_哔哩哔哩_bilibili​编辑https://www.bilibili.com/video/BV1HM411377j/?vd_source95dda35ac10d1ae6785cc7006f365780 1 创建分支dev,并用merge合并master分支,使dev分支合并上master分支中内容为…

【学习笔记】HarmonyOS 4.0 鸿蒙Next 应用开发--安装开发环境

开发前的准备 首先先到官网去下载Devco Studio 这个开发工具,https://developer.harmonyos.com/cn/develop/deveco-studio/#download 提供了WIndows和Mac的开发环境,我自己是Windows的开发环境。 所以下载之后直接点击exe进行安装即可。 如果之前安装过…

C#WPF控件ViewBox详解

本文详解C#WPF控件ViewBox。 目录 定义 常用的属性 事件 实例 定义 ViewBox控件是一个用于缩放和调整其子元素大小的容器控件。它可以根据可用空间自动调整子元素的大小,以使其适应ViewBox的边界。这使得在不同尺寸的窗口或布局中保持元素的比例和缩放变得更加容易。

vue如何进行如何进行移动端的响应式布局

在Vue中进行移动端的响应式布局,通常涉及使用CSS媒体查询、灵活的盒模型布局、以及可能的第三方库或框架,如Vue UI库。下面是一个简单的Vue组件示例,展示了如何构建移动端的响应式布局: 首先,确保你有一个Vue项目。如…

Eplan带你做项目——如何实现项目的交付

前言 Eplan作为一款专业的电气工程设计软件,不仅在设计阶段为电气工程师提供了强大的绘图、计算、仿真等功能,还具备丰富的数据管理与交换能力,能够便捷、准确地导出软件设计、生产制造所需的数据,实现电气设计与软件设计、生产制…

Moby简介:openEuler 中的开源docker引擎

Moby 是一个开源的容器化引擎,它提供了创建和管理容器所需的核心功能。在 openEuler 系统中,Moby 作为容器技术的实现之一,它允许用户利用容器化技术来部署、运行和移植应用程序。 Moby 的功能和作用: 1. **容器创建**&#xff…

反汇编一个ARM64的机器码

文章目录 使用objdump直接阅读ARM64手册使用反汇编网站 有下面一个机器码:0x929ffee9,如何翻译成汇编呢? 下面介绍几种做法: 使用objdump 将这个机器码写到文件中,然后使用objdump去反汇编 创建一个二进制文件 dd…

Golang | Leetcode Golang题解之第67题二进制求和

题目&#xff1a; 题解&#xff1a; func addBinary(a string, b string) string {ans : ""carry : 0lenA, lenB : len(a), len(b)n : max(lenA, lenB)for i : 0; i < n; i {if i < lenA {carry int(a[lenA-i-1] - 0)}if i < lenB {carry int(b[lenB-i-1…