NSString NSCFString isMemberOfClass 遇到的相关的问题

深入理解Toll-Free Bridging 前言 Toll-Free Bridging本身不是什么新技术,那为什么还要写这篇博客呢? 原因是今天和一个同事讨论到相关问题的时候,发现理解并不够深入,于是仔细研究了下,整理成了这篇博客。 本文的Github地址:LeoMobileDeveloper Toll-Free Bridging是什么? 摘自文档: There are a number of data types i... 阅读详情

Toll Free Bridging

一.Toll-free bridging介绍

Toll-free bridging,简称为TFB,是一种允许某些ObjC类与其对应的CoreFoundation类之间可以互换使用的机制。比如 NSString与CFString是桥接(bridged)的, 这意味着可以将任意NSString当做CFString使用,也可以将任意的CFString当做NSString使用。如下:

NSString ocString = [[[NSString]] stringWithString:@"pants"];
CFIndex length = CFStringGetLength((CFStringRef)ocString);

CFStringRef cfString = CFStringCreateWithCString(NULL,"pants",kCFStringEncodingASCII);
NSUInteger length = [(NSString *)cfString length];

大部分(但不是全部)同时在Cocoa和CoreFoundation中存在的类是以这种方式桥接的,除NSString之外,还有NSArray与CFArray,NSDictionary与CFDictionary等。
TollFreeBridged中列出了可以toll-free bridged的类和non toll-free bridged的类。

二.从CoreFoundation类桥接到ObjC类

从CoreFoundation类桥接(bridge)到Objective-C类(即CFString可以当做NSString处理)的方法很简单。每个桥接类(bridged class)实际上是一个类簇(class cluster),这意味着公共类(public class)是抽象的,核心功能由私有子类(private subclasses)实现。CoreFoundation类的内存结构(memory layout)与其中一个私有子类相同,而这个子类仅仅作为CoreFoundation类的Objective-C对应类存在,其他Objective-C私有子类可能以其他方式独立存在,但因为所有私有子类都有相同的公共接口,所以从外界看来,它们看起来一样而且以相同的方式工作。

具体来说,NSString是一个抽象类,每当你创建一个NSString实例,实际上是创建的NSString的一个私有子类实例。其中一个私有子类就是NSCFString,其是CFString类的在ObjC中的对应类。CFString中的第一个元素就是isa指针,指向NSCFString类,所以其可以作为一个Objective-C对象工作。

NSCFString实现了作为NSString需要的所有方法,实现这些方法有两种方式,一种是作为桩函数(stub)实现,仅仅通过它调用CoreFoundation中的对应函数;另一种方法是实现与CoreFoundation中函数相同的方法。在实际代码中,这两种方法共同存在。

从这个方向看,桥接机制很简单,就像不存在一样。CFString只是NSCFString类的一个实例,而NSCFString是NSString的子类,实现了作为NSString的所有方法,很多的实现只是直接调用CoreFoundation的实现。

三.从ObjC类桥接到CoreFoundation类

这个方向的桥接就会很复杂,这是因为一个TFB Objective-C类的实例可能是其任意一个子类的实例,还可能是应用程序自定义的子类,但这些可能为任意子类的实例需要在CoreFoundation函数中透明使用,即你可以在任意一个NSString实例(很可能不是NSCFString)上使用CFStringGetLength获得字符串的长度。实际上如果这是NSString实例恰好是NSCFString,则直接调用CoreFoundation的函数,如果不是则直接向其发送-length消息,以Objective-C的方式处理。
这是怎么实现的呢,现在来看下CFStringGetLength函数的实现

	CFIndex CFStringGetLength(CFStringRef str) {
	    CF_OBJC_FUNCDISPATCH0(__kCFStringTypeID, CFIndex, str, "length");
	    __CFAssertIsString(str);
	    return __CFStrLength(str);
	}

第一行的CF_OBJC_FUNCDISPATCH0宏可以处理Objective-C对象,其实现如下:

	// Invoke an ObjC method, return the result
	#define CF_OBJC_FUNCDISPATCH0(typeID, rettype, obj, sel) \
		if (__builtin_expect(CF_IS_OBJC(typeID, obj), 0)) \
		{rettype (*func)(const void *, SEL) = (void *)__CFSendObjCMsg; \
		static SEL s = NULL; if (!s) s = sel_registerName(sel); \
		return func((const void *)obj, s);}

