1

NSMutableArray から plist にデータを永続化する方法を学習するのに役立つ簡単なテスト アプリがあります。AppDelegate.m ファイルで「saveData」と呼ばれる ViewController メソッドを呼び出してデータを保存しようとするまで、すべてがうまく機能しているようです。

- (void)applicationDidEnterBackground:(UIApplication *)application
{

    [ViewController saveData];
}

メソッドはViewController.hで明確に宣言されていますが、次のように、「セレクター「saveData」の既知のクラスメソッドはありません。

//
//  ViewController.h
//  PlistTest
//
//  Created by Tim Jones on 10/30/13.
//  Copyright (c) 2013 TDJ. All rights reserved.
//

#import <UIKit/UIKit.h>

@interface ViewController : UIViewController

@property (weak, nonatomic) IBOutlet UILabel *nameLabel;

@property (weak, nonatomic) IBOutlet UILabel *timeLabel;

@property NSMutableArray *mainActivityArray;



- (IBAction)buttonHit:(id)sender;

-(NSString *) getFilePath;
-(void) saveData;
-(void) loadData;


@end

ViewController.m に実装されているため、次のようになります。

//
//  ViewController.m
//  PlistTest
//
//  Created by Tim Jones on 10/30/13.
//  Copyright (c) 2013 TDJ. All rights reserved.
//

#import "ViewController.h"
#import "DataClass.h"

@interface ViewController ()

@end

@implementation ViewController

-(NSString *) getFilePath
{
    NSArray *pathArray = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
    return [[pathArray objectAtIndex:0] stringByAppendingPathComponent:@"PlistTestData"];
}

-(void) saveData
{
    [self.mainActivityArray writeToFile: self.getFilePath atomically:YES];
}

ViewController.h を AppDelegate.h にインポートしました。

私はかなり緑なので、ここにいる多くの人にとって問題は明白かもしれません. 助けていただければ幸いです。

4

3 に答える 3

1

問題:

[ViewController saveData];

saveDataclass name を使用して method を呼び出していViewControllerます。
ただしsaveData、クラスメソッドではなくインスタンスメソッドです。

-(void) saveData;

修正:

saveData1)クラスメソッドとして宣言

+(void) saveData;

2)saveDataのオブジェクトを使用して呼び出しますViewController

ViewController *vControl = [[ViewController alloc] init];
[vControl saveData];
于 2013-11-01T19:14:07.780 に答える
0

前の回答 (Midhun #2) は機能しますが、Application Did Enter Background Notification を使用してデリゲートをスキップした方がよいと思います。

これを「view did load」に追加するだけです。アプリがバックグラウンドになるたびに saveData が呼び出されます。

[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(saveData) name:UIApplicationDidEnterBackgroundNotification object:nil];

お役に立てれば。

于 2013-11-01T20:55:52.707 に答える
0

他の人が指摘したように、あなたの問題は、メソッド呼び出しが「クラスメソッド[ViewController saveData]」を呼び出そうとしていることを明確に示しており、間違いなく「インスタンスメソッド」を呼び出したいことです(ビューコントローラーのインスタンスであるため)保存したいデータ)。これを実現するには、次の 2 つの基本的な選択肢があります。

  1. saveDataビュー コントローラーでアプリ デリゲートにメソッドを呼び出させることができます。

    さまざまなコメントの中で、「想像できるあらゆる方法とあらゆる場所で VC のインスタンス化を試みた」と述べています。しないでください。Midhun の例は概念的なもので、クラスとインスタンス メソッドの違いを示しています。ただし、インスタンス メソッドを呼び出したい場合は、新しいビュー コントローラーをインスタンス化するのではなく、ビュー コントローラーの既存のインスタンスに対してこれを呼び出したいと考えています。

    では、View Controller の既存のインスタンスへの参照をどのように取得するのでしょうか? あなたがしたいことは、(a)saveDataメソッドでView Controllerへの参照を保持するためにアプリデリゲートにプロパティを作成することです。(b) ビュー コントローラーでアプリ デリゲートのプロパティを設定します。そのため、まず、アプリ デリゲートの .h ファイルにプロパティを作成して、View Controller を参照します。

    @property (weak, nonatomic) ViewController *viewController;
    

    #import "ViewController.h"明らかに、.h ファイルの最初の行を忘れないでください。

    次に、viewDidLoadビュー コントローラーのメソッドでアプリ デリゲートのviewControllerプロパティを更新します。

    - (void)viewDidLoad
    {
        [super viewDidLoad];
    
        AppDelegate *delegate = [[UIApplication sharedApplication] delegate];
        delegate.viewController = self;
    }
    

    繰り返しますが、ファイル#import "AppDelegate.h"の先頭にあることを忘れないでください。ViewController.m

    それが完了すると、アプリのデリゲートは、applicationDidEnterBackground設定したこのプロパティを参照できるようになりますviewDidLoad

    - (void)applicationDidEnterBackground:(UIApplication *)application
    {
        [self.viewController saveData];
    }
    

    率直に言って、この手法を行った場合は、特にデリゲート プロトコル パターンを採用するなど、さらに改良することを提案するかもしれませんが、上記の手法を習得するまで、その会話は延期します。

  2. 上記よりも簡単に、このアプリ デリゲートapplicationDidEnterBackgroundコードを完全に削除し、ビュー コントローラー自体を、アプリがバックグラウンドに入ることに関連付けられているシステム通知に応答させるだけです。そして、言うまでもなく、このコードをビュー コントローラー自体に配置します。

    - (void)viewDidLoad
    {
        [super viewDidLoad];
    
        [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(saveData) name:UIApplicationDidEnterBackgroundNotification object:nil];
    }
    
    - (void)dealloc
    {
        [[NSNotificationCenter defaultCenter] removeObserver:self name:UIApplicationDidEnterBackgroundNotification object:nil];
    }
    
    - (void)saveData
    {
        // save your data here
    }
    

    ご覧のとおり、 で監視するように登録しますがUIApplicationDidEnterBackgroundNotificationviewDidLoadでオブザーバーを削除することも忘れないでくださいdealloc@selectorまた、メソッド名がメソッド名と正確に一致していることも確認しました (たとえば、この例では、パラメーターがなく、したがってコロンもありません)。

于 2013-11-02T06:51:06.963 に答える