问题标签 [reference-counting]

For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.

0 投票
3 回答
106 浏览

objective-c - 什么会自动保留和释放?

我有点理解自动保留和释放的内容,但我找不到任何官方数据,我认为我做错了。

  1. 设置使用 @property(retain) 声明的属性将保留和释放旧值,但不会在同一对象内设置属性self.
  2. 方法内的所有对象(包括参数)在创建/传递时保留,在方法返回时释放。
  3. 方法返回的对象不会被释放,而是会被返回到的方法释放,因为它是方法内部的局部变量。

我做错了什么/忘记了什么吗?
当退货被丢弃时会发生什么?喜欢[object someMethodThatReturnsAnObject];。它不会是它返回的方法的本地,所以我不确定它是否会被释放并且 xCode 会发出警告。

0 投票
1 回答
1499 浏览

string - 为什么这个字符串的引用计数为 4?(德尔福 2007)

这是一个非常特定于 Delphi 的问题(甚至可能是 Delphi 2007 特定的)。我目前正在为实习字符串编写一个简单的 StringPool 类。作为一个优秀的小程序员,我还添加了单元测试,并发现了一些让我困惑的东西。

这是实习的代码:

没什么特别的:FList 是一个已排序的 TStringList,因此所有代码所做的只是在列表中查找字符串,如果它已经存在,则返回现有字符串。如果它还没有在列表中,它将首先调用 UniqueString 以确保引用计数为 1,然后将其添加到列表中。(我检查了 Result 的引用计数,在添加了两次 'hallo' 之后它是 3,正如预期的那样。)

现在到测试代码:

这会将字符串 'hallo' 添加到字符串池中两次,并检查字符串的引用计数以及 s1 和 s2 确实指向相同的字符串描述符。

每个 CheckEquals 都按预期工作,但最后一个。它失败并出现错误“预期:<3> 但原为:<4>”。

那么,为什么这里的引用计数是 4 呢?我本来期望3:

  • s1
  • s2
  • 另一个在 StringList

这是 Delphi 2007,因此字符串是 AnsiStrings。

哦,是的,函数 StringReferenceCount 实现为:

在调试器中,同样可以评估为:

只是补充一下 Serg 的答案(这似乎是 100% 正确):

如果我更换

然后检查 s3(和 s1)的引用计数,它是 3,如预期的那样。正是因为再次将 FPool.Intern(s2) 的结果赋值给 s2(s2 既是函数结果的参数,又是函数结果的目的地)导致了这种现象。Delphi 引入了一个隐藏的字符串变量来分配结果。

另外,如果我将函数更改为过程:

正如预期的那样,引用计数为 3,因为不需要隐藏变量。


如果有人对此 TStringPool 实现感兴趣:它在 MPL 下是开源的,可作为 dzlib 的一部分使用,而 dzlib 又是 dzchart 的一部分:

https://sourceforge.net/p/dzlib/code/HEAD/tree/dzlib/trunk/src/u_dzStringPool.pas

但如上所述:这不完全是火箭科学。;-)

0 投票
1 回答
685 浏览

iphone - 为什么保留/释放而不是新/删除?

我是 Objective-C 的新手,我觉得 C++ 很合适。

我的问题是: 为什么 obj-c 的语言设计器适合使用保留/释放而不是仅使用 new/delete(=alloc/dealloc)?

也许我的大脑只适合 new/delete 内存管理,我不明白为什么我应该管理引用计数,我想我知道什么时候对象必须是 alloc/dealloc 与我的 C++ 经验。

(是的,我花了 4 个小时调试引用计数问题,通过 1 行“发布”解决)

当我们使用参考计数器时,谁能解释我什么更好?(在编程语言方面)我认为我可以通过新建/删除来管理对象的生命周期,但我不能使用引用计数。

如果您有链接,我需要长篇文章来解释为什么引用计数器很有用。

PS:我在 WWDC 2011 上听说过 Compile-time Automatic Reference Counting,它真的很棒,例如可能是使用了引用计数器的原因。

0 投票
4 回答
113041 浏览

python - 如何强制删除python对象?

我很好奇__del__python中的细节,何时以及为什么应该使用它以及它不应该用于什么。我学到了一个艰难的方式,它并不像人们天真地期望从析构函数中得到的那样,因为它不是__new__/的对立面__init__

我在文档中看到,当解释器退出时,不能保证__del__()为仍然存在的对象调用方法。

  1. 如何保证对于Foo解释器退出时存在的任何实例,栏关闭?
  2. 在上面的代码片段中,栏是关闭del foo还是关闭gc.collect()......或者两者都没有?如果您想更好地控制这些细节(例如,当对象未被引用时应该关闭栏)通常的实现方法是什么?
  3. 什么时候__del__被调用是否保证__init__已经被调用?如果__init__提高了怎么办?
0 投票
2 回答
1129 浏览