首先看第一行if (__builtin_expect(CF_IS_OBJC(typeID, obj), 0)),__builtin_expect()只是gcc的分支预测标识,表示我们希望CF_IS_OBJC(typeID, obj)返回false。而CF_IS_OBJC做了什么呢?

CF_INLINE int CF_IS_OBJC(CFTypeID typeID, const void *obj) {
	    return (((CFRuntimeBase *)obj)->_isa != __CFISAForTypeID(typeID) && ((CFRuntimeBase *)obj)->_isa > (void *)0xFFF);
	}

这部分代码检查obj是否为Objective-C对象,首先检查其isa指针是否指向了特定的CF类型,如果不是则检查isa指针是否大于0xFFF,如果大于,则说明此对象为Objective-C对象。
而如何根据typeID(__kCFStringTypeID)找到其对应的类(NSCFString)呢,来看__CFISAForTypeID的实现。

extern struct objc_class *__CFRuntimeObjCClassTable[];
CF_INLINE void *__CFISAForTypeID(CFTypeID typeID) {
    return (void *)(__CFRuntimeObjCClassTable[typeID]);
}

__CFISAForTypeID只是以typeID为索引在__CFRuntimeObjCClassTable中查找。__CFRuntimeObjCClassTable是一个CFType与ObjC类的匹配表,在CoreFoundation初始化时,所有桥接类在此表中赋值,而其他项赋值为哑值(NSCFType)。所以以__kCFStringTypeID为索引在此表中可找到NSCFString。如果对象的isa不是指向NSCFString,则说明其不是CFString。

如果经CF_IS_OBJC判断对象不是CF类型,则其为其他Objective-C对象,这时会走Objecitive-C的消息机制,通过__CFSendObjCMsg函数向对象发送-length消息,__CFSendObjCMsg实际上是objc_msgSend_rtp()。

简单来将,处理TFB类的每个CoreFoundation函数首先检查传递的对象是否真正的CoreFoundation类型(特定的CoreFoundation类型,如CFStringGetLength则需要对象是CFString,而不能是其它CoreFoundation对象),如果是纯Objective-C类型,则简单的调用Objective-C类的消息处理。如果是CoreFoundation类型,则以CoreFoundation通常的方式处理。

这种实现有个有趣的后果,如果我们对一个CFArray使用CFStringGetLength函数会有什么效果呢?isa检查为检测到CFArray不是一个真正的CFString,所以会走向Objective-C分支,最终我们得到一个错误

 -[NSCFArray length]: unrecognized selector sent to instance 0x100108e50

以上的代码是CF-368.27中的,在最近的CF-635中实现有变化,不过原理相同。CF635中的CF_IS_OBJC实现

#define __CFRuntimeClassTableSize 1024

extern uintptr_t __CFRuntimeObjCClassTable[];
CF_INLINE uintptr_t __CFISAForTypeID(CFTypeID typeID) {
    return (typeID < __CFRuntimeClassTableSize) ? __CFRuntimeObjCClassTable[typeID] : 0;
}

CF_INLINE Boolean CF_IS_OBJC(CFTypeID typeID, const void *obj) {
    if (CF_IS_TAGGED_OBJ(obj)) return true;
    uintptr_t cfisa = ((CFRuntimeBase *)obj)->_cfisa;
    if (cfisa == 0) return false;
#if 0
    // Temporarily disabled
#if __LP64__
    if (cfisa < 0x10000000UL) {
        CFLog(kCFLogLevelWarning, CFSTR("*** Warning: CF tested pointer %p for objectness and found its isa pointer to be bogus (%p)"), obj, cfisa);
        return false;
    }
#else
    if (cfisa < 0x1000UL) {
        CFLog(kCFLogLevelWarning, CFSTR("*** Warning: CF tested pointer %p for objectness and found its isa pointer to be bogus (%p)"), obj, cfisa);
        return false;
    }
#endif
#endif
    if (cfisa == (uintptr_t)__CFConstantStringClassReferencePtr) return false;
    uintptr_t type_isa = (uintptr_t)(typeID < __CFRuntimeClassTableSize ? __CFRuntimeObjCClassTable[typeID] : 0);
    if (cfisa == type_isa) return false;
    return true;
}

