我很困惑我必须使用“seenArray”的方式
#define kseenArray @"seenArray"
和NSString * const kseenArray = @"seenArray";
为什么?。关于记忆,如果有的话,我想知道哪一个更好。
答案 0 :(得分:2)
就内存而言,我认为它不会有太大的区别,因为编译器不会复制字符串文字,并且会对同一个对象进行所有引用。
但我认为这是最好的:
NSString * const kseenArray = @"seenArray";
因为它允许你比较基于对象的地址的文字,而不是它的内容(使用[NSString isEqualToString]
),这更快:
- (void)someMethod:(NSString *)someString
{
if (someString == kseenArray)
{
...
}
}
答案 1 :(得分:1)
由于我对大会没有足够的了解得出结论,我已经写了测试并提供了结果,我会让你得出自己的结论
我写了这个小测试:
#import <Foundation/Foundation.h>
NSString * const aString = @"String";
//#define aString @"String"
int main()
{
NSLog(@"%@", aString);
return 0;
}
使用以下行编译:
gcc StringTest.m -g -m64 -framework Cocoa
第一个程序集使用#define
0x0000000100000ee0 <main+0>: push %rbp
0x0000000100000ee1 <main+1>: mov %rsp,%rbp
0x0000000100000ee4 <main+4>: sub $0x10,%rsp
0x0000000100000ee8 <main+8>: lea 0x191(%rip),%rax # 0x100001080
0x0000000100000eef <main+15>: lea 0x16a(%rip),%rcx # 0x100001060
0x0000000100000ef6 <main+22>: xor %dl,%dl
0x0000000100000ef8 <main+24>: mov %rax,%rdi
0x0000000100000efb <main+27>: mov %rcx,%rsi
0x0000000100000efe <main+30>: mov %dl,%al
0x0000000100000f00 <main+32>: callq 0x100000f22 <dyld_stub_NSLog>
0x0000000100000f05 <main+37>: movl $0x0,-0x8(%rbp)
0x0000000100000f0c <main+44>: mov -0x8(%rbp),%eax
0x0000000100000f0f <main+47>: mov %eax,-0x4(%rbp)
0x0000000100000f12 <main+50>: mov -0x4(%rbp),%eax
0x0000000100000f15 <main+53>: add $0x10,%rsp
0x0000000100000f19 <main+57>: pop %rbp
0x0000000100000f1a <main+58>: retq
此程序集使用NSString * const
0x0000000100000ee0 <main+0>: push %rbp
0x0000000100000ee1 <main+1>: mov %rsp,%rbp
0x0000000100000ee4 <main+4>: sub $0x10,%rsp
0x0000000100000ee8 <main+8>: mov 0x171(%rip),%rax # 0x100001060 <aString>
0x0000000100000eef <main+15>: lea 0x192(%rip),%rcx # 0x100001088
0x0000000100000ef6 <main+22>: xor %dl,%dl
0x0000000100000ef8 <main+24>: mov %rcx,%rdi
0x0000000100000efb <main+27>: mov %rax,%rsi
0x0000000100000efe <main+30>: mov %dl,%al
0x0000000100000f00 <main+32>: callq 0x100000f22 <dyld_stub_NSLog>
0x0000000100000f05 <main+37>: movl $0x0,-0x8(%rbp)
0x0000000100000f0c <main+44>: mov -0x8(%rbp),%eax
0x0000000100000f0f <main+47>: mov %eax,-0x4(%rbp)
0x0000000100000f12 <main+50>: mov -0x4(%rbp),%eax
0x0000000100000f15 <main+53>: add $0x10,%rsp
0x0000000100000f19 <main+57>: pop %rbp
0x0000000100000f1a <main+58>: retq
答案 2 :(得分:0)
const string更好。
宏保持盲目复制。因此,当您使用宏时,它实际上会创建字符串对象。
但是,输入const只会引用全局字符串。
答案 3 :(得分:0)
宏编译在编译时发生。因此,如果您在代码中使用宏1000x,则与编码相同字符串文字的1000个副本相同
使用const变量,如果你引用它1000次,你仍然引用相同的变量。