标签: objective-c-runtime

在dealloc中使用self.property = nil有什么问题吗?

我知道声明属性生成存取方法,这只是语法糖.

我发现self.property = nil他们的dealloc方法中有很多人使用它.

1)在Apple的内存管理文档中,p23它说:

您不应该使用访问器方法来设置实例变量的唯一地方是init方法和dealloc.

为什么不呢?

2)在Apple的Objective-C 2.0,p74中

声明的属性从根本上取代了访问器方法声明; 在合成属性时,编译器仅创建任何缺少的访问器方法.没有与dealloc 方法直接交互  - 不会自动为您释放属性.但是,声明的属性提供了一种交叉检查dealloc 方法实现的有用  方法:您可以在头文件中查找所有属性声明,并确保未标记的对象属性assign 被释放,并且标记的  对象属性不会  assign 被释放.

注意:通常在dealloc方法中,您应该release直接对象实例变量(而不是调用set访问器并nil作为参数传递),如下例所示:

- (void)dealloc { [property release]; [super dealloc]; }
Run Code Online (Sandbox Code Playgroud)

但是,如果使用现代运行时并合成实例变量,则无法直接访问实例变量,因此必须调用访问器方法:

- (void)dealloc { [self setProperty:nil]; [super dealloc]; }
Run Code Online (Sandbox Code Playgroud)

这个音符是什么意思?

我找到了[property release];并且[self setProperty:nil];都工作了.

null properties objective-c objective-c-runtime dealloc

9
推荐指数
1
解决办法
4037
查看次数

Objective-C相关对象在ARC下泄漏

objc_setAssociatedObject在ARC下遇到了一个奇怪的行为.请考虑以下代码:

static char ASSOC_KEY;

@interface DeallocTester : NSObject
@end

@implementation DeallocTester
- (void) dealloc
{
    NSLog(@"DeallocTester deallocated");
    //objc_setAssociatedObject(self, &ASSOC_KEY, nil, OBJC_ASSOCIATION_RETAIN);
}
@end

@implementation AppDelegate
- (void) applicationDidFinishLaunching:(UIApplication *)application
{
    NSObject *test = [[DeallocTester alloc] init];
    objc_setAssociatedObject(test, &ASSOC_KEY, [[DeallocTester alloc] init],
                             OBJC_ASSOCIATION_RETAIN);
}
Run Code Online (Sandbox Code Playgroud)

我正在创建一个实例DeallocTester,然后我将另一个设置DeallocTester为关联对象,然后它们都超出了范围.

我希望-dealloc第一个对象被调用,然后关联的对象也要被释放,但我看到"DeallocTester deallocated"消息只打印一次.如果我取消注释该objc_setAssociatedObject-dealloc,则第二个对象也会被取消分配.

Objective-C引用声明关联对象在对象销毁时自动解除分配.它是编译器/ ARC /任何问题还是我错过了什么?

更新

如果您从一个全新的项目运行它,这个示例代码实际上是有效的.但我有两个启用ARC的项目.我会做一些调查并提供更好的样本.

更新2

我填写了一个rdar:// 10636309,如果在启用ARC的项目中启用了NSZombie对象,则相关对象泄漏

objective-c objective-c-runtime automatic-ref-counting

9
推荐指数
1
解决办法
4792
查看次数

C作为校长级或; 没有ObjC的可可应用程序

对于那些质疑我的理智/浪费时间/能力/动机的人来说,这件事是"基础与勺子"项目的一个端口,现在因为是一个全C的iOS应用程序而臭名昭着.

所以,我有交流文件铆足了劲去,要在主类的全部-C的MAC-应用的背后,但是,限制因素是阻止正在启动的应用程序的组合.就目前而言,该项目只是一个main.m和一个名为AppDelegate.c的类,所以我输入了"AppDelegate"作为info.plist中主要类的名称,令我完全惊讶的是,打印的日志:

无法找到类:AppDelegate,退出

这将iOS中很好地工作,因为主函数接受委托类的名称,并自动处理它,但NSApplicationMain()函数没有这样的说法.

现在,我知道这源于@interface/@implementationC 中没有指令的事实,而这正是操作系统似乎正在寻找的,所以我编写了一个简单的NSApplication子类并将其作为主要类提供给plist,它完美地启动了好.我的问题是,怎样才能将ac文件设置为mac应用程序中的主要类并使其正确启动?

