我的NSMAnagedObject中有一个依赖于其他enitity的权限,所以在阅读了Depend Keys上的文档后,我在我的子类中提出了以下内容
+ (NSSet *)keyPathsForValuesAffectingValueForKey:(NSString *)key
{
NSSet *keyPaths = [super keyPathsForValuesAffectingValueForKey:key];
if ([key isEqualToString:@"assetAmount"]) {
NSArray *affectingKeys = @[@"assetAlternativeCur", @"assetAltCur", @"assetCurrency"];
keyPaths = [keyPaths setByAddingObjectsFromArray:affectingKeys];
}
return keyPaths;
}
- (void)setAssetAmount:(NSDecimalNumber *)assetAmount
{
[self willChangeValueForKey:@"assetAmount"];
if ([[self useAlternativeCur] boolValue] == YES) {
NSDecimalNumber *result;
result = [[self assetConversionRate] decimalNumberByMultiplyingBy:[self assetAlternativeCur]];
[self setPrimitiveAssetAmount:result];
} else {
[self setPrimitiveAssetAmount:assetAmount];
}
[self didChangeValueForKey:@"assetAmount"];
}
我的问题是,当我直接更改“assetAmount”值时,只会调用setter“setAssetAmount”,如果更改keyPathsForValuesAffectingValueForKey中包含的值,则不会调用setter。我是以错误的方式来做这件事的吗?我希望每次任何值改变时都会调用setter。
答案 0 :(得分:1)
NSArray *affectingKeys = @[@"assetAlternativeCur", @"assetAltCur", @"assetCurrency"];
告诉运行时系统这3个其他因素会影响assetAmount
的值...所以当其中一个更改时,您会收到assetAmount
更改的通知,但是其他3的设置者密钥不会改变assetAmount
的吸气剂的工作方式..所以你不会有任何改变......
您可以通过几种不同的方式强制执行此操作..您的assetAmount
getter可能是动态的,只需计算该值然后返回它。
或在其他3个键的setter中,您可以执行以下操作:
self.assetAmount = self.primativeAssetAmount;
但我认为这很草率,可能会引发问题...你应该只有一个值,然后是另一个方法,即具有格式化版本的adjustedAssetAmount
......
一个例子就是温度。
你有property absoluteTemp
,以及C和F的吸气剂。
getter for C: => absoluteTemp+273.15
getter for F: => 9/5 * absoluteTemp + 32
答案 1 :(得分:1)
如果您拥有assetAmount值的观察者,或者绑定到assetAmount的值,那么当影响assetAmount的值发生更改时,这些观察者和绑定将得到适当更新。然后调用assetAmount getter 。
在assetAmount getter中,您可以重新计算要返回的assetAmount。
如果你想在每次调用getter时进行计算,你就完成了。
如果你想在ivar中保存计算的值,那么你必须确保直接访问ivar以避免KVO和绑定触发。(是一个catch-22)< / p>
如果您不希望getter每次都计算该值,我相信您可以从setter中为其他值调用assetAmount的setter。你甚至不需要值影响东西,因为你正在调用setter并触发KVO。
从这个意义上讲,如果您希望assetAmount getter每次都进行计算,那么您只需要keyPathsForValuesAffectingValueForKey: 。如果您希望将其保存在ivar中,只需在其他值更改时使用其setter。
(另外,如果你要去那条路线,你可以实现keyPathsForValuesAffectingAssetAmount)