四.基本行为的桥接

以上描述的是显式的桥接的工作方式,对于TFB还有更有趣的一方面,所有对象都共享的基本行为实际上是对所有类桥接的,实质上NSObject可以桥接到CFType。一个最普遍的例子,可以对任意Objective-C对象使用CFRetain,也可以对任意CoreFoundation对象使用retain方法,与其他桥接相同,如果你在Objective-C代码中重写了retain方法,则CFRetain会调用你重写的retain方法。这种桥接行为不仅适合于内存管理方法,对任意的CFType函数(如CFCopyDescription),任意的NSObject方法(如performSelector:withObject:afterDelay:)都适用。

CoreFoundation对象桥接到ObjC对象时,因为任何CoreFoundation对象的首字段(isa)都指向一个ObjC类,对于桥接类isa指向其在ObjC中的对应类,对于非桥接类isa指向一个特殊的__NSCFType(__CFRuntimeObjCClassTable表中的默认值),所有这些类都是NSObject的子类,所以它们继承了NSObject类的所有行为。对于映射到对应CoreFoundation类的方法,则是直接调用CoreFoundation侧的实现。

当ObjC类桥接到CoreFoundation时,和上面描述的机制相同,CFRetain以及其他CFType函数首先检查此对象是否真正的CoreFundation对象(应该是仅检测是否CoreFundation对象,而不是桥接类中检测是否特定的CoreFundation对象)或者是其他Objecitive-C类。如果是CF对象,则调用CoreFoundation的实现,如果不是,则使用消息模式让Objective-C侧处理。

五.ARC与Toll-free bridging

ARC只能管理Objective-C类型,对于Objective-C对象我们不用手动进行retain/release/autorelease的操作,ARC会自动为我们完成。但对于CoreFoundation对象则仍然需要我们手动管理。因为存在所有权(ownership)不明确的问题,所以ARC禁止Objecitive-C对象指针与其它指针类型进行标准cast转换,对CoreFoundation对象指针也是如此。下面一行代码,则手动内存管理时是很典型的转换,但在ARC下却不能编译。

id obj = (id)CFDictionaryGetValue(cfDict, key);

为了使其在ARC环境下可编译,需要使用特殊的casting标注告诉ARC关于所有权(ownership)的语义。这些标注为__bridge,__bridge_transfer和__bridge_retained。
最简单的是__bridge,这是没有所有权影响的直接转换。ARC接收此值,像通常那样处理。

id obj = (__bridge id)CFDictionaryGetValue(cfDict, key);

另外两个casting标注分别向ARC系统转移所有权和从ARC系统获取所有权,在以下情况下使用。以下面代码为例

    NSString *value = (NSString *)CFPreferencesCopyAppValue(CFSTR("someKey"), CFSTR("com.company.someapp"));
    [self useValue: value];
    [value release];

在使用ARC时,如果使用__bridge,则代码需修改为

    NSString *value = (__bridge NSString *)CFPreferencesCopyAppValue(CFSTR("someKey"), CFSTR("com.company.someapp"));
    [self useValue: value];

CFPreferencesCopyAppValue操作需要一个与之匹配的release操作,在初始化value时,ARC系统使用了retain,当value不再使用时,ARC系统会自动对value release,以与之前的retain操作配对。但并没有与CFPreferencesCopyAppValue操作配对的release,所以此对象泄漏。
__bridge_transfer可以用来解决这个问题,__bridge_transfer在将指针值传递给ARC时,同时传递了所有权(transfers ownership)。当__bridge_transfer用来标注cast时,它告诉此对象已经被retain过了,不需要再次retain。既然ARC获取到了所有权,那么它仍然会在使用完毕后release。代码如下:

NSString *value = (__bridge_transfer NSString *)CFPreferencesCopyAppValue(CFSTR("someKey"), CFSTR("com.company.someapp"));
    [self useValue: value];

Toll-free bridging可以在两个方向进行,当从ObjC对象向CoreFundation桥接时代码如下:

   CFStringRef value = (__bridge CFStringRef)[self someString];
    UseCFStringValue(value);