编辑:解决了!该文件可能是.m(框架错误,由于某种原因),但类对的分配足以滑倒.您可以在此处下载基于C的Mac App的源代码.快乐挖!

代码已被编写,签名,密封和盖章,但我需要的只是解决plist中NSPrincipalClass要求的方法.

c macos cocoa objective-c objective-c-runtime

9
推荐指数
2
解决办法
1561
查看次数

如何创建一个"包裹"目标/选择器对的块?

我喜欢积木,而且非常酷.

但是,我发现块可能会混乱我的代码并使其更难阅读而不将所有这些代码都放在Xcode中(我不喜欢这样做).

我喜欢将我的代码拆分为逻辑方法(选择器)以使其更易于阅读,但是(表面上)看起来这对于诸如dispatch,AFNetworking和其他几个框架来说是不可能的.

我也不关心委托方法,因为这意味着我不能按照我的意愿来命名我的方法,而是依赖于其他人认为我需要的方法.

所以,没有像这样编写一堆粘合代码:

-(void) reloadData { 
    ...
    [[EventsManager instance] data:YES async:^(NSArray *events) { [self processEvents:events] }];
    ...
}
Run Code Online (Sandbox Code Playgroud)

我可以做这样的事情:

-(void) reloadData {
    ...
    [[EventsManager instance] data:YES async:createBlock(self, @selector(processEvents:))];
    ...
}
Run Code Online (Sandbox Code Playgroud)

哪个更容易阅读(对我来说).

凭借Objective-c的功能和运行时,这应该是可能的,不是吗?不过,我还没有见过这样的东西.

objective-c objective-c-runtime selector objective-c-blocks

9
推荐指数
2
解决办法
617
查看次数

在isa中存储东西

64位运行时消除了直接访问对象的isa字段的能力,这是CLANG工程师一直警告我们的事情.它们被一组相当具有创造性(且神奇)的ABI规则所取代,这些规则关于新命名的isa标题的哪些部分包含有关该对象的信息,甚至包含其他状态(在NSNumber/NSString的情况下).似乎存在一个漏洞,因为你可以选择退出新的"魔法"isa并使用你自己的一个(原始的isa),代价是通过某些运行时代码路径走慢路.

我的问题是双重的,然后:

如果可以选择退出并将object_setClass()任意类放入对象中+allocWithZone:,是否也可以在类的额外空间中放置任何内容,或者运行时是否会尝试通过快速路径读取它?

isa标题中究竟是什么标记为让运行时将它与正常的isa区分开来?

objective-c objective-c-runtime

9
推荐指数
2
解决办法
428
查看次数

为什么objc运行时函数`class_addMethod()`在目标类为'NSObject`时将实现添加为实例和类方法?

当我使用objc运行时函数class_addMethod()向NSObject的实例选择器注入一个实现时,它实际上将实现注入实例选择器类选择器:

@implementation HelloWorldClass
- (void) helloWorld{
    NSLog(@"hello world from instance method -helloWorld");
}
@end

// ====
// Do method injection when the application did finish launching.
Class sourceClass = objc_getClass("HelloWorldClass");
Class targetClass = objc_getClass("NSObject");
SEL helloWorldSelector = @selector(helloWorld);

Method method = class_getInstanceMethod(sourceClass, helloWorldSelector);
IMP imp = method_getImplementation(method);
const char *methodTypeEncoding = method_getTypeEncoding(method);

class_addMethod(targetClass, helloWorldSelector, imp, methodTypeEncoding);
Run Code Online (Sandbox Code Playgroud)

现在我们只声明helloWorldvia Objc Category 的接口,并将helloWorld消息调用到NSObject实例和类:

// Declare the interface for `helloWorld
@interface NSObject (HelloWorld)
+ …
Run Code Online (Sandbox Code Playgroud)

objective-c objective-c-runtime

9
推荐指数
1
解决办法
2565
查看次数

部署到OS X 10.6并且在使用旧运行时的平台上不支持"-fobj-arc"

背景:

