繁体   English   中英

尝试将阵列数据保存/加载到Plist

[英]Trying to Save/Load Array Data to Plist

我一直在逐步学习Objective C和iPhone SDK,而我目前的项目涉及构建一个存储数字数据(体育数据)的应用程序。 这主要是出于学习目的,因为有多个应用程序执行相同的操作。 无论如何,我遇到了一些障碍。 我的意图是在表中存储一个玩家列表,并允许用户添加其他玩家。

目前,我有一个按钮,当按下该按钮时,“忍者”将添加到表格中。 我还启用了表格中的删除功能。 不幸的是,我似乎无法弄清楚如何从plist中保存和加载数据。 我遵循了各种教程和指南,但是我无法弄清楚发生了什么。 我的怀疑是我正在从一个空数组中加载数据并添加到该数组中,但是涉及数据的数组是与plist分离的数组。 不幸的是,我对此感到迷茫。

每当我切换视图时,阵列中的数据都会被擦除。 但是,我注意到,如果我离开然后再回来,数据仍然保留,但是如果我离开很长一段时间,离开并重新启动iphone等,数据就不会保留。即使对于我尚未使用过的应用,这似乎也会发生保存。 这是否只是iPhone保留数据的功能,以防用户意外退出程序?

希望我能切实地解释我的问题。 TL:DR版本:我想将数据添加到数组,将其保存到plist,并在屏幕上出现数组时从plist重新加载数据。 下面的代码正在尝试完成此操作,但未成功。

谢谢

#import "RootViewController.h"
#import "NewPlayer.h"
#import "OptionsMenu.h"

@implementation RootViewController
@synthesize createdPlayers;
@synthesize listOfPlayers;

-(NSString *) pathOfFile{
    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES); 
        NSString *documentFolder = [paths objectAtIndex:0];
    return [documentFolder stringByAppendingFormat:@"myfile.plist"];

}


-(void)applicationWillTerminate:(NSNotification*)notification{
    NSMutableArray *array = [[NSMutableArray alloc]init];
    [array writeToFile: [self pathOfFile] atomically:YES];
}


- (void)viewDidLoad
{

    NSString *filePath = [self pathOfFile];
    if ([[NSFileManager defaultManager]fileExistsAtPath:filePath]) {
        NSArray *array = [[NSArray alloc]initWithContentsOfFile:filePath];
        listOfPlayers.array = [array objectAtIndex:0];
        [array release];

    }

    UIApplication *app = [UIApplication sharedApplication];
    [[NSNotificationCenter defaultCenter]addObserver:self selector:@selector(applicationWillTerminate:) name:UIApplicationWillTerminateNotification object:app];

    [super viewDidLoad];
    listOfPlayers = [[NSMutableArray alloc] init];

}


-(IBAction)AddButtonAction:(id)sender{
    [listOfPlayers addObject:@"Ninjas"];
    [createdPlayers reloadData];
}

-(IBAction)switchView:(id)sender{

    OptionsMenu *second = [[OptionsMenu alloc] initWithNibName:nil bundle:nil];
    [self presentModalViewController:second animated:YES];
}

-(IBAction)newView:(id)sender{
    NewPlayer *second = [[NewPlayer alloc] initWithNibName:nil bundle:nil];
    [self presentModalViewController:second animated: YES];
}

- (void)viewWillAppear:(BOOL)animated
{
    [super viewWillAppear:animated];
}

- (void)viewDidAppear:(BOOL)animated
{
    [super viewDidAppear:animated];
}

- (void)viewWillDisappear:(BOOL)animated
{

    [super viewWillDisappear:animated];
}

- (void)viewDidDisappear:(BOOL)animated
{
    [super viewDidDisappear:animated];
}

- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
    return 1;
}

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
    return [listOfPlayers count];
}

// Customize the appearance of table view cells.
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    static NSString *CellIdentifier = @"Cell";

    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
    if (cell == nil) {
        cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier] autorelease];
    }

    // Configure the cell.
    cell.textLabel.font = [UIFont fontWithName:@"Helvetica" size:15];

    cell.textLabel.textColor = [UIColor whiteColor];
    cell.textLabel.textAlignment = UITextAlignmentCenter;

    NSString *cellValue = [listOfPlayers objectAtIndex:indexPath.row];
    cell.textLabel.text = cellValue;

    return cell;
}

- (BOOL)tableView:(UITableView *)tableView canEditRowAtIndexPath:(NSIndexPath *)indexPath
{
    return YES;
}

