从 NSDictionary 设置时 BOOL 值从 NO 变为 Yes

BOOL value changing from NO to Yes when setting up from NSDictionary

我有这个代码

if ([args valueForKey:@"showSetupScreen"]) {
    BOOL showSetupScreen = [args valueForKey:@"showSetupScreen"];
    NSLog(showSetupScreen ? @"YES" : @"NO");
    //  meetingConfig.showSetupScreen = showSetupScreen;
}

其中 argsNSMutableDictionary

args 在我的字典中的值是 NO 但是当我设置为 BOOL showSetupScreen = [args valueForKey:@"showSetupScreen"]; 它变成 YES

谁能帮我理解为什么会这样。

附上截图供您参考

A NSDictionary(或NSMutableDictionary)不能直接包含原始C类型,例如BOOLNSDictionary 中的原始数字类型(包括布尔值)包装在 NSNumber 对象中。参见 Numbers Are Represented by Instances of the NSNumber Class and Most Collections Are Objects

因此,使用NSNumber方法boolValueNSNumber中提取布尔值,例如

BOOL showSetupScreen = [[args valueForKey:@"showSetupScreen"] boolValue];

或者,更简单地说:

BOOL showSetupScreen = [args[@"showSetupScreen"] boolValue];

例如,原始 C 类型的示例,包括 BOOLNSIntegerdouble

NSDictionary *args = @{
    @"foo": @NO,
    @"bar": @YES,
    @"baz": @42,
    @"qux": @3.14
};

BOOL foo = [args[@"foo"] boolValue];         // NO/false
BOOL bar = [args[@"bar"] boolValue];         // YES/true
NSInteger baz = [args[@"baz"] integerValue]; // 42
double qux = [args[@"qux"] doubleValue];     // 3.14

值得一提的是,如果您展开 args 中包含的值,将会显示这些值的内部类型,并且您会看到与 showSetupScreen 关联的值(或 foo 在我的示例中),不是 BOOL,而是指向 __NSCFBoolean/NSNumber:

的指针

[args valueForKey:@"showSetupScreen"]语句returns指针(内存中的地址)它有两个选项:一些地址(非零值)和NULL(零)。对于 C 编程语言,true 是任何非零值(在我们的例子中是内存中的任何地址)。因此,您在 if 运算符和 showSetupScreen 变量中得到 true 。但它只告诉你字典中有指定键的某个对象,但没有这个键的值(包装在这个对象中的值)。要获得此值(在我们的示例中为 BOOL),您必须调用 boolValue.