标签: objective-c-runtime

具有未知数量参数的resolveInstanceMethod

语境:

我有一个依赖注入容器 - www.typhoonframework.org

它允许使用接口定义组件以在运行时解析它们 - 使用resolveInstanceMethod和implementntationWithBlock将请求拖拽到DI容器.

用户一直在要求在运行时提供一些参数.例如:

[assembly dangerousEnemyWithWeapon:id<BigGun>]
Run Code Online (Sandbox Code Playgroud)

..敌人是由DI容器中的合作类组装而成,但枪是在运行时提供的...

问题:

是否可以使用resolveInstanceMethod来定义预先知道参数数量的实现?

我想打包这些论点,并将它们转发给另一个响应者.

参数可以按顺序打包或添加到字典中,匹配的选择器部分作为键.

objective-c objective-c-runtime

3
推荐指数
1
解决办法
816
查看次数

iOS/Objective-C元类和类别

我理解一个类实际上是struct的object/typedef(objc_class*).每个类都有一个"支持"元类,它又有一个指向元类的isa指针NSObject.

并且NSObject基本上有一个isa指针指向自身.

我们可以通过这一行获得元类:

objc_getMetaClass("<CLASS_NAME>");
Run Code Online (Sandbox Code Playgroud)

我希望到目前为止我对meta class的理解并不在这里(请纠正我,如果是的话).

我的问题是:

1.)

我们什么时候需要处理元类?您能否在我们需要的时候引用代码中的示例/场景?

2.)

背景:

我正在思考第三方库以及它们的结构.

通常它们为您提供一个类方法并返回一个类,所有其他方法都是私有/"隐藏".而且大多数时候,虽然它们可以被子类化,但由于我们不知道该init方法,因此子类化是没有用的.

突然间我开始考虑Objective-C类别,从而引导我思考Objective-C元类.

这导致我的问题#2:

是否可以通过使用Objective-C类和/或使用元类来破解这种结构(通过抓住它并在元类中直接插入类方法)?或者甚至查找私有实例方法的名称?

我的意图不是"打破"任何东西,我只是非常好奇这些第三方图书馆是如何"牢不可破"的,如果它们的结构不能通过使用类别元类来"打破" .

@Leo Natan:

1.)

什么是method_*()

2.)

对于Objective-C Runtime热爱:

您能否举一个示例实现 - 调整实例方法,比方说,

(我不确定这种方法是否是一个很好的例子,因为我们可以首先覆盖它)

NSArray-count实例方法(让它使它返回总是计数100,例如)

3.)

所以理论上所有类(包括所有第三方库)都可以中断(破坏)?换句话说,没有办法创建一个"只调用此类方法 - 或者你不能使用我"的API /库

非常感谢.

metaclass objective-c objective-c-runtime ios objective-c-category

3
推荐指数
1
解决办法
1071
查看次数

块和消息

这里的问题更多的是教育问题.我在一小时前开始想到这一点,同时翻转一个乐高积木(傻,我知道).

根据我的理解,块是在堆栈上创建的对象.

让我们说A是一个对象,这意味着我们可以做到:

[A message];
Run Code Online (Sandbox Code Playgroud)

基于此,如果块是一个对象,我们也可以这样做:

[block message];
Run Code Online (Sandbox Code Playgroud)

我对么?

当运行时看到它时,它会调用:

objc_msgSend(block, @selector(message), nil);
Run Code Online (Sandbox Code Playgroud)

所以我的问题是,我们如何发送一个消息块?

如果这是可能的,我会想象也可以发送一个块参数为块的消息?

并且,如果我们可以通过执行以下操作来调用块:

block();
Run Code Online (Sandbox Code Playgroud)

这是否意味着我们甚至可以将一个块作为message(SEL),因为块具有void (^)(void)类似于方法的签名?

因为如果有可能,那么下面的内容会让我感到惊讶:

objc_msgSend(block, @selector(block), block);
Run Code Online (Sandbox Code Playgroud)

要么:

objc_msgSend(block1, @selector(block2), block3);
Run Code Online (Sandbox Code Playgroud)

我希望我的想象力不会有点疯狂,我的理解不在这里(如果是的话,请纠正我).

macos objective-c objective-c-runtime ios objective-c-blocks

3
推荐指数
1
解决办法
471
查看次数

如何从协议方法描述列表中解密“ objc_method_description”?

我有一些Swift 3代码来解码iOS Objective-C协议(有一个Swift对应版本)。在总结完Swift 3反射后,我发现反射还不够完善,无法满足我的需要,我偶然发现了objc运行时方法protocol_copyMethodDescriptionList(),该方法返回以下C结构的数组:

struct objc_method_description
     SEL name;
     char *types;
};
Run Code Online (Sandbox Code Playgroud)

该代码获取协议选择器名称的列表,但不确定在该type字段中返回什么。我对如何正确解码objc_method_description.type值感到困惑。

什么我得到在该type领域是一个神秘的格式,例如,"B48@0:8@16{_NSRange=QQ}24@40"起初我还以为是在我是如何转换C字符串的一个问题,但一些研究之后,我怀疑它实际上参数的编码,类似Java的JVM如何传递方法签名。但是我仍然没有参考来解码它。

import UIKit

class ViewController: UIViewController, UITextViewDelegate {

    @IBOutlet weak var noteView : UITextView!