这种情况下,ARC不会管理value的声明周期,所以在赋值操作完成之后,UseCFStringValue使用value之前,此对象就会被立即释放,这样在UseCFStringValue使用该对象时就会因访问已释放的对象而crash。通过使用__bridge_retained可以让ARC将所有权转出,既然ARC已将所有权转出,所以其不会再释放此对象,这时UseCFStringValue就可以安全使用了,使用完毕后由CoreFundation负责释放,如下

    CFStringRef value = (__bridge_retained CFStringRef)[self someString];
    UseCFStringValue(value);
    CFRelease(value);

这些cast标注不仅可用于toll-free bridging,当需要将Objecitve-C对象指针不当做ObjC对象存储时都可以使用,可以使用此方式将ObjC对象指针与void *或其他指针任意转换。如下:

    NSDictionary *contextDict = [NSDictionary dictionary...];
    [NSApp beginSheet: sheetWindow
       modalForWindow: mainWindow
        modalDelegate: self
       didEndSelector: @selector(sheetDidEnd:returnCode:contextInfo:)
          contextInfo: (__bridge_retained void *)contextDict];

    - (void)sheetDidEnd: (NSWindow *)sheet returnCode: (NSInteger)code contextInfo: (void *)contextInfo
    {
        NSDictionary *contextDict = (__bridge_transfer NSDictionary *)contextInfo;
        if(code == NSRunStoppedResponse)
            ...
    }

总结如下:

  • __bridge仅仅在ARC和non-ARC之间转移指针,并不转移所有权。
  • __bridge_transfer将一个non-Objective-C指针移动到Objective-C指针,并转移所有权,这样ARC会代替你release它.
  • __bridge_retained将一个Objective-C指针指针移动到一个non-Objective-C指针,同样转移所有权,这样ARC将不会release它,编程者负责后续使用CFRelease或其他函数释放。

六.创建桥接类

不是所有的CoreFoundation类是可以桥接的,从上述讨论的TFB的实现方式可见,做到双向桥接需要CoreFoundation类的每个函数都要首先判断该对象是否真正的CF对象,若不是CF对象,则以Objective-C对象处理。因为CoreFoundation类由苹果控制,所以若其本身未实现此功能,我们没有办法手动添加,所以不能创建双向桥接的TFB类。
但由于任何CoreFoundation的首字段都是isa,我们可以把其当做objective-C对象处理,所以单向的桥接时可以实现的。我们可以在Objective-C侧创建新的类以匹配CoreFoundation中的类。在HowToCreateTollFreeBridgedClass中讨论了如何创建新的TollFreeBridged类,在http://code.google.com/p/corefoundation-bridging中收集了开发者创建的TollFreeBridged类。

参考:
Friday Q&A 2010-01-22: Toll Free Bridging Internals
Friday Q&A 2011-09-30: Automatic Reference Counting
Bridge
HowToCreateTollFreeBridgedClass
TollFreeBridging
TollFreeBridged
corefoundation-bridging
Cocoa Core Competencies - Class cluster
Core Foundation Design Concepts - Toll-Free Bridged Types
CFType Reference
CF-368.27 CFInternal.h
CF-635 CFInternal.h
CF-368.27 CFString.c

本文出自 清风徐来,水波不兴 的博客,转载时请注明出处及相应链接。

本文永久链接: http://www.winddisk.com/2012/08/16/toll-free-bridging/

Rockchip MPP解码H264实战:从文件到YUV的完整流程解析 本文详细解析了在Rockchip平台上使用MPP(Media Process Platform)硬件解码H264视频文件并输出YUV数据的完整流程。通过实战代码示例,深入讲解了MPP解码器的初始化、数据包投递、非阻塞模式下的双循环控制以及YUV帧的提取与保存等核心步骤,并提供了环境搭建、编译运行和常见问题排查指南,帮助开发者高效利用硬件加速进行视频处理。 阅读详情

相关推荐

解锁Jetbrains AI助手:中国开发者实战配置与效率跃迁指南

