在Swift类中,我们可以使用class function
来创建预设实例。像下面的日历示例:
let calender = NSCalendar.currentCalendar()
这将具有与此类似的模式:
class SomeClass {
var attribute : String
init(value:String) {
attribute = value
}
class func testClass() -> SomeClass {
return SomeClass(value: "test")
}
}
let test = SomeClass.testClass()
但显然没有结构中的类函数。 Xcode建议使用static
代替。这非常接近单身模式。
struct SomeStruct {
var attribute : String
init(value:String) {
attribute = value
}
static var testStruct = SomeStruct(value: "test")
}
单身人士模式
class Singleton {
static let shared = Singleton()
private init() {
}
}
因为结构是值类型,所以这是一个使用预设值初始化结构的好方法。如果不行,那么正确的方法是什么?
答案 0 :(得分:2)
结构类型的等效class func
为static func
:
static func testStruct() -> SomeStruct {
return SomeStruct(value: "foo")
}
和静态属性(“singleton-pattern”)的工作方式相同 同时使用类和结构类型:
static let singleStruct = SomeStruct(value: "foo")
testStruct()
为每次调用创建一个值,而singleStruct
创建一次值(在第一次调用时)。
在大多数情况下,因为结构不会产生任何影响
价值类型。如果创建静态属性有优势
价值是“昂贵的”。另外,正如@Lance在评论中注意到的那样,
Apple经常使用此模式,例如CGRect.zero
。
但是,如果struct具有属性,则会有所不同 是引用类型(或指向非托管内存的指针)。这是一个例子:
class MyClass {
var attribute : String
init(value : String) {
attribute = value
}
}
struct SomeStruct {
var ptr : MyClass
init(value : String) {
ptr = MyClass(value: value)
}
static func testStruct() -> SomeStruct {
return SomeStruct(value: "foo")
}
static let singleStruct = SomeStruct(value: "foo")
}
使用静态功能:
let test1 = SomeStruct.testStruct()
print(test1.ptr.attribute) // foo
let test2 = SomeStruct.testStruct()
test2.ptr.attribute = "bar"
print(test1.ptr.attribute) // foo
此处test1
和test2
是单独的值,我们得到预期的值
输出
使用静态属性:
let test1 = SomeStruct.singleStruct
print(test1.ptr.attribute) // foo
let test2 = SomeStruct.singleStruct
test2.ptr.attribute = "bar"
print(test1.ptr.attribute) // bar <--- What?
此处,test1
和test2
设置为从中返回的相同值
静态属性。更改test2.ptr
不会改变 test2
,
导致test1.ptr.attribute
请参阅Friday Q&A 2015-04-17: Let's Build Swift.Array,了解有关如何解决此问题的有趣文章。
顺便说一下,static
也可以与类类型一起使用,static
是class final
的快捷方式:无法覆盖的类型方法
在子类中。由于它没有继承结构类型
感觉结构类型的类型方法被写为static
。