【发布时间】:2020-12-18 10:06:26
【问题描述】:
我正在尝试按 ID 过滤我的 json 数据(尝试标记一些收藏夹并使用它进行过滤)
struct workoutList : Codable {
let id : Int
let title : String
let tag : String
}
func selectedWorkoutGroup(libraryFilter: Int, jsonErgWorkouts:[workoutList], workoutGroupBox: UITextField) -> [workoutList] {
var selectedGroup = [workoutList]()
let workoutFav = [1,10,100]
if libraryFilter == 0 {
// This works because I'm filtering based on 1 specific item
selectedGroup = jsonErgWorkouts.filter { $0.tag == workoutGroupBox.text }
} else if libraryFilter == 1 {
// Here I want to filter and show only the favorites
selectedGroup = jsonErgWorkouts.filter { $0.id } //
print("selectedGroup:\(selectedGroup)")
}
return selectedGroup
}
在上面的代码中,当我有 1(一个)要过滤的特定项目然后我得到带有该标记的整个 json 数组时,过滤器就会起作用。
现在我想实现一个收藏列表,其中用户选择例如 ID == [1, 10 ,100] 作为他们的收藏夹。
如何使用过滤器命令来做到这一点?我尝试了一些东西并通过 SO 搜索(但不起作用)。大多数答案都是基于基于特定项目的过滤,例如:
selectedGroup = jsonErgWorkouts.filter { workoutFav?.contains($0.id) }
编辑:(省略了我在 userDefaults 中使用/存储收藏夹。这段代码给出了“表达式类型不明确,没有更多上下文”的错误
func selectedWorkoutGroup(libraryFilter: Int, jsonErgWorkouts:[workoutList], workoutGroupBox: UITextField) -> [workoutList] {
var selectedGroup = [workoutList]()
UserDefaults.standard.set([1,10,100], forKey: "workoutFavorite")
/// This one gets stored as [Any] so I cast it to [Int]
let workoutFav = UserDefaults.standard.array(forKey: "workoutFavorite") as? [Int]
if libraryFilter == 0 {
// This works because I'm filtering based on 1 specific item
selectedGroup = jsonErgWorkouts.filter { $0.tag == workoutGroupBox.text }
} else if libraryFilter == 1 {
selectedGroup = workoutFav.flatMap { favouriteId in // for each favourite ID
jsonErgWorkouts.filter { $0.id == favouriteId } // This returns Error "type of expression is ambiguous without more context"
} // flatMap joins all those arrays returns by "filter" together, no need to do anything else
print("selectedGroup:\(selectedGroup)")
}
return selectedGroup
}
最终解决方案: 从此改变
let workoutFav = UserDefaults.standard.array(forKey: "workoutFavorite") as? [Int]
to This(注意 as! 而不是 as?)
let workoutFav = UserDefaults.standard.array(forKey: "workoutFavorite") as! [Int]
使用@sweeper 的答案工作。谢谢
更新:
弄清楚为什么在转换 UserDefaults as? [Int] 的输出时会出现此错误“表达式类型不明确,没有更多上下文”,并且必须使用 as! [Int]
但如果用户没有将任何收藏夹保存到 UserDefault 中,则使用 as! [Int] 强制解包会导致应用程序崩溃。 (然后我不得不编写代码)如下所示
var workoutFav = [Int]()
if !(UserDefaults.standard.array(forKey: "workoutFavorite") == nil) {
workoutFav = UserDefaults.standard.array(forKey: "workoutFavorite") as! [Int]
}
然后根据此 SO https://stackoverflow.com/a/37357869/14414215 对其进行了简化并删除了强制展开,变成了这一行
let workoutFav = UserDefaults.standard.array(forKey: "workoutFavorite") as? [Int] ?? [Int]()
【问题讨论】: