iOS開發(fā)中使用的類型
Foundation中的類型可以分為三類:
- NSInteger等,在C語言中嬉挡,枚舉類型钝鸽、字符型和各種整數(shù)的表示形式統(tǒng)一叫做標(biāo)量類型
- immutable類型,如:NSString等
- mutable類型庞钢,如:NSMutableString等
如果使用了Swift那么還需要了解Swift標(biāo)準(zhǔn)庫中的類型可分類為:
- 值類型拔恰,如struct,enum基括,tuple
- 引用類型颜懊,即class
OC中的基本類型例如NSString等都是使用的引用類型,而Swift中大多是使用的值類型
Swift的值類型與引用類型
- 在Swift中struct為值類型风皿,在此處值類型(Value Types)的定義為:每個(gè)實(shí)例都保留其數(shù)據(jù)的唯一副本(each instance keeps a unique copy of its data)
// Value type example
struct S { var data: Int = -1 }
var a = S()
var b = a // a is copied to b
a.data = 42 // Changes a, not b
print("\(a.data), \(b.data)") // prints "42, -1"
- 在Swift中class和引用類型(Reference Types)是一一對應(yīng)的關(guān)系河爹,定義為:實(shí)例共享數(shù)據(jù)的單個(gè)副本(each instance keeps a unique copy of its data)
// Reference type example
class C { var data: Int = -1 }
var x = C()
var y = x // x is copied to y
x.data = 42 // changes the instance referred to by x (and y)
print("\(x.data), \(y.data)") // prints "42, 42"
與OC中區(qū)分最大的是Swift的有值類型的存在,下面將僅討論Swift值類型與OC中的引用類型
可變與不可變類型
OC中可變與不可變使用mutable和immutable來表示桐款,而在Swift中使用let和var來表示咸这,但是Swift中關(guān)于可變與不可變的描述更加符合使用的直覺
// OC
// str所指向的內(nèi)存區(qū)域內(nèi)容是不可變的,但是str指向的位置是可變的
NSString *str = [[NSString alloc] init];
// 簡單類比一下C++
const char *str
// Swift
// str 指向的內(nèi)存區(qū)域的內(nèi)容是不可變的且str指向的位置是不可變的
let str = String("")
str.append("a") // 編譯錯(cuò)誤
str = "a" // 編譯錯(cuò)誤
// 簡單類比下C++
const char * const str
在函數(shù)傳參時(shí):
// case 1:
// Swift
func doSomething(str: String) {
// 編譯錯(cuò)誤
str = ""
}
// OC
-(void) doSomething: (NSString*)str
// 類比C++魔眨,指向的內(nèi)存區(qū)域和指針都是常量
void doSomething(const char * str)
// case 2:
func doSomething(str: inout S) {
// 編譯通過
str = ""
}
// OC
-(void) doSomething: (NSMutableString**)str
// 類比C++媳维,指向的內(nèi)存區(qū)域和指針都是變量
void doSomething(char **str)
OC中不可變類型的copy僅僅是增加對象的引用計(jì)數(shù),并將指針指向原來的內(nèi)存區(qū)域遏暴,這么做可以提高效率侄刽,減少內(nèi)存占用,Swift為了效率對值類型也有優(yōu)化(寫時(shí)復(fù)制):
var str = ""
// 此時(shí)str1和str指向同一塊內(nèi)存
var str1 = str
// 此時(shí)才會copy
// 修改str1后將會先開辟一塊新的內(nèi)存朋凉,將原來的內(nèi)容copy過去唠梨,然后再append
str1.append("a")
總結(jié)
我認(rèn)為,Swift把所有的基本類型定義為值類型是更加符合我們的使用習(xí)慣的侥啤,大多數(shù)情況下,我們更多的是在使用純函數(shù)茬故,我們不希望改變傳遞進(jìn)來的參數(shù)盖灸,但是要在OC中實(shí)現(xiàn)這個(gè)功能要時(shí)刻關(guān)注類型是否Mutable,而且還要關(guān)注指針的值是否可變磺芭,在Swift中一個(gè)inout關(guān)鍵字就對OC來說是好多種情況赁炎,而Swift直觀的用let和var就統(tǒng)一的表達(dá)了這些語義。