谓词,从 NSDate 中按年份过滤,产生一个 nil 日期和一个讽刺的 Xcode 错误
Posted
技术标签:
【中文标题】谓词,从 NSDate 中按年份过滤,产生一个 nil 日期和一个讽刺的 Xcode 错误【英文标题】:Predicate, Filtering by Year from NSDate producing a nil date and a sarcastic Xcode error 【发布时间】:2013-12-04 07:41:47 【问题描述】:我有一个简单的应用程序:用户在 UIDatePicker 中选择一个日期并填写一些字段,然后通过 Core Data 保存,表视图控制器应该只显示在日期选择器中选择的年份列表.如果有人选择了 1 个以 2013 为年份的日期,然后又选择了另一个,则表视图中应该只有 1 个 2013 条目。
我有用于重复检查的后端逻辑。我的问题是 FetchedResultsController 中这个表视图控制器的实际谓词。这导致我的日期为零,Xcode 也给了我一个幽默的信息!
date cannot be nil
I mean really, what do you think that operation is supposed to mean with a nil date?
An exception has been avoided for now.
A few of these errors are going to be reported with this complaint, then further violations will simply silently do whatever random thing results from the nil.
做谓词的代码是:
NSCalendar *calendar = [NSCalendar currentCalendar];
NSDateComponents *components = [calendar components:(NSYearCalendarUnit ) fromDate:self.date.dateOfEvent];
//create a date with these components
NSDate *startDate = [calendar dateFromComponents:components];
[components setYear:components.year]; //reset the other components
fetchRequest.predicate = [NSPredicate predicateWithFormat:@"dateOfEvent == %@",startDate];
NSLog(@"New Date = %@", startDate);
我有一个名为 date 的 Date Entity 属性,dateOfEvent 属性是我试图提取的 NSDate!
NSLog 给了我2001-01-01 00:00:00 +0000
,所以它显然没有得到那个日期。
如果有人能够帮助解决这个问题:a)为什么我有效地得到了一个 nil 日期,b)对 Xcode 错误的想法,c)我将如何更新 cellForRow 以仅显示年份?
谢谢!
【问题讨论】:
Sending NSCFCalendar nil NSDate Sarcastic Error的可能重复 报错信息确实不正常,只是简单的表示self.date.dateOfEvent
是nil
。
谢谢马丁 - 看着那个帖子,它是有道理的!似乎苹果公司的某个人有幽默感!
是的。但请注意,通过简单的 Google 搜索错误消息会导致您看到该帖子以及更多类似的帖子。
绝对 - 很抱歉没有提及 - 我已经阅读了一些关于这个错误的帖子,但似乎没有一个可以为我的问题提供可行的解决方案
【参考方案1】:
首先,self.date.dateOfEvent
很可能为零。这就是讽刺错误信息所表明的。但是,您的日志消息似乎包含有效年份,因此使用调试器单步执行代码可能会有所帮助。
第二,[components setYear:components.year]
与components.year = components.year
相同,它完全没有任何作用。仅包含年的组件的日期将没有月、日、小时等(它们都将为零)。
第三,如果数据库中的日期完全相同(精确到秒),谓词只会返回一个值,但情况可能并非如此。假设您有某年要查询,则需要构造一个日期间隔来查找相关记录。
NSInteger year = 2011;
NSDateComponents *components = [[NSDateComponents alloc] init];
components.year = year;
NSDate *startOfYear = [[NSCalendar currentCalendar] dateFromComponents:components];
components.year = 1; // (one year)
NSDate *endOfYear = [[NSCalendar currentCalendar] dateByAddingComponents:components
toDate:startOfYear options:0];
然后使用这样的谓词:
[NSPredicate predicateWithFormat:
@"dateOfEvent > %@ && dateOfEvent <= %@", startOfYear, endOfYear];
【讨论】:
非常感谢@Mundi - 这非常有意义,并且通过一些 NSLogs 和您的代码,我可以看到它报告了正确的日期。这几乎是可行的——我的下一个问题是关于 NSInteger year = 2011;我已将其设置为 2013 年,果然,它显示了 2013 年的条目(尽管如果月份/日期不同,会有一些重复项 - 我将单独处理).. 我将如何修改该代码以便用户添加从 datePicker 中选择的年份(保存到 dateOfEvent)而不是预定义的年份?再次感谢 显然,您将使用一个变量并从日期选择器中获取数字。 (或者您可以只使用允许年份的UIPicker
,以便为用户进一步简化它。)如何使用 Picker 确实是一个不同的问题,因此您应该接受这个答案并提出一个新问题。
感谢 Mundi - 非常感谢!以上是关于谓词,从 NSDate 中按年份过滤,产生一个 nil 日期和一个讽刺的 Xcode 错误的主要内容,如果未能解决你的问题,请参考以下文章
作为获取谓词的日期范围 - 核心数据之间的 NSDate 谓词