NSUserDefaults setObject崩溃

时间:2017-12-01 04:06:15

标签: ios objective-c nsuserdefaults sigsegv

我有一个单例类,在它的init方法中,我设置了一个NSMutableArray,稍后当我保存它时,应用程序随机崩溃了这个崩溃日志,我确信recordUploadCnt不能为零,但无法找出哪里出了问题。

  NSString* const KEY_SENSOR_UPLOAD = @"recordUploadCnt";
  @property(nonatomic, strong) NSMutableArray* recordUploadCnt;

- (id)init {
    if (self = [super init]) {
         NSMutableArray* cnt = [[NSUserDefaults standardUserDefaults] objectForKey:KEY_SENSOR_UPLOAD];
         self.recordUploadCnt = cnt ? [NSMutableArray arrayWithArray:cnt] :  [NSMutableArray new];
    }
    return self;
}

double currentTime = [[NSDate date] timeIntervalSince1970];
if ([self.recordUploadCnt count] < 6) {
    [self.recordUploadCnt addObject:[NSString stringWithFormat:@"%f",currentTime]];
} else {
    [self.recordUploadCnt removeObjectAtIndex:0];
    [self.recordUploadCnt addObject:[NSString stringWithFormat:@"%f",currentTime]];
}
[[NSUserDefaults standardUserDefaults] setObject:self.recordUploadCnt forKey:KEY_SENSOR_UPLOAD];
[[NSUserDefaults standardUserDefaults] synchronize];

Exception Type:  SIGSEGV
Exception Codes: SEGV_MAPERR at 0xebfecbeb8
Crashed Thread:  37
Thread 37 Crashed:
0   libobjc.A.dylib                 0x0000000184980430 _objc_msgSend :16 (in libobjc.A.dylib)
1   CoreFoundation                  0x00000001856bf4c8 __CFPropertyListIsValidAux :52 (in CoreFoundation)
2   CoreFoundation                  0x00000001856c02a4 __CFPropertyListIsArrayPlistAux :40 (in CoreFoundation)
3   CoreFoundation                  0x00000001855e3900 _CFArrayApplyFunction :80 (in CoreFoundation)
4   CoreFoundation                  0x00000001856bf5fc __CFPropertyListIsValidAux :360 (in CoreFoundation)
5   CoreFoundation                  0x00000001855fc414 _CFPropertyListWrite :96 (in CoreFoundation)
6   CoreFoundation                  0x00000001855fbc14 _CFPropertyListCreateData :316 (in CoreFoundation)
7   CoreFoundation                  0x0000000185778f28 _CFPrefsEncodeKeyValuePairIntoMessage :504 (in CoreFoundation)
8   CoreFoundation                  0x0000000185689f94 -[CFPrefsPlistSource sendMessageSettingValue:forKey:] :136 (in CoreFoundation)
9   CoreFoundation                  0x00000001856886ec -[CFPrefsPlistSource alreadylocked_setValues:forKeys:count:from:] :440 (in CoreFoundation)
10  CoreFoundation                  0x0000000185756034 -[CFPrefsSource setValues:forKeys:count:removeValuesForKeys:count:from:] :220 (in CoreFoundation)
11  CoreFoundation                  0x00000001856b9150 -[CFPrefsSearchListSource alreadylocked_setValues:forKeys:count:from:] :584 (in CoreFoundation)
12  CoreFoundation                  0x0000000185756034 -[CFPrefsSource setValues:forKeys:count:removeValuesForKeys:count:from:] :220 (in CoreFoundation)
13  CoreFoundation                  0x00000001857563f4 -[CFPrefsSource setValue:forKey:from:] :64 (in CoreFoundation)
14  CoreFoundation                  0x00000001856bbfa4 __108-[_CFXPreferences(SearchListAdditions) withSearchListForIdentifier:container:cloudConfigurationURL:perform:]_block_invoke :260 (in CoreFoundation)
15  CoreFoundation                  0x00000001856bb7c8 _normalizeQuintuplet :356 (in CoreFoundation)
16  CoreFoundation                  0x00000001856bbe94 -[_CFXPreferences(SearchListAdditions) withSearchListForIdentifier:container:cloudConfigurationURL:perform:] :108 (in CoreFoundation)
17  CoreFoundation                  0x000000018576008c -[_CFXPreferences setValue:forKey:appIdentifier:container:configurationURL:] :92 (in CoreFoundation)
18  CoreFoundation                  0x000000018576370c _CFPreferencesSetAppValueWithContainer :128 (in CoreFoundation)
19  Foundation                      0x000000018601bf80 -[NSUserDefaults(NSUserDefaults) setObject:forKey:] :68 (in Foundation)

2 个答案:

答案 0 :(得分:1)

您将对象转换为数据&amp;尝试保存,你不能将可变对象直接保存到NSUserDefaults

NSData *data = [NSKeyedArchiver archivedDataWithRootObject:self.recordUploadCnt];

[[NSUserDefaults standardUserDefaults] setObject:data forKey: KEY_SENSOR_UPLOAD];

[[NSUserDefaults standardUserDefaults] synchronize];

答案 1 :(得分:0)

参考Apple文档:UserDefaults - Storing Default Objects

  

默认对象必须是属性列表 - 即NSData,NSString,NSNumber,NSDate,NSArray或NSDictionary的实例(或集合,实例的组合)。如果要存储任何其他类型的对象,通常应将其存档以创建NSData实例。

您可能需要将其转换为NSData(试试看看)

NSData *arrayData = [NSKeyedArchiver archivedDataWithRootObject: self.recordUploadCnt];
[[NSUserDefaults standardUserDefaults] setObject:arrayData forKey: KEY_SENSOR_UPLOAD];

在将数组值添加到NSUserDefaults之前确切地检查数组值。

我试过以下,它对我有用:

#import "ViewController.h"

@interface ViewController () {

}

@property(nonatomic, strong) NSMutableArray* recordUploadCnt;
@end

NSString* const KEY_SENSOR_UPLOAD = @"recordUploadCnt";

@implementation ViewController

- (void)viewDidLoad {
    [super viewDidLoad];
    [self testArrayWithUserDefaults];
}

-(void)testArrayWithUserDefaults {

    double currentTime = [[NSDate date] timeIntervalSince1970];
    [self.recordUploadCnt addObject:[NSString stringWithFormat:@"%f",currentTime]];
    [[NSUserDefaults standardUserDefaults] setObject:self.recordUploadCnt forKey:KEY_SENSOR_UPLOAD];
    [[NSUserDefaults standardUserDefaults] synchronize];

    NSMutableArray* userDefaultsArray = (NSMutableArray *)[[NSUserDefaults standardUserDefaults] objectForKey:KEY_SENSOR_UPLOAD];
    NSLog(@"Array = %@", [NSString stringWithFormat:@"%f",currentTime]);
}
  

<强>结果:   数组= 1512136898.293169

以下是工作副本的快照:

enter image description here