    func decodeProto() {
        var methodCount : UInt32 = 1
        if let methodList = protocol_copyMethodDescriptionList(UITextViewDelegate.self,
                  false, true,  UnsafeMutablePointer<UInt32>(&methodCount)) {
            for i in 0..<Int(methodCount) {
                let methodDesc = methodList[i];
                let name = methodDesc.name
                let types = String(validatingUTF8: methodDesc.types)
                print("\(name) \(types)")
            }
        }
    }

    override …
Run Code Online (Sandbox Code Playgroud)

objective-c objective-c-runtime swift

3
推荐指数
1
解决办法
467
查看次数

Objective-c运行时是指比直接c/c ++程序更多的层吗?

我已经读过,objective-c程序需要objective-c运行时才能运行.

AFAIK,两个C/C++程序都不需要运行任何运行时环境.因为生成的二进制代码正由底层OS直接执行.

那么这意味着Objective-c程序需要一个冗余层来运行,正确吗?如果是这样,这个层看起来像Java VM和.net运行时还是看起来像Qt运行时(在一些额外的库中)?

EDIT: 一些读出后,我发现,在objc编译器生成在生成的编译代码一些更多的信息,其负责的许多东西,如方法通过(objc_sendMsg(),introspection及其他)

谢谢.

runtime objective-c objective-c-runtime

2
推荐指数
1
解决办法
491
查看次数

了解Objective-C中选择器的唯一性

我正在理解"选择器"功能的一部分,如Apple指南中所述.我把那些让我感到困惑的部分加粗了:

在Objective-C中,selector有两个含义.它可以用于简单地引用方法的名称,当它在对象的源代码消息中使用时.但是,它也指的是在编译源代码时替换名称的唯一标识符.编译选择器的类型为SEL.具有相同名称的所有方法都具有相同的选择器.您可以使用选择器来调用对象上的方法 - 这为在Cocoa中实现目标操作设计模式提供了基础.

方法和选择器为了提高效率,完整的ASCII名称不用作编译代码中的方法选择器.相反,编译器将每个方法名称写入表中,然后将名称与表示运行时方法的唯一标识符配对.运行时系统确保每个标识符都是唯一的:没有两个选择器是相同的,并且所有具有相同名称的方法都具有相同的选择器.

任何人都能解释这些位吗?另外,如果不同的类具有相同名称的方法,它们是否也具有相同的选择器?

objective-c objective-c-runtime selector

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

使用运行时将弱ivar添加到Objective-C类

是否可以在使用运行时创建的类中添加归零弱引用(在ARC意义上,而不是GC中)实例变量?如果是这样的话?

有一个函数调用class_setWeakIvarLayout()似乎与此相关,但遗憾的是文档(对于此函数和非弱对应函数)都非常薄.

weak-references objective-c objective-c-runtime automatic-ref-counting

2
推荐指数
1
解决办法
1470
查看次数

object_setClass()的性能而不是指定isa指针

我注意到了对XCode(4.6)的最新更新,我收到了关于几行的警告JSONKit.m.特别是,设置对象类的行:

dictionary->isa = _JKDictionaryClass;
Run Code Online (Sandbox Code Playgroud)

这些标记为已弃用,并注明首选方法是使用object_setClass():

object_setClass(dictionary, _JKDictionaryClass);
Run Code Online (Sandbox Code Playgroud)

当我问为什么最好只是让警告静音时,回答是:

即使新的Xcode版本抱怨,一切都运行正常,我不想:
1)测试每个项目我使用JSONKit来检查在object_setClass()后是否一切正常
2)松散的cpu周期,这就是我使用JSONKit的原因以NSJSONSerialization为例.我当前的应用程序解析权重为600K-1M的json文件

我们在这里讨论了多少性能影响?

注意:

我更感兴趣

dictionary->isa = _JKDictionaryClass VS object_setClass()

JSONKitVS NSJSONSerialization.

objective-c objective-c-runtime ios jsonkit

2
推荐指数
1
解决办法
1396
查看次数

Objective-C注册类Runtime Reference

所以我上课了MyClass.它的名字是其中的一部分char * myclasses[].我想使用objc运行时api来分配它.
1)这是最好的方法吗?我的目标是不分配10或15个ViewControllers,直到它们实际需要使用,并且还没有巨大的switch语句来创建它们.

Class aClass = NSClassFromString ( [NSString stringWithUTF8String:myclasses[1]] );
id myClass = class_createInstance(aClass, 0);
Run Code Online (Sandbox Code Playgroud)

我正在努力理解注册课程..

2)因为我不是在运行时创建一个新类(只是分配),所以我不应该注册它,对吗?
3)班级注册通常如何运作?(随意指点我某处的文件).

class objective-c objective-c-runtime

2
推荐指数
1
解决办法
1123
查看次数

GCD对象作为Objective-C对象

当使用Objective-C编译器编译时,Grand Central Dispatch对象的行为类似于Objective-C对象.但这对我来说有点不清楚.

事实上,Objective-C对象是至少有一个字段的结构:指向isa对象类结构的指针(指针).其他字段(如果有)对应于对象的ivars.

那么,可以将GCD对象转换为第一个字段是指向Objective-C类结构的指针的结构吗?由于调度对象参与ARC,什么是编译器的更多信息:它发送retainrelease邮件的对象(如objc_msgSend(obj, @selector(retain)),例如)或它生成dispatch_object_retaindispatch_object_release电话?我的意思是,GCD对象是否以[obj mesg]时尚方式响应ObjC消息?

objective-c objective-c-runtime grand-central-dispatch

2
推荐指数
1
解决办法
296
查看次数