一段时间以来,我一直在努力解决这个问题,但无法理解 KVC 的优势,除了:
除了上面提到的两种情况(我知道我可能错了),我不确定使用 KVC 是否有任何优势,但我找不到一个!
比如考虑下面的代码:
class Profile: NSObject {
@objc var firstName: String
var lastName: String
init(firstName: String,lastName: String) {
self.firstName = firstName
self.lastName = lastName
super.init()
}
}
let profile1 = Profile(firstName: "John", lastName: "Doe")
profile1.firstName // returns String "John"
profile1.value(forKey: "firstName") // returns Optional<Any>
let firstNameKey = \Profile.firstName
profile1[keyPath: firstNameKey] /* returns String "John" */
我的意思是我为什么要使用:
let firstNameKey = \Profile.firstName
profile1[keyPath: firstNameKey] /* returns String "John" */
代替:
profile1.firstName // returns String "John"
如果有人有一些代码示例/示例,那么如果他们可以使用 swift 来解释它,那就太好了(因为我的 Objective-C 不好)
最佳答案
您使用的示例不是使用 KVC 或 keyPath 本身的最佳情况。
在您使用协议(protocol) 时,keyPath 的真正力量,IMO 会释放出来。让我举个例子-
假设您有一个协议(protocol) Identifiable,它只有一个成员 - id。符合此要求的每个类型都必须使用唯一标识它的 id 属性。
protocol Identifiable {
var id: Int { get }
}
struct Person: Identifiable {
var id: Int
var name: String
}
在这里,具有成员 id 的 Person 类型听起来不太好。考虑另一个 -
struct Book: Identifiable {
var id: Int
var title: String
var author: String
}
在这里,一本书也可以通过 id 来唯一标识,但这听起来不太好。
这就是 keyPath 发挥作用的地方。
你可以在一个协议(protocol)中定义一些名字的成员,然后让一致的类型为那个特定的协议(protocol)成员写下他们自己的名字。符合类型可以使用 keyPath 映射或告诉编译器它们的特定成员是协议(protocol)内部成员的替换。
protocol Identifiable {
associatedtype ID
static var id: WritableKeyPath<Self,ID> { get }
}
struct Person: Identifiable {
static var id = \Person.socialSecurityNumber
var socialSecurityNumber: Int
var name: String
}
struct Book: Identifiable {
static var id = \Book.isbn
var isbn: String
var title: String
var author: String
}
func printID<T: Identifiable>(aType: T) {
print(aType[keyPath: T.id])
}
printID(aType: Person(socialSecurityNumber: 1234, name: "Shubham Bakshi"))
printID(aType: Book(isbn: "qwertyui", title: "The Theory of Everything", author: "Stephen W. Hawking"))
作为一个附加优势,您的符合类型可以具有任何类型的 id、String、Int 而不是 Int 仅(与之前的情况相同)
如果你只想给 id 一个特定的类型,比如 Int,你可以用这个替换我们协议(protocol)的定义 -
protocol Identifiable {
static var id: WritableKeyPath<Self,Int> { get }
}
这将强制符合类型使用 Int 作为它们的 id 替代品。
关于swift - KVC的优势,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56166096/
假设我想像这样访问散列的值:munsters={"Herman"=>{"age"=>32,"gender"=>"male"},"Lily"=>{"age"=>30,"gender"=>"female"},"Grandpa"=>{"age"=>402,"gender"=>"male"},"Eddie"=>{"age"=>10,"gender"=>"male"},"Marilyn"=>{"age"=>23,"gender"=>"female"}}我可以使用带有两个参数的#each:munsters.eachdo|key,value|puts"#{name}isa#{value["age"]
假设如下:defcreate_new_saltself.salt=self.object_id.to_s+rand.to_send为什么使用“self”更好。而不是实例变量“@salt”? 最佳答案 如果已定义,使用self.salt=将导致使用salt=方法。这对于确保使用salt=方法内的任何错误检查/转换很有用。然而,这意味着必须有一个明确的salt=方法(例如,可能由attr_accessor创建),这不一定是个好主意。总结:如果你有一个自定义的salt=方法,使用self.salt=;使用@salt=如果你确切地知道你想要
按照目前的情况,这个问题不适合我们的问答形式。我们希望答案得到事实、引用或专业知识的支持,但这个问题可能会引发辩论、争论、投票或扩展讨论。如果您觉得这个问题可以改进并可能重新打开,visitthehelpcenter指导。关闭10年前。你能给我一些值得使用rubinius的例子吗,比如这篇文章:http://yehudakatz.com/2009/08/31/simplifying-rails-block-helpers-with-a-side-of-rubinius/
关闭。这个问题不符合StackOverflowguidelines.它目前不接受答案。我们不允许提问寻求书籍、工具、软件库等的推荐。您可以编辑问题,以便用事实和引用来回答。关闭2年前。Improvethisquestion我注意到很多人更喜欢Mocha而不是RSpec的内置模拟框架。有人可以解释Mocha或任何替代方案相对于内置模拟框架的RSpec的优势吗?
什么时候使用Ruby的StringIO而不是只使用String是合适的?我想我理解它们之间的根本区别,正如“Whatisruby'sStringIOclassreally?”所强调的那样,StringIO使人们能够以面向流的方式从String读取和写入。但这实际上意味着什么?当简单地使用String不会真正削减它时,使用StringIO的实际用途的一个很好的例子是什么? 最佳答案 基本上,它使字符串看起来像一个IO对象,因此得名StringIO。StringIO类具有read和write方法,因此它可以传递给设计用于从文件或套接字读
我对nodeJS和可以在服务器上运行JS的想法很感兴趣,所以想知道是否有人有一些示例或可以解释nodeJS的潜力(站点上的文档不是大) 最佳答案 我现在正在用nodejs编写一个应用程序,我可以说最大的优势之一就是性能。您可以使用像mongoDB这样的文档数据库,并且您将拥有一个turbo应用程序。有一个Web框架,例如SinitraforRuby,即ExpressJS,它使用起来非常简单,并且非常适合小型应用程序。http://expressjs.com/对于数据库,mongoDB使用起来非常简单并且与javascript配合得很
CORS和跨域消息在我看来是一样的:它们允许跨域通信。是否有任何理由使用一个与另一个? 最佳答案 CORS用于ajax请求或flash通常不允许的flash请求。例如,如果域x没有跨域策略,你通过flash从那里检索一个mp3文件进行播放,flash将不允许你读取mp3文件的id3标签。对于ajax,如果目标服务器没有允许您的域发出请求的跨域策略,您将无法发出请求。跨域消息传递允许您与来自不同来源的文档中的iframe进行通信。例如,如果您有youtube视频iframe,您可以向该iframe传递一条消息以更改音量。通常无法进行通
浏览互联网,我发现了新的AmpleSDKJavaScript框架。来自他们的aboutsection:AmpleSDKisastandard-basedcross-browserJavaScriptGUIFrameworkforbuildingRichInternetApplications.ItemploysXMLtechnologies(suchasXUL,SVGorHTML5)forUIlayout,CSSforUIstyleandJavaScriptforapplicationlogic.Itequalizesbrowsersandbringstechnologiessuppo
替代标题:“为什么这么多流行的JavaScript库使用伪类继承而不是函数继承(工厂函数)?”JavaScript:TheGoodParts建议使用工厂函数,以便您获得方法和属性的真正隐私。这是有道理的,所以我想知道为什么这么多现代JS库仍然使用伪类继承(使用new关键字)。与工厂功能相比,走这条路有一些技术优势吗?如果不是,是否只是一种风格选择?编辑:这不是基于意见的帖子。我不是在问哪个更好,我是在问伪经典继承相对于函数式继承有哪些技术优势,以了解为什么有人会选择这种风格。编辑2:我可以看到伪经典的几个优点:当您console.log一个原型(prototype)的实例时,它会向您显
我正在使用immutability-helper对状态数据进行CRUD操作,想知道我是否应该始终使用$splice来删除数据,还是可以使用filter(因为它没有破坏性)?例如,假设我有一个对象数组:todos=[{id:1,body:"eat"},{id:2,body:"drink"},{id:3,body:"sleep"},{id:4,body:"run"}]给定一个项目ID,我可以通过两种方式删除它:一个。找到它的index并使用$splice:index=todos.findIndex((t)=>{return(t.id===id)});newtodos=update(todo