java - 引用计数是好的设计吗

我们正在开发一个应用程序容器,它使用引用计数作为跟踪接收到的请求和发送的响应的机制。引用计数用于允许容器正常关闭,即if (refCount == 0) shutdown;

对于每个请求以及待处理的响应,引用计数都会增加。仅当应用程序接受请求并且仅当应用程序发送有效响应时,引用计数才会减少。所以这是我的问题,在这种情况下引用计数是否是一个好的设计决策,比如与RequestContext仅在应用程序/容器发送响应时保持关闭的情况相比?

由于该软件是用 Java 实现的,因此我正在查看 Java 中的其他选项并遇到了这篇文章http://weblogs.java.net/blog/2006/05/04/understanding-weak-references这让我觉得尝试利用ReferenceQueue可能是另一种方法来做到这一点。

0 投票
2 回答
6636 浏览

python - 我应该将 Py_INCREF 和 Py_DECREF 放在 Python C 扩展中的这个块的哪里?

每当我调用我的函数时,每次调用的内存使用量都会增加大约+10M,所以我认为这里有一些内存泄漏。

当我阅读文档时,有些电话像

需要像这样放置引用计数

那么,我应该将 Py_INCREF 和 Py_DECREF 放在哪里?

0 投票
5 回答
2001 浏览

delphi - 是否有像 TInterfacedObject 这样的非引用计数基类?

我需要一个类似但没有引用计数的基类TInterfacedObject(所以一种TNonRefCountedInterfacedObject)。

这实际上是我第 n 次需要这样的课程,不知何故,我总是一次又一次地编写(阅读:复制和粘贴)我自己的课程。我不敢相信没有我可以使用的“官方”基类。

RTL 实现中是否有一个基类,IInterface但没有引用计数,我可以从中派生我的类?

0 投票
2 回答
776 浏览

com - VB6 中的 AddRef()

是否可以从 Visual Basic 6 中的接口 IUnknown 调用方法 AddRef() 或实现一些技巧来增加对象引用计数器?

0 投票
1 回答
255 浏览

objective-c - 是否在(保留)正确的@property 上分配 self.string = @"" ?

某种哲学问题。将常量字符串分配给(保留的)@property 是否合适?或者,我应该这样做self.string = [NSString stringWithString:@""]

有内存泄漏吗?如果超载了怎么办?

它是一个常量字符串,那么它的行为方式是否与 NSString 对象相同?

如果属性是 (assign) 是否意味着它在运行循环后将无效?

0 投票
2 回答
2871 浏览

c++ - 设计着色器类

自从我开始学习 OpenGL 之后,我想我也应该为自己编写一个小型 C++ 框架,以避免过度使用 C-ish 代码显然导致的恶心。:)由于我打算坚持使用 Qt,因此该框架使用了一些 Qt 类。

我真正需要的第一件事是使用着色器和程序的简单方法。这是我对着色器类的想法。

不同的功能在做什么一定很明显。每个都调用相关的 OpenGL 例程,检查错误并在任何失败的情况下抛出异常。构造函数调用glCreateShader. 现在是棘手的部分。析构函数需要调用glDeleteShader(handle);,但在这种情况下我有一个难题:

选项 1:禁用分配和复制。这有避免引用计数的好处和被迫使用 shared_pointers 将它们放在向量中并在一般情况下传递的缺点。

选项 2:启用引用计数。这具有启用复制的明显优势,因此可以存储在容器中(稍后我需要将一系列着色器传递给程序)。缺点如下:

如您所见,我通过 s2 更改了 s1 的来源,因为它们共享相同的内部着色器句柄。老实说,我认为这里没有什么大问题。我写了这门课,所以我知道它的复制语义是这样的,我可以接受。问题是我不确定这种设计是否可以接受。所有这一切都可以通过 Option1 + 共享指针来实现,唯一的区别是我不想每次创建着色器时都有一个共享指针(不是出于性能原因 - 只是为了语法方便)。

Q1:请评论选项和可选的整个想法。1
Q2:如果我要选择选项 2,我是否必须自己实现它,或者在 boost 或 Qt 中有一个现成的类,我可以从中派生或拥有它的成员,并且我会获得免费的引用计数?
Q3:您是否同意创建Shader一个抽象类并拥有三个派生类VertexShader, FragmentShader, 和GeometryShader是矫枉过正?

1如果您应该向我推荐一个现有的 C++ OpenGL 框架,那很好(因为我实际上还没有找到一个),但这应该是一个旁注,而不是我的问题的答案。另请注意,我在文档的某处看到了 QGLShader 类,但它显然不存在于我的 Qt 版本中,我有理由立即避免升级。

更新

感谢您的回答。我最终决定通过删除源函数使我的着色器类不可变。着色器在创建时被编译并且没有非常量成员函数。因此,一个简单的引用计数一下子解决了我所有的问题。