对于64位版本的iOS,我们不能再使用%d%u来格式化NSIntegerNSUInteger.因为对于64位,它们的类型定义为longunsigned long,而不是intunsigned int.

因此,如果您试图用%d格式化NSInteger,Xcode将抛出警告.Xcode对我们很好,并为这两种情况提供了一个替代品,它由一个带l前缀的格式说明符和一个长类型转换组成.然后我们的代码基本上如下所示:

NSLog(@"%ld", (long)i);
NSLog(@"%lu", (unsigned long)u);

如果你问我的话,这是一种眼睛疼痛.

几天前,Twitter上有人提到了在32位和64位平台上格式化有符号变量的格式说明符%zd和格式化无符号变量的格式说明符%tu.

NSLog(@"%zd", i);
NSLog(@"%tu", u);

这似乎有效.我更喜欢打字和打字.

但我真的不知道为什么会这样.现在对我来说,这两个基本上都是神奇的价值观.

我做了一些研究,发现z前缀意味着下面的格式说明符的大小与size_t相同.但我完全不知道前缀t是什么意思.所以我有两个问题:

%zd%tu到底是什么意思?

%zd%tu代替苹果的建议打字到long是否安全?


I am aware of similar questions and Apples 64-Bit Transition guides, which all recommend the 100 approach. I am asking for an alternative to type casting.

推荐答案

http://pubs.opengroup.org/onlinepubs/009695399/functions/printf.html开始:

  • z
  • t

http://en.wikipedia.org/wiki/Size_t#Size_and_pointer_difference_types开始:

  • size_t用于表示特定实现中任何对象(包括数组)的大小.它用作sizeof运算符的返回类型.
  • ptrdiff_t表示指针之间的差异.

在当前的OS X和iOS平台上

typedef __SIZE_TYPE__ size_t;
typedef __PTRDIFF_TYPE__ ptrdiff_t;

其中__SIZE_TYPE____PTRDIFF_TYPE__

#define __SIZE_TYPE__ long unsigned int
#define __PTRDIFF_TYPE__ int

对于64位,编译器定义

#define __SIZE_TYPE__ long unsigned int
#define __PTRDIFF_TYPE__ long int

(这可能在Xcode版本之间发生了变化.@user102008的

所以ptrdiff_tNSInteger都是same type的类型定义:

NSLog(@"%td", i);
NSLog(@"%tu", u);

正确工作,编译时在所有当前

size_tNSUInteger在所有平台上的大小都相同,但是

NSLog(@"%zu", u);

实际上在编译32位时会给出警告.

但这种关系在任何标准中都是不固定的(据我所知),因此我会

我所知道的类型转换的唯一替代方法是使用预处理器宏来回答"Foundation types when compiling for arm64 and 32-bit architecture":

// In your prefix header or something
#if __LP64__
#define NSI "ld"
#define NSU "lu"
#else
#define NSI "d"
#define NSU "u"
#endif

NSLog(@"i=%"NSI, i);
NSLog(@"u=%"NSU, u);

Objective-c相关问答推荐

我在哪里可以找到 info.plist 文件?

使用自动布局自定义纵横比

iOS 7 / Xcode 5:以编程方式访问设备启动图像

使用 ARC,什么更好:alloc 或 autorelease 初始化程序?

单元测试私有方法 - 目标 C

如果安装了应用程序,如何以编程方式判断?

setStatusBarHidden 在 iOS 9.0 中已弃用

静态 NSString 使用与内联 NSString 常量

判断一个 NSDate 是否大于另一个

无法加载从笔尖引用的图像

当服务器上的图像文件更改时,我的应用程序中的 SDWebImage 缓存图像会发生什么情况?

如何编写 OS X Finder 插件

如何在iphone的objective-c中以编程方式调整图像大小

Objective-C 中的 alloc、init 和 new

带有 NSBlockOperation 和队列的 NSURLSession

在 UITextField 文本上投影

何时在 iPhone 上使用 UIView 与 UIViewController?

如何在 UITextField 上自动打开键盘?

UICollectionView 断言失败

无法在 iOS7 上将 UITextField 添加到 UIAlertView ...在 iOS 6 中有效