object_getIvar无法读取BOOL iVar的值

Sre*_*ree 0 iphone objective-c-runtime

object_getIvar(id对象,Ivar ivar)正确读取iVArs的值,但在BOOL类型iVar上失败并崩溃.我需要一个类的所有iVars的值.有什么方法可以解决它.

Jim*_*yes 22

可以使用ARC 直接访问ivars .您可以访问基本C类型(char,short,int等)和Objective-C对象.例如,unsigned char可以使用以下模式访问ivar.用其他基本类型替换类型名称会产生该类型的ivar的访问器.

unsigned char val;

val = ((unsigned char (*)(id, Ivar))object_getIvar)(object, ivar);

NSLog(@"Looks like I got: %u (or character %c)", val, val);
Run Code Online (Sandbox Code Playgroud)

在幕后,你正在使用一些恶作剧来伪造编译器,认为这 object_getIvar()实际上是一个返回你所追求的类型的函数.这种类型转换改变了编译器调用和解释结果的方式object_getIvar,并且是必需的,因为基本的C类型可以是8到64位大,并且只有编译器知道它们在用作返回值时如何处理,由您正在编译的体系结构使用的ABI定义.

是的,它看起来很有趣,但它是最便携的方式,而且,它只是有效.:-)使用直线型无法使用,ARC也不允许这样做.

如果ivar是从NSObject派生的对象,则可以直接使用返回值,或者将其强制转换为您期望的对象而不会出现问题,ARC或无ARC.


Olo*_*f_t 5

答案有点老了。使用ARC和结构(或者为了安全起见,在访问任何非对象iVar时),您应该这样做:

ptrdiff_t offset = ivar_getOffset(ivar);
unsigned char *stuffBytes = (unsigned char *)(__bridge void *)object;
CGRect gilligans = * ((CGRect *)(stuffBytes + offset));
Run Code Online (Sandbox Code Playgroud)

至少这是让它为我工作的唯一方法。

摘自此页面:http : //www.bignerdranch.com/blog/inside-the-bracket-part-5-runtime-api/