节的NSFetchedResultsController和transient属性 [英] NSFetchedResultsController and transient property for sections
问题描述
在数据模型中,我有一个临时属性 uppercaseFirstLetterOfName
,它将返回持久性属性的第一个字母。我在
NSSortDescriptor * sortByWordDescriptor = [[NSSortDescriptor alloc]
initWithKey:@subject是];
NSArray * sortArray = [[NSArray alloc]
initWithObjects:sortByWordDescriptor,nil];
[fetchRequest setSortDescriptors:sortArray];
NSFetchedResultsController * controller = [[NSFetchedResultsController alloc]
initWithFetchRequest:fetchRequest
managedObjectContext:managedObjectContext
sectionNameKeyPath:@uppercaseFirstLetterOfName
cacheName:@Root ];
当我改变从fetchedresultscontroller取得的持久化对象时,应该删除该部分,只有 controller:didChangeObject
fires。但由于该部分已经走了(事实上),我会期望 controller:didChangeSection
也被触发。在调整持久化对象以使 controller:didChangeSection
被调用时,我应该多做些额外的工作吗?
UPD: p>
这是模型子类中的临时属性getter
- (NSString *) uppercaseFirstLetterOfName
{
[self willAccessValueForKey:@uppercaseFirstLetterOfName];
NSString * aString = [[self valueForKey:@subject] uppercaseString];
NSString * stringToReturn = [aString substringWithRange:
[aString rangeOfComposedCharacterSequenceAtIndex:0]];
[self didAccessValueForKey:@uppercaseFirstLetterOfName];
return stringToReturn;
}
这里我获取对象并传递给view controller修改
...
detailViewController.unit =(ModelClass *)[fetchedResultsController
objectAtIndexPath:indexPath];
...
最后修改数据
unit.subject = someTextField.text;
...
[unit.managedObjectContext save:& error]
我没有任何其他特殊的临时对象,所以我不直接修改它。
没有看到代码围绕该瞬态属性的更新,我不得不猜测你有一个KVO问题。你可以发布代码吗?
更新
如果没有,是否为 uppercaseFirstLetterOfName
设置了一个依赖项?如果没有,那就是你的问题。更改一个值不会触发其他值更改。这是一个KVO情况。
NSFetchedResultsController正在观察 uppercaseFirstLetterOfName
,并等待它更改。它不只是观察对象改变。因此,当您更改主题时,您还需要触摸flag uppercaseFirstLetterOfName
。最简单的方法是将以下方法添加到您的 NSManagedObject
子类:
+(NSSet *)keyPathsForValuesAffectingUppercaseFirstLetterOfName
{
return [NSSet setWithObject:@Subject];
}
这将告诉KVO: code>属性已更改,它也应该触发
UppercaseFirstLetterOfName
的更改通知。
In data model I have transient property uppercaseFirstLetterOfName
which will return first letter of persistent property. I specify this property in
NSSortDescriptor* sortByWordDescriptor = [[NSSortDescriptor alloc]
initWithKey:@"subject" ascending:YES];
NSArray* sortArray = [[NSArray alloc]
initWithObjects:sortByWordDescriptor, nil];
[fetchRequest setSortDescriptors:sortArray];
NSFetchedResultsController* controller = [[NSFetchedResultsController alloc]
initWithFetchRequest:fetchRequest
managedObjectContext:managedObjectContext
sectionNameKeyPath:@"uppercaseFirstLetterOfName"
cacheName:@"Root"];
When I change the persistent object taken from fetchedresultscontroller so the section should be deleted, only controller:didChangeObject
fires. But since the section is gone(in fact) I would expect controller:didChangeSection
also be fired. Should I do something extra when modifying persistent object in order to make controller:didChangeSection
invoked?
UPD:
This is transient property getter in model subclass
- (NSString *)uppercaseFirstLetterOfName
{
[self willAccessValueForKey:@"uppercaseFirstLetterOfName"];
NSString *aString = [[self valueForKey:@"subject"] uppercaseString];
NSString *stringToReturn = [aString substringWithRange:
[aString rangeOfComposedCharacterSequenceAtIndex:0]];
[self didAccessValueForKey:@"uppercaseFirstLetterOfName"];
return stringToReturn;
}
Here I get the object and pass to view controller to modify
...
detailViewController.unit = (ModelClass*)[fetchedResultsController
objectAtIndexPath:indexPath];
...
and finally data modification
unit.subject = someTextField.text;
...
[unit.managedObjectContext save:&error]
I don't have anything other special for transient object, so I don't modify it directly.
WIthout seeing the code surrounding the update of that transient property I would have to guess that you are having a KVO issue. Can you post the code?
Update
Do you have a custom setter for subject? If not, do you have a dependent key set up for uppercaseFirstLetterOfName
? If not, then that is your issue. Changing one value will not trigger the other value to change. This is a KVO situation.
NSFetchedResultsController is observing the uppercaseFirstLetterOfName
specifically and waiting for it to change. It is not just watching the object to change. Therefore when you change the subject you need to "flag" uppercaseFirstLetterOfName
as touched as well. The easiest way to do this is to add the following method to your NSManagedObject
subclass:
+ (NSSet*)keyPathsForValuesAffectingUppercaseFirstLetterOfName
{
return [NSSet setWithObject:@"Subject"];
}
This will tell KVO that whenever the subject
property has changed that it should also fire a change notification for UppercaseFirstLetterOfName
.
这篇关于节的NSFetchedResultsController和transient属性的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!