【问题标题】:Compare integer with string in NSPredicate在 NSPredicate 中比较整数和字符串
【发布时间】:2020-09-23 14:33:57
【问题描述】:

我在项目数组中有一系列锻炼程序(它们的代码在 Objective-C 上),在每个程序中我都有@property (nullable, nonatomic, copy) NSString *scheduleStr; 用于程序持续时间。此属性存储诸如 1 周2 周3 周 等值。我需要过滤所有大于 6 周的值。我正在尝试应用 NSPredicate:

predicates.append(NSPredicate(format: "scheduleStr.integerValue >= 6"))

在此之后,我只收到长度为 6-9 周的程序,但不超过 10 周,但可以肯定的是,我在数据库中有几个长度等于 12 周的程序。 如果我试图应用这样的东西:

predicates.append(NSPredicate(format: "scheduleStr.integerValue >= 10"))

我会收到几乎所有的节目。如何获取超过选定值的所有程序?

【问题讨论】:

  • 您是在 Core Data 上使用谓词还是数组,它看起来像是一个数组,但您已使用 Core Data 标记了问题,因此不清楚。此外,您将谓词附加到数组中,那么您是否有多个同时使用的谓词(复合谓词)?我尝试使用自定义类和 NSArray 在操场上重现这一点,但谓词工作正常。
  • 是的,这是核心数据。我正在请求获得一组合适的程序。
  • 您是否单独测试了这个谓词而没有其他任何人的获取请求?

标签: swift core-data nspredicate


【解决方案1】:

问题在于,尽管您指定了integerValue,但在将谓词用作提取的一部分时,CoreData 将您的字符串视为字符串。在字符串方面,10 weeks 是“小于”6 weeks,因此它被排除在结果之外。

您应该存储数字(作为 Int)而不是存储字符串。然后添加文本“周”是您出于显示目的所做的事情。如果您存储的是数字而不是字符串,那么 CoreData 可以进行数值比较,并且您的谓词将按预期工作。

如果您真的不想这样做,可以使用一种解决方法和一种技巧。解决方法是过滤内存中的对象,而不是作为提取的一部分。然后,integerValue 将被正确解释,并且比较将是数字。

破解方法是强制 CoreData 将您的字符串视为数字,通过使用数字函数,例如 abs(假设您只有正数周数,取绝对值使值保持不变) :

predicates.append(NSPredicate(format: "abs:(scheduleStr) >= 6"))

【讨论】:

  • 很遗憾,我无法更改保存信息的格式,所以感谢您解释问题的原因和破解。
  • @Maxvale:另一个“hack”是使用localizedStandardCompare作为比较函数,例如stackoverflow.com/a/30554868/1187415
【解决方案2】:

要在您的情况下获取字符串中的整数部分,您可以查看以下内容:

假设元素就是你的字符串

let component = element.components(separatedBy: .letters) // this will give you the non letter values 
let integerValues = component.filter({ $0 != "" }) 
print(integerValues[0]) // As first value in your input string is an integer

这将为您提供可用于过滤数组的字符串的整数部分。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2011-11-24
    • 1970-01-01
    • 2011-09-03
    • 1970-01-01
    • 2013-09-03
    • 2015-10-27
    • 1970-01-01
    相关资源
    最近更新 更多