我正在为OS X构建一个应用程序,部署目标为10.6.我没有完全将我的应用程序转换为ARC,但是我添加了一些可以从ARC中受益的新类,所以我-fobj-arc为这些类设置了编译器标志.

通用32/64位英特尔架构的编译失败,使用旧版运行时的平台不支持错误-fobj-arc.

仅64位构建成功.

我不熟悉低级架构.我的问题是:仅为64位Intel构建的影响是什么?这会阻止应用程序完全在10.6上运行吗?或者只有一些机器运行10.6?

compilation cpu-architecture computer-architecture objective-c-runtime automatic-ref-counting

9
推荐指数
1
解决办法
8292
查看次数

有没有办法列出iOS应用程序中的所有混合方法?

我基本上正在寻找一种方法来检测何时/什么第三方库调配.我最近遇到了一个广告库使用了AFNetworking的古怪分叉的情况.AFNetworking对NSURLSessionTask进行了调整,在某些情况下,这两个混合体并没有很好地发挥作用.我真的希望能够检测和理智检查这种事情,理想情况下甚至在应用程序中保留每个混合方法的版本化转储,这样我们就可以了解谁在修补什么以及风险是什么.谷歌和堆栈溢出搜索只发布了一堆关于如何调整的教程.有人遇到过这个问题或有解决方案吗?看起来我可能能够使用objc/runtime.h编写代码,但我无法想象我是第一个需要它的人.

objective-c objective-c-runtime ios method-swizzling

9
推荐指数
1
解决办法
1256
查看次数

什么是`objc_msgSend_fixup`,究竟是什么?

我正在搞乱Objective-C运行时,尝试编译Objective-c代码而不将其链接起来libobjc,并且我对程序有一些分段错误问题,所以我从中生成了一个汇编文件.我认为没有必要显示整个程序集文件.在我的main功能的某些方面,我有以下一行(顺便说一句,这是我得到seg错误之后的行):

callq   *l_objc_msgSend_fixup_alloc
Run Code Online (Sandbox Code Playgroud)

这是以下定义l_objc_msgSend_fixup_alloc:

.hidden l_objc_msgSend_fixup_alloc # @"\01l_objc_msgSend_fixup_alloc"
    .type   l_objc_msgSend_fixup_alloc,@object
    .section    "__DATA, __objc_msgrefs, coalesced","aw",@progbits
    .weak   l_objc_msgSend_fixup_alloc
    .align  16
l_objc_msgSend_fixup_alloc:
    .quad   objc_msgSend_fixup
    .quad   L_OBJC_METH_VAR_NAME_
    .size   l_objc_msgSend_fixup_alloc, 16
Run Code Online (Sandbox Code Playgroud)

我重新实现objc_msgSend_fixup了一个函数(id objc_msgSend_fixup(id self, SEL op, ...))返回nil(只是为了看看会发生什么),但是这个函数甚至没有被调用(程序在调用之前崩溃).

所以,我的问题是,callq *l_objc_msgSend_fixup_alloc应该做什么以及objc_msgSend_fixup(之后l_objc_msgSend_fixup_alloc:)应该是什么(一个函数或一个对象)?

编辑

为了更好地解释,我没有将我的源文件与objc库链接.我想要做的是实现libray的一些部分,只是为了看它是如何工作的.这是我所做的一种方法:

#include <stdio.h>
#include <objc/runtime.h>

@interface MyClass {

}
+(id) alloc;
@end

@implementation MyClass
+(id) alloc {
  // alloc the object
  return nil;
}
@end

id objc_msgSend_fixup(id …
Run Code Online (Sandbox Code Playgroud)

assembly objective-c objective-c-runtime segmentation-fault

8
推荐指数
2
解决办法
999
查看次数

方法不能标记为@objc,因为其结果类型无法在Objective-C中表示

我在Objective-C和Objective-C运行时暴露了swift API.

当我在函数抛出错误之前添加"@objc"时"无法将方法标记为@objc,因为其结果类型无法在Objective-C中表示"

我的代码在这里

@objc public static func logIn(_ userId: String) -> User? { }
Run Code Online (Sandbox Code Playgroud)

用户是可选的结构.怎么解决这个问题.

objective-c optional-parameters objective-c-runtime ios swift

8
推荐指数
2
解决办法
9250
查看次数