赞 | 0 |
VIP | 2 |
好人卡 | 27 |
积分 | 1 |
经验 | 26327 |
最后登录 | 2019-10-13 |
在线时间 | 953 小时 |
Lv1.梦旅人
- 梦石
- 0
- 星屑
- 120
- 在线时间
- 953 小时
- 注册时间
- 2007-4-25
- 帖子
- 805
|
本帖最后由 苏小脉 于 2011-9-4 04:41 编辑
精灵使者 发表于 2011-9-3 22:47 ![]()
不过我确实测试clone是可以通过的。
@苏小脉
乱嚼舌头。Cache 存在便是为了共享内存,若需分配新内存,又何 ...
仆并未言道不能“通过”,只是说如若每次都克隆一份,那将失去 Cache 共享内存、避免不必要内存拷贝的意义。仅有的好处便是数字图像解码的过程被 cache 了。
>> 若是用 Object#clone 拷贝值,被调用者便止于修改复件而无法修改原件。
这一点很重要,如果首先共享了内存而又对共享后的东西作改动的话,所有的Cache的被调用者将会调用修改后的东西,那会是很危险的。
Ruby 的危险功能不知其数,然 Ruby 设计哲学是在给用户最大限度的自由的同时又相信用户有自己判断何所为何所不为的能力,更不提“被调用者修改调用者传递的数据”是各种编程语言中都常用的手法。永远使用数据拷贝的手法在函数式递归编程中更常用,但依赖于强大的 GC 性能。
@熊猫
看你的解释貌似是[分配一个新的String对象]就等于clone然后赋值了,这部分操作被ruby封装了。
或许仆于君之原句理解有误,理当先确认一番。
- a = 'hello'
- b = 'hello'
- p a.object_id == b.object_id # => false
复制代码 “可以直接赋值而不用clone创建新的对象”可是指以上现象?
此处并非一个克隆过程,但与克隆的结果相同 [1]。盖因 Ruby 解释器在词法、文法分析时会构建并维护一个内部的抽象语法树,而两个 "hello" 单词(须得是字符串字面值)则分别会成为语法树的两个(一致的)节点。之后解释器便从树根起步走遍整个树,见到第一个 "hello" 节点,便和 Ruby 堆通信并生成一个 String 对象,见到第二个 "hello" 节点,又和 Ruby 堆通信并生成另一个 String 对象,如此 Ruby 堆中便有了两个内容为 "hello" 的 String 对象,但其过程又非是克隆。
[1] 即生成了两个一致的字串 "hello"。 |
|