本文为中国开发者提供了一份详细的Jetbrains AI助手实战配置指南。针对服务地域限制,核心解决方案是通过修改Jetbrains账户区域信息并配置网络代理,实现插件的稳定启用。文章进一步分享了AI助手在解读遗留代码、生成中文提交信息、智能问答等场景下的具体应用,旨在帮助开发者深度集成这一工具,实现编码生产力的显著提升。

weixin_28832121的博客 572

【OC】NSString的三种实现方式

通过阶段性的学习,我们iOS小组进行了组内考核,在主观题回答时,对于NSString的三种实现方式,我没有弄明白,所以有了这篇学习笔记。

2301_80467753的博客 1309

计算机组成原理 微程序控制器实验

微程序控制器实验 实验环境 计算机组成原理实验环境 实验目的 掌握微程序控制器的组成原理和工作过程。 理解微指令和微程序的概念,理解微指令与指令的区别与联系。 掌握指令操作码与控制存储器中微程序的对应方法。熟悉根据指令操作码从控制存储器中读出微程序的过程。 实验要求 做好实验预习,读懂实验电路图,熟悉实验元器件的功能特性和使用方法。 按照实验内容与步骤的要求,独立思考,认真仔细地完成实验。 写出实验报告。 实验电路        

Long_UP的博客 7万+

CFStringRef相关的CFSTR与和NSString相关的@

CoreFoundation里面的CFStringRef和NSString*是可以直接转换的,两种也都有一个相似的用来直接赋常量的操作。 例如: CFStringRef a = CFSTR("a"); NSString *b = @"b"; CFSTR是一个宏,这个宏的定义可能是CFStringMakeConstantString,也可能__builtin___CFString...

gtts 428

高斯-约当(Gauss-Jordan)消元法——c++代码实现

具体算法的详细原理请参照此篇博客:高斯-约当(Gauss-Jordan)消元法下面是具体c++代码,不保证程序最优化,提供一个可行的程序,供大家改进,同时感谢大家提意见。——大神勿喷呀,我是一个小菜鸟~void Guss_Jordan(int n,double *a)//阶数n 系数矩阵a { double*a_temp = new double[n*n * 2];//a与单位矩阵的组合

zwz的学习之路 6873

Python Opencv cv2提取图像中某种特定颜色区域(例如黑字白纸背景下的红色公章提取),并将纯色背景透明化

拜拜PHOTOSHOP- 领导突然让我帮他把公章从图片中抠出来,在确保了不是要做坏事的情况下,我打开了PHOTOSHOP,用魔棒工具一点一点抠,但由于魔棒工具的原理是对比临近区域像素差值,导致封闭字体中的区域无法剔除,而且一点一点抠非常麻烦,愤而PYTHON,使用CV2完美解决。 效果如下(马赛克是我添加的): 任务就是把蓝色的公章抠出来。 效果如上。 代码如下: import cv2 import numpy as np src = cv2.imread(r"imagepath")#这里填你的原图像路

qq_43670549的博客 1万+

NSString NSCFString区别

NSString是 NSCFString的父类 在于NSString是个class cluster,一个类簇。什么是一个类簇?简单的来说,NSString是个“工厂类”,然后它在外层提供了很多方法接口,但是这些方法的实现是由具体 的内部类来实现的。当使用NSString生成一个对象时,初始化方法会判断哪个“自己内部的类”最适合生成这个对象,然后这个“工厂”就会生成这个具体 的类对象返回给你。这...

weixin_30629653的博客 524

ARM Cortex-M系列授权解析:从研发到量产的免费与付费之路

本文深入解析了ARM Cortex-M系列内核从研发到量产过程中的授权模式。研发阶段可利用ARM DesignStart等免费资源进行原型验证,但产品商业化量产则需支付授权费与版税。文章对比了采购商用MCU与自研芯片的成本差异,并探讨了RISC-V作为免费替代方案在IoT领域的应用前景与挑战,为开发者提供了清晰的选型指南。

weixin_29292431的博客 494

objc’s category and class cluster 详解

objective-c有一个feature,可以给已有的类添加方法,而无需改变类名。传统的语言可能需要通过继承或者组合实现,但是obj-c只需要用这个feature就好,这就是category。 Category: 举个例子,NSString是一个常用的类,NSString是原生支持unicode,比如NSString* str = @”感谢国家”; 要获得string的len

jjj706的专栏 1189

