在 Swift 中:Array VS NSArray VS [AnyObject] 之间的区别
in Swift: Difference between Array VS NSArray VS [AnyObject]
正如标题所说,Array vs NSArray vs [AnyObject] 有什么区别?
此外,最推荐的解决方法是什么。我的意思是推荐,什么是最简单的实现。谢谢。
Array
是一个 Swift 构造和泛型结构,这意味着它可以是任何特定类型(Int、String、AnyObject 等)的数组
[T]
是 Array<T>
的语法糖
AnyObject
是任何 class 的对象,包括 Objective-C classes.
NSArray
是一个 Objective-C 构造,它可以容纳任何 Objective-C 对象并且透明地映射到 Array<AnyObject>
和从 Array<AnyObject>
映射
Array
是一个结构,因此它是Swift中的值类型。
NSArray
是不可变的Objective Cclass,因此它是[=38=中的引用类型 ] 并桥接到 Array<AnyObject>
。
NSMutableArray
是 NSArray
的可变子 class。
var arr : NSMutableArray = ["Pencil", "Eraser", "Notebook"]
var barr = ["Pencil", "Eraser", "Notebook"]
func foo (var a : Array<String>)
{
a[2] = "Pen"
}
func bar (a : NSMutableArray)
{
a[2] = "Pen"
}
foo(barr)
bar(arr)
println (arr)
println (barr)
打印:
(
Pencil,
Eraser,
Pen
)
[Pencil, Eraser, Notebook]
因为 foo
更改了 a
的本地值,而 bar
更改了引用。
如果您使用 let arr
而不是 var
与其他引用类型一样,它也会起作用。
使用 Krzak 答案,这是一个实际示例:
// Let´s create an Array as a struct showing alternative ways
var arrStruct = ["Pencil", "Eraser", "Notebook"]
// or var arrStruct: [String] = ["Pencil", "Eraser", "Notebook"]
// or var arrStruct: Array = ["Pencil", "Eraser", "Notebook"]
// or var arrStruct = Array(["Pencil", "Eraser", "Notebook"])
// All this alternative ways create an array as struct
// Now let´s create a function that modifies this array struct
func modifyArr(alternativeArr: [String])
// or func modify(alternativeArr: Array<String>)
{
alternativeArr[2] = "Pen" // compilation error
// This won´t work. In swift >= 3.0 all func parametes are a let variable,
// this means alternativeArr is defined as a let. What one has to do is
// create a local variable and copy the value.
var localAlternativeArr = alternativeArr
// or var localAlternativeArr: [String] = alternativeArr
// or var localAlternativeArr: Array = alternativeArr
// now we can change it.
localAlternativeArr[2] = "Pen"
print(localAlternativeArr) // ["Pencil", "Eraser", "Pen"]
print(alternativeArr) // ["Pencil", "Eraser", "Notebook"]
}
modifyArr(alternativeArr: arrStruct)
print(arrStruct) // ["Pencil", "Eraser", "Notebook"]
// Since the arrStruct is a struct every time we assign to another variable or
// pass it as a func argument a copy is made.
// Now let´s create as an NSMutableArray
var arrClass: NSMutableArray = ["Pencil", "Eraser", "Notebook"]
// or var arrStruct = NSMutableArray(array: ["Pencil", "Eraser", "Notebook"])
// All this create an NSMutableArray as a class
// Now let´s create a function that modifies this array struct
func modifyArr(alternativeArr: NSMutableArray)
{
alternativeArr[2] = "Pen"
print(alternativeArr)
// (
// Pencil,
// Eraser,
// Pen
// )
}
modifyArr(alternativeArr: arrClass)
print(arrClass)
// (
// Pencil,
// Eraser,
// Pen
// )
// Since the arrClass is a class everytime we assign to another variable or
// pass it as a func argument is passed by reference. Means that any change
// inside modifyArr is going to change the arrClass outside. The change
// is made in the same pointer.
添加到@Krzak 的出色回答,这就是为什么
print(NSArray().object(at: 1)) // Triggers an UnmanagedException
2018-11-09 11:38:08.798088-0600 AppName[38786:10497909] * 由于未捕获的异常终止应用程序 'NSRangeException',原因:'* -[__NSArray0 objectAtIndex:]:索引 1 超出空 NSArray 的范围'
和
print(Array<Int>()[1]) // Halts with "Thread 1: Fatal error: Index out of range"
这种对错误的不同处理方式帮助我理解了差异..... e
正如标题所说,Array vs NSArray vs [AnyObject] 有什么区别?
此外,最推荐的解决方法是什么。我的意思是推荐,什么是最简单的实现。谢谢。
Array
是一个 Swift 构造和泛型结构,这意味着它可以是任何特定类型(Int、String、AnyObject 等)的数组
[T]
是 Array<T>
AnyObject
是任何 class 的对象,包括 Objective-C classes.
NSArray
是一个 Objective-C 构造,它可以容纳任何 Objective-C 对象并且透明地映射到 Array<AnyObject>
Array<AnyObject>
映射
Array
是一个结构,因此它是Swift中的值类型。
NSArray
是不可变的Objective Cclass,因此它是[=38=中的引用类型 ] 并桥接到 Array<AnyObject>
。
NSMutableArray
是 NSArray
的可变子 class。
var arr : NSMutableArray = ["Pencil", "Eraser", "Notebook"]
var barr = ["Pencil", "Eraser", "Notebook"]
func foo (var a : Array<String>)
{
a[2] = "Pen"
}
func bar (a : NSMutableArray)
{
a[2] = "Pen"
}
foo(barr)
bar(arr)
println (arr)
println (barr)
打印:
(
Pencil,
Eraser,
Pen
)
[Pencil, Eraser, Notebook]
因为 foo
更改了 a
的本地值,而 bar
更改了引用。
如果您使用 let arr
而不是 var
与其他引用类型一样,它也会起作用。
使用 Krzak 答案,这是一个实际示例:
// Let´s create an Array as a struct showing alternative ways
var arrStruct = ["Pencil", "Eraser", "Notebook"]
// or var arrStruct: [String] = ["Pencil", "Eraser", "Notebook"]
// or var arrStruct: Array = ["Pencil", "Eraser", "Notebook"]
// or var arrStruct = Array(["Pencil", "Eraser", "Notebook"])
// All this alternative ways create an array as struct
// Now let´s create a function that modifies this array struct
func modifyArr(alternativeArr: [String])
// or func modify(alternativeArr: Array<String>)
{
alternativeArr[2] = "Pen" // compilation error
// This won´t work. In swift >= 3.0 all func parametes are a let variable,
// this means alternativeArr is defined as a let. What one has to do is
// create a local variable and copy the value.
var localAlternativeArr = alternativeArr
// or var localAlternativeArr: [String] = alternativeArr
// or var localAlternativeArr: Array = alternativeArr
// now we can change it.
localAlternativeArr[2] = "Pen"
print(localAlternativeArr) // ["Pencil", "Eraser", "Pen"]
print(alternativeArr) // ["Pencil", "Eraser", "Notebook"]
}
modifyArr(alternativeArr: arrStruct)
print(arrStruct) // ["Pencil", "Eraser", "Notebook"]
// Since the arrStruct is a struct every time we assign to another variable or
// pass it as a func argument a copy is made.
// Now let´s create as an NSMutableArray
var arrClass: NSMutableArray = ["Pencil", "Eraser", "Notebook"]
// or var arrStruct = NSMutableArray(array: ["Pencil", "Eraser", "Notebook"])
// All this create an NSMutableArray as a class
// Now let´s create a function that modifies this array struct
func modifyArr(alternativeArr: NSMutableArray)
{
alternativeArr[2] = "Pen"
print(alternativeArr)
// (
// Pencil,
// Eraser,
// Pen
// )
}
modifyArr(alternativeArr: arrClass)
print(arrClass)
// (
// Pencil,
// Eraser,
// Pen
// )
// Since the arrClass is a class everytime we assign to another variable or
// pass it as a func argument is passed by reference. Means that any change
// inside modifyArr is going to change the arrClass outside. The change
// is made in the same pointer.
添加到@Krzak 的出色回答,这就是为什么
print(NSArray().object(at: 1)) // Triggers an UnmanagedException
2018-11-09 11:38:08.798088-0600 AppName[38786:10497909] * 由于未捕获的异常终止应用程序 'NSRangeException',原因:'* -[__NSArray0 objectAtIndex:]:索引 1 超出空 NSArray 的范围'
和
print(Array<Int>()[1]) // Halts with "Thread 1: Fatal error: Index out of range"
这种对错误的不同处理方式帮助我理解了差异..... e