- c - 在位数组中找到第一个零
- linux - Unix 显示有关匹配两种模式之一的文件的信息
- 正则表达式替换多个文件
- linux - 隐藏来自 xtrace 的命令
我在阅读一些关于 ARC 的内容时看到了这个:
@interface Address : NSObject {
@public
NSString *city;
}
@end
@implementation Address
- (Address*) init: (NSString*) c {
city = c;
return self;
}
- (void) dealloc {
NSLog(@"Destroying address: %@", city);
}
@end
@interface Customer : NSObject {
NSString *name;
Address *addr;
}
@end
@implementation Customer
- (Customer*) init: (NSString*) n withAddress: (Address*) a {
//Note 1: Automatic retain on assignment
name = n;
addr = a;
return self;
}
- (void) dealloc {
NSLog(@"Destroying: %@", name);
//Note 2: Automatic release of member variables
}
@end
Customer* objectReturnTest() {
NSString * n = [[NSString alloc] initWithString: @"Billy Bob"];
Address * a = [[Address alloc] init: @"New York City"];
Customer *c = [[Customer alloc] init: n withAddress: a];
//Note 3: ARC will put the returned object in autorelease pool.
return c;
}
A couple of basic things to note here. As "Note 1" says, when an object is assigned to a variable, a call to retain is made automatically. This increments the reference count. As "Note 2" says, when an object is destroyed, all member variable objects are released for you. You no longer have to do that from the dealloc method.
Finally, when a method returns a newly created object, ARC will put the returned object in an autorelease pool. This is stated in "Note 3".
Now, let’s use the code.
int main (int argc, const char * argv[])
{
NSString * n = [[NSString alloc] initWithString: @"Johnny Walker"];
Address * a = [[Address alloc] init: @"Miami"];
Customer *c = [[Customer alloc] init: n withAddress: a];
NSLog(@"Before force release");
c = nil; //Force a release
NSLog(@"After force release");
@autoreleasepool {
Customer *c2 = objectReturnTest();
}
NSLog(@"After autorelease pool block.");
return 0;
}
The log output from this code will be:
Before force release
Destroying: Johnny Walker
After force release
Destroying: Billy Bob
Destroying address: New York City
After autorelease pool block.
Destroying address: Miami
A couple of things to note here. See how force release works. We set a variable to nil. ARC immediately releases the reference count. This causes the Customer object "Johnny Walker" to get destroyed. But, the member Address object "Miami" doesn’t get destroyed. This object gets destroyed at the very end of the main method. This is an extremely odd and non-intuitive behavior. Technically, this is not a memory leak, but, in reality member variables can pile up and take up a lot of memory. This is just as bad as memory leak.
The object return test works as expected. Customer "Billy Bob" is put in auto release pool. At the end of the @autoreleasepool block, the pool is drained and the object is released.
看这部分;
int main (int argc, const char * argv[])
{
NSString * n = [[NSString alloc] initWithString: @"Johnny Walker"];
Address * a = [[Address alloc] init: @"Miami"];
Customer *c = [[Customer alloc] init: n withAddress: a];
NSLog(@"Before force release");
c = nil; //Force a release
NSLog(@"After force release");
@autoreleasepool {
Customer *c2 = objectReturnTest();
}
NSLog(@"After autorelease pool block.");
return 0;
}
当他做 c = nil;c a 和 n 不应该全部销毁吗?然而它说输出只是 n 被销毁了..谁能解释一下为什么?
他说结果和内存泄漏一样糟糕,那你怎么解决呢?
最后一个问题,什么时候应该使用@autoreleaasepool?
最佳答案
按行
c = nil; //Forces a release
Customer
实例被释放,因为没有人保留它,因此输出是
Destroying: Johnny Walker
但是 n
和 a
还没有被释放,因为它们仍然在范围内并且 nil
还没有分配给它们。
而且我不认为这是任何类型的内存泄漏
你通常不需要使用@autorelasepool,除非你正在做这样的事情
- (void)myMethod {
for (int i = 0; i < 1000000; i++) {
NSString *string = [NSString stringWithFormat:@"%d", i];
// do something with string
}
}
超过 1000000 NSString 将在循环期间分配。它们将在方法返回后(实际上是在此运行循环之后)被释放,但已经消耗了太多内存。因此应该替换为
- (void)myMethod {
for (int i = 0; i < 1000000; i++) {
@autoreleasepool {
NSString *string = [NSString stringWithFormat:@"%d", i];
// do something with string
}
}
}
您应该阅读本文以了解有关内存管理的更多信息 https://developer.apple.com/library/mac/#documentation/Cocoa/Conceptual/MemoryMgmt/Articles/mmAutoreleasePools.html#//apple_ref/doc/uid/20000047-CJBFBEDI
关于objective-c - Objective-C - ARC - 何时使用@autoreleasepool,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9244735/
在循环操作中将大量autoreleased 对象放入autoreleasepool 是一个很好的做法。我发现有人将@autoreleasepool 放入循环中,但其他人将循环放入@autoreleas
在 ios 中,一个主要的自动释放池围绕着 UIApplicationMain。如果我没有在应用程序内手动设置其他自动释放池,这是否意味着每当我在应用程序中使用自动释放释放对象时,它实际上不会被释放,
我目前正在构建一个通过 API 请求提取大型 JSON 文件的应用。 在下载-解码-存储数据的过程中,我收到了内存警告(超过 500MB)。我找到了一个解决方案来避免内存过载,并通过添加 @autor
我正在使用 ARC,我知道自动释放池会向其中的所有元素发送释放。考虑以下示例。 -(NSString*)someMethod{ NSString *string1=@"sample text
我在大型应用程序中遇到内存问题。我已将其简化为以下代码。如果我让应用程序运行到完成,内存就会耗尽,因此我没有真正的内存泄漏。 但是,在它运行时,每次调用 customLog: 都会累积内存并且内存不会
我在我的代码中混合了一些 ObjectiveC 和 C++。 (我的文件是 .mm 文件,而不是 .m。)什么时候才是用 @autoreleasepool 包装任何代码块的正确理由?不知道我在做什么,
我不能在 main() 中有一个“大的”NSAutoreleasePool——我不允许碰它。那么每个对象有一个池呢? struct MacGuiEngine { // members … Sc
这个问题在这里已经有了答案: How does the NSAutoreleasePool autorelease pool work? (7 个答案) 关闭 6 年前。 我看了很多关于@autor
我有一个头文件(类似 C) 我必须创建一个 Obj-c 库(或者只是几个 .m -s)来实现它。 调用该库的人将是一个 C 程序。 但是我不想手动处理内存分配,我想使用 ARC。 我可以在我的函数中使
我的问题中的术语可能错误,但这是我最好的尝试: 我的 iOS 应用程序的 ARC 启用了 autoreleasepool。因此,我不会根据自己的选择释放内存,但它似乎是在 GC 拾取器上。 我无法让
我尝试在 dispatch_async block 中使用 autoreleasepool,但它不会释放 str。当重复调用 timerEvent 时,会导致内存不足问题。 - (void)viewD
Advanced Memory Management Programming Guide关于@autoreleasepool 说: 使用本地自动释放池 block 减少峰值内存占用量 Many pro
看了GCD的文章,有个例子: dispatch_queue_t bgQueue = myQueue; dispatch_async(dispatch_get_main_queue(), ^{
在ARC下,我们不能再调用autorelease了。本质上,自动释放池的整个概念已经过时了。那么,为什么我们需要 @autoreleasepool 指令? 最佳答案 事实上,在使用 ARC 时,保留/
我正在阅读 llvm 站点上的 ARC 文档:http://clang.llvm.org/docs/AutomaticReferenceCounting.html#autoreleasepool ..
我有一个正在重构的应用程序,我刚刚实现了多线程,以便 UI 可以运行得更流畅。在 iPhone 模拟器中,我没有遇到任何泄漏,但在运行 iOS 4.2 的 iPhone 3G 上进行测试时,出现了内存
考虑这个例子: - (void)doSomething { @autoreleasepool { if (someCondition) { /* ... alloc
我正在开发一个 NSData 扩展,它使用 key 加密数据,如下所示。我对 Objective-C 不太了解,但想将它用于这个 Cordova 插件,而不是需要另一个插件来桥接 Swift 文件。
如果我将 UIApplicationMain 包装在 @autoreleasepool 中,是否意味着我永远不必考虑 Objective C 中的内存管理? 例如: @autoreleasepool
所以应用程序崩溃了,没有堆栈跟踪或任何异常,我每次都可以复制这个崩溃。我的第一个想法是它必须是双版本,在运行 zombies 10 分钟后,我无法让应用程序崩溃,一次都没有。 在查看 Allocati
我是一名优秀的程序员,十分优秀!