爱快路由(ikuai)多WAN口配置实战:提升网络带宽与稳定性

本文详细解析了爱快路由(ikuai)多WAN口配置的实战技巧,包括双线智能分流、毫秒级故障切换和带宽叠加利用等核心功能。通过七种配置方案和智能QoS策略,帮助企业提升网络带宽与稳定性,实现99.9%以上的高可用性。

weixin_30566063的博客 700

Horn-Schunck光流算法的Python实现

光流是计算机视觉领域中的一个重要概念,它描述了图像中物体在时间上的运动。Horn-Schunck光流算法是一种经典的光流估计方法,通过对图像的亮度变化进行建模,来估计像素的运动速度。在本文中,我们将使用Python实现Horn-Schunck光流算法,并提供相应的源代码。请注意,该算法假设图像上的亮度变化主要由物体的运动引起,并且假设光流在整个图像上是稠密的。在上面的示例中,我们首先读取了两个输入图像,然后使用我们实现的Horn-Schunck光流算法估计了它们之间的光流。首先,我们需要导入一些必要的库。

持续更新 495

NSString NSCFString NSCFConstantString isMemberOfClass 遇到的相关的问题

一.Toll-free bridging介绍 Toll-free bridging,简称为TFB,是一种允许某些ObjC类与其对应的CoreFoundation类之间可以互换使用的机制。比如 NSString与CFString是桥接(bridged)的, 这意味着可以将任意NSString当做CFString使用,也可以将任意的CFString当做NSString使用。如下: NSStri

iOS学堂 1706

数字IC/FPGA 秋招知识点不全面整理

数字IC/FPGA 秋招知识点不全面整理

w0shishabi的博客 7866

NSCFDictionary

[NSCFDictionary setObject:forKey:] mutating method send to immutating object 修改方法: NSMutableDictionary *dict = [[NSUserDefaults standardUserDefaults] objectForKey:@"dict"]; 為: NSMutableDictionary

1299

C# WinForm 基于DirectShow.dll编写的程序,可边预览边保存视频,音频和图片

基于微软的DirectShow.dll的二次开发1.自动识别连接的摄像头跟麦克风且可以对其进行选择(默认选中第一个)2.可录制wmv和avi两种格式的视频并且都带有音频,avi可以录制的分辨率和帧数进行选择,wmv默认进行了淸晰度优化如不喜欢可去除代码中有相关提示3.可在预览点开之后进行拍照,也可边录制视频边拍照4.添加了视频和音频的压缩功能(酌情使用)这次二次开发发现C#对DirectShow的相关信息太少,这次做完也不敢藏私共享出来,还望大家指正

精雕软件(JDpaint) 5.5 绿色版

精雕软件(JDpaint) 5.5 绿色版精雕软件(JDpaint) 5.5 绿色版精雕软件(JDpaint) 5.5 绿色版

iOS 中 copy 的原理

Python实战社群Java实战社群长按识别下方二维码,按需求添加扫码关注添加客服进Python社群▲扫码关注添加客服进Java社群▲作者丨伯阳来源丨知识小集(zsxjtip)前几天在群...

iOS_开发 816

SAP B1中文培訓教材_SDK

公司内部培训资料,对开发工具 ,DIAPI, UIAPI,Add-ON有详细解说

ios什么时Toll_free_bridge

什么是 Toll-Free Bridging 有一些数据类型是能够在 Core Foundation Framework 和 Foundation Framework 之间交换使用的。这意味着,对于同一个数据类型,你既可以将其作为参数传入 Core Foundation 函数,也可以将其作为接收者对其发送 Objective-C 消息(即调用ObjC类方法)。这种在 Core Foundatio...

weixin_33698823的博客 254

visio安装包

Microsoft Office Visio 是一款专业的制图软件。利用经过更新的形状、协作工具和数据链接图表,创建专业级图表以简化复杂的信息。

问题人生[20160330] -[NSCFString containsString:]: unrecognized selector sent to instance 0x7f9902724da0

进行字符串搜索比对时用到的方法 containsString,在iOS7中运行时发生崩溃 -[NSCFString containsString:]: unrecognized selector sent to instance 0x7f9902724da0 查询API文档可知containsString的定义如下 - (BOOL)containsString:(NSString *)s