// Override to support editing the table view.
- (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath
{
    if (editingStyle == UITableViewCellEditingStyleDelete) {

        NSLog(@"delete section: %d rol: %d", [indexPath indexAtPosition:0], [indexPath indexAtPosition:1]);
        [listOfPlayers removeObjectAtIndex:[indexPath indexAtPosition:1]];
        [tableView deleteRowsAtIndexPaths:[NSArray arrayWithObject:indexPath] withRowAnimation:UITableViewRowAnimationFade];
    }

    else if (editingStyle == UITableViewCellEditingStyleInsert)
    {
        // Create a new instance of the appropriate class, insert it into the array, and add a new row to the table view.
    }   
}


-(void)tableView:(UITableView *)listOfPlayers moveRowAtIndexPath:(NSIndexPath *)fromIndexPath toIndexPath:(NSIndexPath *)toIndexPath{
}

-(void)didReceiveMemoryWarning
{
    // Releases the view if it doesn't have a superview.
    [super didReceiveMemoryWarning];

    // Relinquish ownership any cached data, images, etc that aren't in use.
}

- (void)viewDidUnload
{
    [super viewDidUnload];

    // Relinquish ownership of anything that can be recreated in viewDidLoad or on demand.
    // For example: self.myOutlet = nil;
}



- (void)dealloc{
    [createdPlayers release];
    [listOfPlayers release];
    [super dealloc];
}

@end


#import <UIKit/UIKit.h>

@interface RootViewController : UIViewController <UITableViewDelegate, UITableViewDataSource> {

    IBOutlet UITableView* createdPlayers;
    IBOutlet UIButton* superCat;

    NSMutableArray *listOfPlayers;

}

@property(nonatomic, retain) IBOutlet NSObject *listOfPlayers;

-(NSString *) pathOfFile;  
-(void)applicationWillTerminate:(NSNotification*)notification;

-(IBAction)AddButtonAction:(id)sender;

-(IBAction)switchView:(id)sender;

-(IBAction)newView:(id)sender;

@property (nonatomic, retain) UITableView* createdPlayers;


@end

代码更新12月20日:

-(NSString *) pathOfFile{
    NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES); 
        NSString *documentFolder = [paths objectAtIndex:0];
    return [documentFolder stringByAppendingFormat:@"myfile.plist"];

}


-(void)applicationWillTerminate:(NSNotification*)notification
{
    [self.listOfPlayers writeToFile:[self pathOfFile] atomically:YES encoding:NSUTF8StringEncoding error:NULL];

}



- (void)viewDidLoad
{
    self.listOfPlayers = [[NSMutableArray alloc] init];

    NSString *filePath = [self pathOfFile];
    if ([[NSFileManager defaultManager]fileExistsAtPath:filePath]) {
        NSArray *array = [[NSArray alloc]initWithContentsOfFile:filePath];
        self.listOfPlayers = array;
        [array release];

    }

    UIApplication *app = [UIApplication sharedApplication];
    [[NSNotificationCenter defaultCenter]addObserver:self selector:@selector(applicationWillTerminate:) name:UIApplicationWillTerminateNotification object:app];

    [super viewDidLoad];


}

我不知道plist。 但是您可以尝试使用NSData

NSArray *array;
NSData *data = [NSKeyedArchiver archivedDataWithRootObject:array];
//Write data
[data writeToFile:filePath atomically:YES];
//Read data
NSFileManager *fileManager = [NSFileManager defaultManager];
NSData *oldData = [fileManager contentsAtPath:filePath];
NSArray *newArray = [NSKeyedUnarchiver unarchiveObjectWithData:oldData]

欢迎来到iOS编程世界。 这很有趣,但可能会令人沮丧,就像使用任何语言进行编程一样。 我感到你很痛苦。

我看到了很多东西:

  1. 在viewDidLoad中,似乎可以将文件读取到数组中的代码可以了,但是看上去好像您只是试图将此数组的第一行分配给listOfPlayers一样。 尝试:

     self.listOfPlayers = array; 
  2. array是一个数组,您的listOfPlayers也是如此。 另外,使用self将确保使用合成的setter,从而在释放数组时保留listOfPlayers。

  3. 我相信在applicationWillTerminate中,您希望将listOfPlayers写入文件,但是您实际要做的是分配和初始化一个空数组,然后将THAT写入文件。 尝试:

     -(void)applicationWillTerminate:(NSNotification*)notification { [self.listOfPlayers writeToFile: [self pathOfFile] atomically:YES]; } 

我希望这有帮助!

您的viewDidLoad中似乎有问题

if ([[NSFileManager defaultManager]fileExistsAtPath:filePath]) {
    NSArray *array = [[NSArray alloc]initWithContentsOfFile:filePath];
    listOfPlayers.array = [array objectAtIndex:0];
    .
    .

}
.
.
.
listOfPlayers = [[NSMutableArray alloc] init];

您在分配listOfPlayers之前就已经对其进行了访问。 listOfPlayers.array也是错误的

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM