1

以编程方式将子视图添加到视图的正确方法是什么,

A)使用@property:

// SampleViewController.h
@interface SampleViewController : UIViewController

@property (nonatomic, weak) UITableView *subTableView;
@end

// SampleViewController.m
@synthesize subTableView = _subTableView;

或 B)在 loadView 中:

// SampleViewController.m 
- (void)loadView
{
    UITableView *subTableView = [[UITableView alloc] initWithFrame:self.view.bounds];
    [self.view addSubview:subTableView];
}

同样,这是假设我根本不使用 IB。两者之间有什么区别(因为实际上两者似乎都有效)?

附加问题,如果我在 中同时具有 A) 和 B) 代码SampleViewController.m,为什么 XCode 允许我subTableView在 B 中用作变量名,即使我已经@synthesize在代码部分使用了该名称?

更新: 我做了一些挖掘,结果发现从 XCode 4.4 开始不再需要@synthesize关键字。

4

4 回答 4

2

如果您想访问两个不同类中的对象,则使用@property,这是更好的方法,因为我们也可以释放它,否则如果您想在本地使用局部变量就足够了

于 2013-09-06T05:43:05.970 回答
2

取决于你的需要。如果您想添加一次并忘记它,则局部变量就足够了。它会被superview保留,不会被释放。

但是,如果您希望稍后访问它,您可以使用实例变量或属性来保留对您的视图的引用。

再次,您的财产是弱还是强取决于您的使用情况。如果将它添加到超级视图并且不再删除它,那么弱就足够了,因为它被超级视图保留。但是,如果您动态添加和删除它,例如以横向显示它但以纵向删除它,那么您会希望该属性具有“强”修饰符,以便即使对象不属于查看层次结构。

于 2013-09-06T02:50:54.280 回答
1

正如您所说,(A)或(B)都有效。如果你需要在loadView之外的其他方法中引用subTableView,那么你应该使用(A)。

至于附加问题,您可以在 (B) 中使用 subTableView,因为您要声明一个与合成变量同名的局部变量。

于 2013-09-06T02:53:42.877 回答
1

第一种方法很好。但对于第二个,这是不正确的。你需要这样做

// SampleViewController.m 
- (void)loadView
{
  CGRect frame = ...
  UIView * view = [[UIView alloc] initWithFrame:frame]; 
  UITableView *subTableView = [[UITableView alloc] initWithFrame:frame];
  // Warn: it's |view|, not |self.view|,
  //   should not use |self.view| in this method except the retain process at bottom,
  //   i.e.: |self.view = view|.
  [view addSubview:subTableView];
  // If not use ARC, you need to release the view here: [subTableView release];

  // Note: |-loadView| is for |self.view| in case the view does not exist.
  //   Generally specking, it'll only be dispatched once.
  self.view = view;
  // If not use ARC, ...: [view release];
}

或者您可以在方法中添加子视图-viewDidLoad:

- (void)viewDidLoad
{
  [super viewDidLoad];

  UITableView *subTableView = [[UITableView alloc] initWithFrame:self.view.bounds];
  [self.view addSubview:subTableView];
  // If not use ARC, ...: [subTableView release];
}

如果您需要在视图加载后频繁更新视图数据,您最好像您提到的第一种方式那样声明子视图。

于 2013-09-06T02:53:20.377 回答