雅香小筑 3611

Objective-C中的BOOL/bool/Boolean/NSCFBoolean区别

原文点这儿 Objective-C用BOOL来编码真值。它是signed char的typedef,并且用宏YES和NO来相应的表示真和假。 布尔值用于条件判断,比如if和while语句,来进行有条件的逻辑或者重复运行。当判断一个条件语句,数值0为“假”,而其他任何数值为“真”。因为NULL和nil被定义为0,所以对于这些不存在的数值的条件语句也被判定为“假”。 在Objecti

Le_Wrynn的博客 8208

iOS里Toll-Free Bridging的桥接机制

为什么80%的码农都做不了架构师?>>> ...

weixin_34250709的博客 241

什么是Toll-free bridging

Core Foundation 框架 Core Foundation框架 (CoreFoundation.framework) 是一组C语言接口,它们为iOS应用程序提供基本数据管理和服务功能。下面列举该框架支持进行管理的数据以及可提供的服务: 群体数据类型 (数组、集合等) 程序包 字符串管理 日期和时间管理 原始数据块管理 偏好管理 URL及数据

两万马力的专栏 3534

iOS-深入理解NSString的三种存储类型

在 Objective-C 的 Fondation 框架中 NSString 对象是很复杂的存在,各种方式创建以及不同长度的字符串都会影响 NSString 对象在内存中所处的位置。Objective-C 在运行时也对其做了很多优化。今天就来研究一下 NSString 这个复杂的对象。 打印结果 对于这个类型的NSString,我们测试打印他的retainCount 类型和地址 创建两个内容一样的 __NSCFString 他们的地址是不一样的 引用计数 查阅资料 和 __NSCFCo

weixin_61639290的博客 1281

NSTaggedPointerString,__NSCFConstantString,__NSCFString和NSString的关系?NSString为什么用copy?

​​​​问题引入: NSString都存储在堆区吗?会不会存在栈区,或者数据区呢? NSString用copy修饰还是strong修饰?NSString调用copy和mutableCopy会创建一个新的内存空间吗?NSMutableString用copy修饰会导致什么样的后果? 一.各类型字符串的关系和存储方式 NSString和NSMutableString相信我们平时都用过n遍了,但N...

qq_31186665的博客 4086

NSString的内存管理之 __NSCFConstantString、NSTaggedPointerString、__NSCFString

&gt; 转自:http://skyfly.xyz/2015/11/08/iOS/NSString%E7%9A%84%E5%86%85%E5%AD%98%E7%AE%A1%E7%90%86/  by skyfly   在 Objective-C 的 Fondation 框架中 NSString 对象是很复杂的存在,各种方式创建以及不同长度的字符串都会影响 NSString 对象在内存中所处的...

王学森的专栏 6886

NSCFString与NSString类型的字符串导致的崩溃问题

今天在做项目时,遇到一个奇怪的问题: NSString *account = [Tool getUserName];  // [Tool getUserName]得到的值为@“liuyao" NSString *account = @"liuyao"; 通过第一种方式创建的account在JSONKit中会导致程序崩溃。于是开始寻找原因,后来发现,两种

mygrilzhuyulin的专栏 6021

iOS 崩溃问题[__NSCFConstantString objectForKey:]: unrecognized selector sent to instance 0x10b15a470

1.服务器返回的数据类型 {     responseMessage =     {         accountid = “”;         data = “”;         errorCode = 0000;         msg = success;         “msg_help” = “”;         “msg_oth

huanghaiyan_123的专栏 6158

iOS开发——常用的四种内存管理

一、block内存管理 1.block内存类型 block内存分为三种类型: _NSConcreteGlobalBlock(全局) _NSConcreteStackBlock(栈) _NSConcreteMallocBlock(堆) 2.三种类型的内存的创建时机 1)对于_NSConcreteStackBlock和_NSConcreteGlobalBlock类型 _NSConcreteStackBlock和_NSConcreteGlobalBlock这两种类型的block,我们可以手动创建,如下所示:

syh96123的博客 323
上一篇: 自定义软键盘上的Return键的文本
下一篇: 关于NSString和NSMutableString的retainCount
trandy
博客等级 码龄17年 79粉丝 20原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值