我在 Swift 中有一个特定的类,我想限制扩展的创建。我尝试添加
final
关键字,但它不限制扩展:
final class MyTest {
func testFunc() {}
}
extension MyTest {
func testFunc2() {}
}
let test = MyTest()
test.testFunc2()
这可能吗?
您无法阻止某人向您的班级添加扩展。就像您无法阻止其他开发人员编写使用您的类的函数一样。
修饰符仅防止子类化。其他开发人员始终能够添加扩展。final
恕我直言,事实并非如此。
我们来看看这堂课
final class Person {
private let name: String
func tellName() -> String { return "I am \(name)" }
init(name: String) {
self.name = name
}
}
现在另一个开发人员可以编写(到另一个源文件中)这个函数
func presentAndTellName(person: Person) {
print("Hello everybody! \(person.tellName())")
}
这在其他几种不支持扩展的编程语言中是可能的。嗯,这基本上就是有多少种编程语言可以工作,这也是我们拥有访问控制(私有、公共……)的原因之一。
另一个开发人员实际上无法使用我们类的
private
属性/方法(除非它可以访问我们的源文件)。他也无法向 Person
添加属性,因为它是一个标记为 final
的类,因此子类化是禁止的。他只能编写使用它的代码。
我们都同意这个吧?
然而,编写一个接受参数并仅对该参数起作用的函数有时很难看。函数应该是一个方法,参数值应该是实例。
所以我们使用扩展来转换它
func presentAndTellName(person: Person) {
print("Hello everybody! \(person.tellName())")
}
进入这个
extension Person {
func presentAndTellName() {
print("Hello everybody! \(self.tellName())")
}
}
这只是编写“相同逻辑”并使其在 OOP 语法糖中可用的一种方式。 现在不用写这个了
presentAndTellName(person)
我们可以写这个
person.presentAndTellName()
将您的资料设为私密
private
。这样其他开发人员将无法在他们的扩展中使用它们。
让我们再看看我们的 Person 类。
class Person {
private let name: String
func tellName() -> String { return "I am \(name)" }
init(name: String) {
self.name = name
}
}
name
属性是市场私有的,因此
没有办法,外部函数或扩展将能够直接访问它。 等等,协议怎么样?
事实上给出了这个协议
protocol Runner {
func run()
}
我们可以将其归为我们不拥有的类
extension Person: Runner {
func run() { print("🏃") }
}
class MyClass {
private var privateVariable = "Hello, private!"
}
extension MyClass {
func accessPrivateVariable() -> String? {
return withUnsafePointer(to: &privateVariable) {
$0.withMemoryRebound(to: String.self, capacity: 1) {
$0.pointee
}
}
}
}
let myObject = MyClass()
if let value = myObject.accessPrivateVariable() {
print(value)
}