2012-04-05 53 views
0

有人能帮助我理解这个例子中,原始的访问者:我不明白什么是自动设置的,这些方法的顺序:原始存取

1.after一个人创建的,是willSave第一种方法叫做? (我猜是这样,因为我们创建insertNewObjectForEntityForName后,一个人​​叫)

2.in RootViewController的(代码的第二块),就可以调用的eyeColor,吸气用:person.eyeColor
一)eyeColor ,我们称之为:[self eyeColorData]
b)setPrimitiveEyeColorDatawillSave,仅如果primitiveEyeColor存在访问,
C)setPrimitiveEyeColoreyeColor,只称为如果[self eyeColorData]存在。所以,我对这段代码有点困惑,有人可以帮我吗?

这里的代码约eyeColoreyeColorData

@dynamic eyeColorData; 
@dynamic eyeColor; 

@interface AWPerson (PrimitiveAccessors) 

- (UIColor *)primitiveEyeColor; 
- (void)setPrimitiveEyeColor:(UIColor *)value; 
- (NSData *)primitiveEyeColorData; 
- (void)setPrimitiveEyeColorData:(NSData *)value; 

@end 

+ (id)personInManagedObjectContext:(NSManagedObjectContext *)moc { 
    return [NSEntityDescription 
      insertNewObjectForEntityForName:@"Person" 
      inManagedObjectContext:moc]; 
} 

+ (id)randomPersonInManagedObjectContext:(NSManagedObjectContext *)moc { 
    AWPerson *randomPerson = [self personInManagedObjectContext:moc]; 
    //... 
    randomPerson.eyeColor = [self randomColor]; //setter eyeColor 
    return randomPerson; 
} 

+ (UIColor *)randomColor { 
    static NSArray *colorsArray = nil; 

    if(!colorsArray) { 
     colorsArray = [[NSArray alloc] initWithObjects: 
         [UIColor lightGrayColor], 
         [UIColor blueColor], 
         [UIColor greenColor], nil]; 
    } 

    int randomIndex = arc4random() % [colorsArray count]; 
    return [colorsArray objectAtIndex:randomIndex]; 
} 

- (void)willSave { 
    UIColor *color = [self primitiveEyeColor]; 
    if(color) { 
     [self setPrimitiveEyeColorData: 
     [NSKeyedArchiver archivedDataWithRootObject:color]]; 
    } else { 
     [self setPrimitiveEyeColorData:nil]; 
    } 

    [super willSave]; 
} 

- (UIColor *)eyeColor { 
    [self willAccessValueForKey:@"eyeColor"]; 
    UIColor *tmpValue = [self primitiveEyeColor]; 
    [self didAccessValueForKey:@"eyeColor"]; 
    if(tmpValue) return tmpValue; 

    NSData *colorData = [self eyeColorData]; 
    if(!colorData) return nil; 

    tmpValue = [NSKeyedUnarchiver unarchiveObjectWithData:colorData]; 
    [self setPrimitiveEyeColor:tmpValue]; 

    return tmpValue; 
} 

在RootViewController的:

- (void)tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath { 
    AWPerson *person = [[self fetchedResultsController] objectAtIndexPath:indexPath]; 

    [cell setBackgroundColor:person.eyeColor]; 
} 

感谢

回答

1

编辑 - 在willSave
添加信息要回答你的第一个问题, willSave is c只要对象被保存就使用(使用save方法)。因此,第一个调用的方法将是类方法之一(用于创建对象)或init,然后,因为您说创建对象后保存,willSave会被调用。

我认为理解这一点的关键是要认识到eyeColor,primitiveEyeColor及其设置者最终都会与内存中的同一变量(名为eyeColor的iVar)进行交互。区别在于setter/getter中的代码是否被调用(在本例中为- (UIColor *)eyeColor {函数)。

只是有几个不同的方式来与它进行交互:

  1. [self primitiveEyeColor]; - 这直接读取伊娃的价值。
  2. [self setPrimitiveEyeColor:tmpValue]; - 这可以直接设置iVar的值。
  3. [self eyeColor] - 这会调用您的类中的- (UIColor *)eyeColor方法(最终应该检索iVar或其表示形式)。
  4. [self setEyeColor:value] - 这在您的班级中调用- (void)setEyeColor:(UIColor *)newColor方法。请注意,在这种情况下,它不存在,因此它只是调用原始方法(并执行KVO魔术)。

在这个特定的代码中,他们使用的是“非标准持久属性”,因为NSManagedObject不支持UIColor。阅读关于它here

EDIT 2
为了回答您的其他问题:

一)randomPerson.eyeColor = [self randomColor]的颜色是 访问与[self primitiveEyeColor](在willSave)?

是的,一旦眼睛颜色设置(通过该setEyeColor方法或setPrimitiveEyeColor方法),你可以从primitiveEyeColor读它,它会返回相同的值。 请注意,设置后,eyeColorprimitiveEyeColor会返回相同的值,并且可以从班级中的任何位置(而不仅仅是willSave)调用。

B)因此,如果[self primitiveEyeColor] != nil:在eyeColor,行: if(tmpValue) return tmpValue;因此应始终是真实的...... 我们什么时候可以解除存档eyeColorData如果UIColor *tmpValue = [self primitiveEyeColor]-(UIColor *)eyeColor总是返回?

此方法仅着眼于eyeColorData(这是最后一次通话过程中存储到willSave)如果eyeColor为零。这是一个优化,因为我们可以跳过所有这些,如果我们愿意,每次都可以取消存档eyeColorData。在这种情况下,一旦某个值被取消存档或设置为新值,它将始终存储该值并返回以便我们不必再次调用unarchive。

此外,我确实认为这是一个错误(虽然它可能是设计)。假设我们执行以下步骤:

  1. eyeColor设置为随机颜色(比方说蓝色)。
  2. 保存对象。
  3. 设置eyeColor为零

现在,如果你用检查它[self eyeColor]会看到primitiveEyeColor是nil和取消归档eyeColorData再次颜色,因此返回蓝色先前存储。您应该可以超越设定的功能,以便当eyeColor设置为nil时,它将eyeColorData设置为nil。这样,在将其设置为nil之后检查eyeColor的值将如预期的那样返回nil

+0

感谢lnafziger,a)'randomPerson.eyeColor = [self randomColor]'中的颜色可以通过'[self primitiveEyeColor]'(in'willSave')访问? b)所以如果'[self primitiveEyeColor]!= nil':在'eyeColor'中,行:'if(tmpValue)return tmpValue;'因此应该总是真的......我们何时可以取消存档'eyeColorData'如果'UIColor * tmpValue = [self primitiveEyeColor]'总是在' - (UIColor *)eyeColor'中返回?再次感谢 – Paul 2012-04-06 00:01:27

+1

我更新了我的答案以解决这些问题,以便我有更多空间。 :) – lnafziger 2012-04-06 03:41:41

+0

谢谢!关于你的n°3:在我们保存物体后,我们在哪里设置eyeColor为零? – Paul 2012-04-06 11:09:55