DELPHI盒子
!实时搜索: 盒子论坛 | 注册用户 | 修改信息 | 退出
检举帖 | 全文检索 | 关闭广告 | 捐赠
技术论坛
 用户名
 密  码
自动登陆(30天有效)
忘了密码
≡技术区≡
DELPHI技术
移动应用开发
Web应用开发
数据库专区
报表专区
网络通讯
开源项目
论坛精华贴
≡发布区≡
发布代码
发布控件
文档资料
经典工具
≡事务区≡
网站意见
盒子之家
招聘应聘
信息交换
论坛信息
最新加入: g929959149
今日帖子: 27
在线用户: 16
导航: 论坛 -> DELPHI技术 斑竹:liumazi,sephil  
作者:
男 lordaeron (Terry) ★☆☆☆☆ -
注册会员
2022/5/9 22:29:28
标题:
開發container 的注意事項 浏览:344
加入我的收藏
楼主: 看很多人,都習慣了會有GC 的Language,對memory的使用漫不經心。
對小型系統(資料量少,Concurrent 少),你可以隨時shutdown 的,倒是無所胃。
但資料量一大,GC 來不級回收,又或者寫的人根本沒在注意。一下就OOM了。
回到Object Pascal,除了string 外,其它的new/allocmem 出來的 Object/Record 
都得要注意release.
哪麼,開發container 時,就更需注意這些事了。
其中有
一、container 本身的的bucket record。
二、user 要container 保存的object/record。
第一項,處理方式,採大水庫處理,bucket 不作 destroy 而是放到一個指向unused bucket 的pointer,用Link list的方式保留起來,方便下次要bucket 時,就可以不用每次都
new/allocmem。而只有在container 本身被destroy 時,才一拼
destroy掉所有bucket。
這樣的好處是可以防止memory 的碎片化以及大量 new/destroy 的OS call 的開銷。
但有好必有壞,這種做法亦有明顯的問題。就是memory 很容易
集中在同一container 手上。
第二項,由於java 的習慣其它的GC language 也相同,object 丟給container。object 的destroy就沒user 的事了。一切交給GC。最終就看到很多人,寫小系統一嘴炮。量一大,就四處找BUG ,到處求救。

最終一副就是,你new 的東西,由別人destroy。如果哪人沒 destroy,就是哪人的錯。

由於以上的現象,在開發container 時,除了要注意bucket的 destroy 外,
user 丟進bucket 的東西,必需要有由user 提供一個scavenger function,
在container 需要destroy/clear bucket 時,用scavenger function,來處理
bucket 的內容物。不然memory leak 就會發生了。
----------------------------------------------
-
作者:
男 pcplayer (pcplayer) ★☆☆☆☆ -
普通会员
2022/5/10 13:44:48
1楼: 用 Delphi,自己写一个自动化管理对象生命周期的框架,包括了对象缓冲池功能,避免了频繁创建和释放带来的 CPU 消耗,200行代码都不用。

关键是利用 Delphi 的 interface 的接口引用计数功能。我在04年时就做了一个,运行良好,从来不用关注释放问题,而且效率也非常高。
----------------------------------------------
-
作者:
男 luckyso999 (luckyso) ★☆☆☆☆ -
盒子活跃会员
2022/5/10 13:46:18
2楼: 听上去特别好啊,能分享一下吗@pcplayer
----------------------------------------------
-
作者:
男 lordaeron (Terry) ★☆☆☆☆ -
注册会员
2022/5/10 13:49:51
3楼: 我是不知你寫得有多好,但從現況就是,不管JAVA, .NET, JS 等,
都有這樣的問題,而產生OOM。
----------------------------------------------
-
作者:
男 lordaeron (Terry) ★☆☆☆☆ -
注册会员
2022/5/10 16:19:42
4楼: 我猜 pcplayer 指的是TMemoryManager ,
https://www.freepascal.org/docs-html/prog/progsu174.html

這東西, 和container 的需求並不相同。看來是雞同鴨講。
----------------------------------------------
-
作者:
男 sxqwhxq (步惊云) ★☆☆☆☆ -
普通会员
2022/5/10 20:17:46
5楼: 这种如果开发高并发,是必须要认真考虑的问题
----------------------------------------------
-
作者:
男 wr960204 (武稀松) ★☆☆☆☆ -
盒子活跃会员
2022/5/11 10:37:02
6楼: 仅仅是考虑内存的分噢诶和释放的话,实际上Delphi内存的管理器已经做了,你释放的内存并没有被还给操作系统,下次分配内存块的时候会被复用。你设计的池也就仅仅能减少对象的构造/析构花费的时间。
另外你容器里面的对象并不好判断什么时候该回收,重用的时候怎么复原。
Java等语言有对象的跟踪机制,垃圾回收器有好几种做法,可以知道对象是否是真正的废弃了。而Delphi的对象并不支持这个。
想要自动回收还是Interface的引用计数比较实用快捷。唯一的问题就是不能循环引用。苹果的Objective-C也是引用计数机制的,解决循环引用的方法是提供弱引用。
Delphi高版本有提供了一种Managed Record的,生存期自管理的record。
如果再能提供以下操作符“.”的重载,指向内部以的对象,就可以方便的实现智能指针,可以用Managed Record套在对象上实现生存期自管理,还能用"."来转向对象的属性和方法。只可惜Delphi做什么都是支持,但不彻底
----------------------------------------------
武稀松http://www.raysoftware.cn
作者:
男 lordaeron (Terry) ★☆☆☆☆ -
注册会员
2022/5/11 11:07:00
7楼: https://docwiki.embarcadero.com/RADStudio/Sydney/en/Memory_Management
從上述得知,只有win32 and win64 使用FASTMM。
其它的平台,就是原生OS。
Java的 "可以知道对象是否是真正的废弃了" 這故事並沒有發生。
Delphi 或 FPC 也只有string 有作 reference counting.
其它的回收,還是請自理。
GC 並沒有"徹底" 解決問題的方法。
有人能想出來,並實作出來,是一定可以拿個圖靈獎 ACM A.M. Turing Award。
並直接解決NP 問題,halting problem 就被解決了。
連數學界的諾貝爾: 費爾茲獎 (Fields medals) 或與奈望林納獎 (Nevanlinna prize)
一拼拿到。加油吧。
Java的GC 算法,是確定沒拿到了。
----------------------------------------------
-
作者:
男 pcplayer (pcplayer) ★☆☆☆☆ -
普通会员
2022/5/11 12:12:32
7楼: 我的作法就是利用 Delphi 的接口引用计数。我修改了接口类的那个引用计数为零自动释放的代码,改为引用计数为零回到那个类的类工厂里面的对象缓冲池。

这样做的目的,其实就是:

1. 避免哪里没有释放导致的内存泄漏。实际上当时做这个,就是因为一个同事做到东西,存在内存泄漏。当时那个程序每秒会需要几十个上百个新的对象,用完了需要释放掉。总有地方没处理好,导致眼睛看得见的内存持续上升。懒得到处检查代码,就做了一个这样的东西。

2. 对象既然缓冲了,就不用每秒有几十个上百个对象的创建和释放,CPU 占用立马就降下来了。

源代码我记得好像在网上发布过。忘记发在哪里了。
----------------------------------------------
-
信息
登陆以后才能回复
Copyright © 2CCC.Com 盒子论坛 v2.1 版权所有 页面执行39.0625毫秒 RSS