在Objective-C开发中从iOS迁移到Mac时,NSIntegers会给出类型匹配错误

Bre*_*aut 6 types objective-c type-conversion ios

我一直在研究iOS项目已有一段时间了,我最近决定将代码移植到Mac项目中.因为我选择在我的代码中使用NSInteger,而NSInteger是一个依赖于环境的类型转换,这意味着我的变量在iOS和Mac应用程序中是不同的类型.

当我在Mac上运行测试套件时,我的所有STAssertEquals调用都会失败并显示错误"Type mismatch - ",因为类型不匹配:

NSInteger foo = 1;
STAssertEquals(foo, 1, nil); // Test fails!!
Run Code Online (Sandbox Code Playgroud)

类似我的标量似乎工作,但这似乎非常混乱:

NSInteger foo = 1;
STAssertEquals(foo, (NSInteger)1, nil); // Succeeds, but is ugly!!
Run Code Online (Sandbox Code Playgroud)

我在这里错过了什么吗?我开始怀疑使用NSIntegers的决定是一个糟糕的选择.

更新:也许这篇文章是相关的.它似乎支持类型转换标量.

icc*_*cir 5

您对NSInteger的使用可能是正确的选择,但它确实会导致STAssertEquals出现一些问题.

如果两个对象具有不同的Objective-C类型编码,则STAssertEquals会失败

孤独1将由C编译器为(符号int),其中有类型的编码"I"来解释.

这些宏也会失败:

unsigned u = 1;
STAssertEquals(u, 1, nil); // Fails because u is type "I" (unsigned int) and 1 is type "i" (int)

char c = 1;
STAssertEquals(c, 1, nil); // Fails because c is type "c" (signed char) and 1 is type "i" (signed int)
Run Code Online (Sandbox Code Playgroud)

要使编译器使用不同的类型1,您可以1U为(unsigned int),1UL(unsigned long)或1L(long)添加后缀,例如for(unsigned int ).

NSInteger定义为与指针大小相同,这取决于设备体系结构.在32位Mac OS X和iOS上,NSInteger是type(signed int)或"i".在64位Mac OS X上,它是long类型或"q".(64位Mac OS X是LP64架构,这意味着L ongs和P ointers都是64位宽)

因此,STAssertEquals的左侧是"q",而右侧是"i",导致类型不匹配.

您使用的解决方案(NSInteger) 1似乎准确地表示您想要的内容 - 针对值为1的NSInteger常量测试NSInteger变量.