从另一个视图控制器记录字符串时,NSLog返回(null)

时间:2013-08-13 20:39:36

标签: iphone objective-c nsstring

我之前发过一个关于同样事情的问题,但现在我已经做了一个简单的项目来展示我在做什么,所以问题可以更容易找到。

我有两个viewControllers,一个叫做ViewController,另一个是SecondViewController。 我尝试将一个名为testy的NSString发送到viewController并记录它,但它返回null。

这是我的代码尝试将字符串从viewController发送到secondViewController

ViewController.m

#import "ViewController.h"

#import "SecondViewController.h"

@interface ViewController ()

@end

@implementation ViewController

@synthesize cellName;

- (void)viewDidLoad
{
    [super viewDidLoad];

    cellName = @"testy";

    SecondViewController *obj = [[SecondViewController alloc] init];

    obj.cellName2 = self.cellName;    
}
- (void)didReceiveMemoryWarning
{
    [super didReceiveMemoryWarning];
    // Dispose of any resources that can be recreated.
}

@end

ViewController.h

#import <UIKit/UIKit.h>

@interface ViewController : UIViewController {

}
@property(nonatomic,retain) NSString *cellName;

@end

SecondViewController.m

#import "SecondViewController.h"

#import "ViewController.h"

@interface SecondViewController ()

@end

@implementation SecondViewController

@synthesize cellName2;

- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
{
    self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
    if (self) {
        // Custom initialization
    }
    return self;
}

- (void)viewDidLoad
{
    [super viewDidLoad];

}

- (void)viewDidAppear:(BOOL)animated {
NSLog(@"%@",cellName2);

}
- (void)didReceiveMemoryWarning
{
    [super didReceiveMemoryWarning];
    // Dispose of any resources that can be recreated.
}

@end

SecondViewController.h

#import <UIKit/UIKit.h>

@interface SecondViewController : UIViewController {

}

@property(nonatomic,retain) NSString *cellName2;

@end

修改

我想说我的故事板有两个viewController,每个都有一个按钮。每个按钮以模态方式将您带到另一个视图。

5 个答案:

答案 0 :(得分:2)

你确定正在调用viewDidLoad吗?我认为在视图加载之前不会调用它。我不认为它是在alloc init之后调用的。 您也在init之后在obj 2中设置字符串。即使您的想法是正确的,也可以在设置字符串之前调用'viewDidLoad'方法。

如果你想在init上设置变量,你需要将viewController 2的init方法覆盖为initWithMyVariable 之类的东西,然后在init上设置var。

来自:Passing Data between View Controllers

将数据从另一个视图控制器传递到视图控制器。如果要将对象/值从一个视图控制器传递到另一个可能正在推送到导航堆栈的视图控制器,则可以使用此方法。

对于此示例,我们将使用ViewControllerA和ViewControllerB

要将ViewControllerA中的BOOL值传递给ViewControllerB,我们将执行以下操作。

ViewControllerB.h中的

为BOOL创建一个属性

@property(nonatomic) BOOL *isSomethingEnabled;
在ViewControllerA中,您需要告诉它有关ViewControllerB的信息,所以请使用

import“ViewControllerB.h”

然后你要加载视图的地方,例如。 didSelectRowAtIndex或某些IBAction,你需要在将它推到导航堆栈之前在ViewControllerB中设置属性。

ViewControllerB *viewControllerB = [[ViewControllerB alloc] initWithNib:@"ViewControllerB" bundle:nil];
viewControllerB.isSomethingEnabled = YES;
[self pushViewController:viewControllerB animated:YES];

这会将ViewControllerB中的isSomethingEnabled设置为BOOL值YES。

答案 1 :(得分:1)

对于阅读本文的所有人来说,提及在两个视图之间传递变量的工作模式可能是值得的:

选项:

  1. 使用全局变量:SO answer
  2. 使用委托模式:SO answer
  3. 使用通知基础架构:article
  4. 在app的userdefault存储中保留该值,然后在需要时阅读:SO answer
  5. 对于这种特殊情况,最好不要在firstviewcontroller的viewdidload中创建secondviewcontroller,而是在用户操作发生时保持cellName直到那一点(例如按下按钮),然后在该方法中设置新创建的secondviewcontroller的cellName2属性。

    SecondViewController *secondViewController = [[SecondViewController alloc] initWithNibName:@"second" bundle:nil];
    secondViewController.cellName = self.cellName;
    

    我已经测试过,它正确记录了secondviewcontroller的viewdidload中的值。

答案 2 :(得分:0)

而不是:cellName = @"testy";你应该致电:

 self.cellName = @"testy";

此外,当您allocinit进入时:

SecondViewController *obj = [[SecondViewController alloc] init];,  当时正在调用第二个ViewController的viewDidLoad(),并且您稍后在行obj.cellName2 = self.cellName;中初始化它的iVar

这就是你将NSLOG作为null的原因。

在secondViewController的viewWillAppear()中打印NSLOG,这次你会看到正确的值。

答案 3 :(得分:0)

为第二个视图控制器创建初始化方法以传递变量..

在secondview控制器中 .h文件

添加init方法

- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil cellString(NSString* )cellName;

和.m文件

-(id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil cellString(NSString* )cellName{

   self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];

     if (self) {

        // Custom initialization
     cellName2=cellName;

     }
     return self;

}

并在ViewController.m中进行初始化

SecondViewController *obj = [[SecondViewController alloc] initWithNibName:@"SecondViewController" bundle:nil cellString:self.cellName];

这应该有用...... 祝你好运

答案 4 :(得分:-1)

在viewcontroller.m中,viewDidLoad中包含以下内容:

..
..
SecondViewController *obj = [[SecondViewController alloc] init];
obj.cellName2 = self.cellName;    
}

SecondViewController&#34; obj&#34;在viewDidLoad结束之前永远不会出现,因此NSLog打印为null。

如果您想通过故事板将值传递给SecondViewController,则需要使用 prepareForSegue 方法。可以找到使用它的一个很好的例子here