由于Swift 3倾向于Data而不是[UInt8],我试图找出最有效/惯用的编码/解码方式将各种数字类型(UInt8,Double,Float,Int64等)作为数据对象.
对于使用[UInt8]有这个答案,但它似乎使用了我在Data上找不到的各种指针API.
我想基本上一些自定义扩展看起来像:
let input = 42.13 // implicit Double
let bytes = input.data
let roundtrip = bytes.to(Double) // --> 42.13
Run Code Online (Sandbox Code Playgroud)
真正逃避我的部分,我已经查看了一堆文档,我是如何从任何基本结构(所有数字都是)得到某种指针的东西(OpaquePointer或BufferPointer或UnsafePointer?).在C中,我只是在它前面拍一个&符号,然后就去了.
我想将自定义枚举保存到我的SwiftData模型中。我可以让它工作,它显示甚至更新 UI 中的值。不过,重新启动应用程序时,枚举变量/实体的更改 \xe2\x80\x99t 仍然存在!
\n使用自定义枚举时需要注意什么有什么建议吗?
\nenum Type: Int, Codable {\n case foo = 0\n case bar = 1\n}\n\n@Model\nfinal public class Item {\n var type: Type\n}\nRun Code Online (Sandbox Code Playgroud)\nstruct DetailView: View {\n @Bindable var item: Item\n \n // MARK: -\n var body: some View {\n Picker("Type", selection: $item.type) {\n Text("Foo").tag(Type.foo)\n Text("Bar").tag(Type.bar)\n }\n .pickerStyle(.segmented)\n }\n}\nRun Code Online (Sandbox Code Playgroud)\n 我有一个简单的例子。Trip我从数据库中获取所有对象:
import SwiftData
@Model
class Trip {
var name: String
}
func fetch() {
let container = ModelContainer(for: Trip.self)
let context = ModelContext(container)
let fetchDescriptor = FetchDescriptor<Trip>()
let trips = try! context.fetch(fetchDescriptor)
// Store it somewhere ...
}
Run Code Online (Sandbox Code Playgroud)
如何观察 trips 数组的变化?我知道数组中的各个对象是可观察的,并且当某些内容提交到数据库时会发生变化。但是,如果顺序发生变化,或者某些行程被删除或插入新行程怎么办?我找不到一种机制来通知这一点。
我发现的唯一方法是@Query在 SwiftUI 中使用新的属性包装器。但我想在单独的类中观察 SwiftUI 环境之外的变化。有没有办法做到这一点?
从 Swift 5.5 开始,我们可以使用这样的绑定创建 SwiftUI 列表(例如,参见这个答案):
class Item {
// ...
var isOn: Bool
}
struct ContentView: View {
@State private var items: [Item] = []
var body: some View {
NavigationView {
List {
ForEach($items) { $item in // <--- list binding
Toggle(isOn: $item.isOn) {
Text("Vibrate on Ring")
}
}
}
}
}
}
Run Code Online (Sandbox Code Playgroud)
现在我想用 SwiftData 做类似的事情,但出现错误:
struct ContentView: View {
@Environment(\.modelContext) private var modelContext
@Query private var items: [Item]
var body: some View {
NavigationView { …Run Code Online (Sandbox Code Playgroud) 完成 SwiftData 的测试版并尝试建立PersistentContainer. 我在我的上设置了一个modelContainer视图修改器ContentView,并使我的类符合@Model各种 WWDC 视频(已发布的视频)中所述的要求。
这是我要存储的基础对象,其中所有变量都符合Codable:
Board.swift
import SwiftData
@Model
class Board {
var size: Int = 3
var cellSize: CGFloat = 44
var numberOfTeamMembers: Int = 3
var numberOfEnemies: Int = 3
var spaces: [[Space]] = []
var selectedSpace: Space? = nil
var characters: [Space: Character] = [:]
var selectedCharacter: Character? = nil
var attackableSpaces: [Space] = []
var movableSpaces: [Space] = []
var teams: [Team] = [] …Run Code Online (Sandbox Code Playgroud) Swift 5.9 和新的 SwiftData 框架引入了@Model和#Predicate宏。我们现在可以在模型中使用自定义枚举和结构,如下所示:
@Model
final class Item {
var name: Name
var nature: Nature
struct Name: Codable {
let base: String
let suffix: String?
}
enum Nature: Int, Codable {
case foo = 0
case bar = 1
case baz = 2
}
init(name: Name, nature: Nature) {
self.name = name
self.nature = nature
}
}
Run Code Online (Sandbox Code Playgroud)
但是我们如何在 a 中使用它们呢Predicate?所有这些例子都失败了:
// Member access without an explicit base is not allowed in this predicate …Run Code Online (Sandbox Code Playgroud) 当我使用 @Model 宏时,为什么我的数组的顺序是随机的。
class TestModel {
var name: String?
var array: \[TestModel2\]
init(name: String = "") {
self.name = name
array = []
}
}
class TestModel2 {
var name: String?
init(name: String = "") {
self.name = name
}
}
Run Code Online (Sandbox Code Playgroud)
这工作正常,并且所有项目都array按照我添加的顺序排列。
但如果我将它们都声明为@Model,如下所示:
@Model
class TestModel {
var name: String?
var array: \[TestModel2\]
init(name: String = "") {
self.name = name
array = []
}
}
@Model
class TestModel2 {
var name: String?
init(name: String = …Run Code Online (Sandbox Code Playgroud) XCode 15 测试版 6。
只是想做一个非常简单的关系模型匹配的查询谓词:
@Query(
filter: #Predicate<Piece> {
$0.artist == selectedArtist
},
sort: [
SortDescriptor(\Piece.age, order: .reverse)
]
) var pieces: [Piece]
Run Code Online (Sandbox Code Playgroud)
我收到错误:
无法将类型“PredicateExpressions.Equal<PredicateExpressions.KeyPath<PredicateExpressions.Variable, Artist>, PredicateExpressions.Value>”的值转换为闭包结果类型“any StandardPredicateExpression”
我还尝试了艺术家的 .id 和 .persistentModelId 但没有运气。
这似乎是最基本的谓词用例,因此如果不支持它,我会感到震惊。我有什么想法吗?
我的模型是基本的:
@Model
final class Piece {
var age: Int
var artist: Artist
}
Run Code Online (Sandbox Code Playgroud)
和
@Model
final class Artist {
var name: String
@Relationship(
deleteRule: .cascade,
inverse: \Piece.artist
)
var pieces: [Piece]?
}
Run Code Online (Sandbox Code Playgroud) 我有两个一对多模型,在尝试访问模型的关系属性时遇到无法解释的崩溃。
错误原因如下:
线程 1:EXC_BREAKPOINT(代码=1,子代码=0x1038f4448)
Xcode 显示错误发生在模型的 .getValue(for: .rows) 方法中。

这是我的 SwiftData 模型:
@Model class Row {
var section: Section?
init(section: Section? = nil) {
self.section = section
}
init() {
self.section = nil
}
}
@Model class Section {
@Relationship(.cascade, inverse: \Row.section)
var rows: [Row] = []
init(rows: [Row]) {
self.rows = rows
}
}
Run Code Online (Sandbox Code Playgroud)
这是我的代码:
class ViewController: UIViewController {
var container: ModelContainer?
override func viewDidLoad() {
super.viewDidLoad()
do {
container = try ModelContainer(for: [Section.self, Row.self])
} catch {
print(error) …Run Code Online (Sandbox Code Playgroud) 我试图弄清楚如何创建一个 SwiftUI 视图,该视图使用包含传递到视图中的变量的查询来显示来自 SwiftData 的数据。我猜我将无法使用 @Query 语法,但是有人想出一种可行的方法来执行类似的操作吗?
我是否需要放弃 @Query 并只创建一个实例化它自己的 ModelContainer 和 ModelContext 的视图模型?
这段代码显然无法编译,因为 @Query 引用了 startDate 和 endDate 变量,但这正是我想要的。
struct MyView: View {
@Environment(\.modelContext) var modelContext
@Query(FetchDescriptor<Measurement>(predicate: #Predicate<Measurement> {
$0.date >= startDate && $0.date <= endDate }, sortBy: [SortDescriptor(\Measurement.date)])) var measurements: [Measurement]
let startDate: Date = Date.distantPast
let endDate: Date = Date.distantFuture
var body: some View {
Text("Help")
}
}
Run Code Online (Sandbox Code Playgroud)