import Foundation
/*定义一个类层次作为例子******************************************************/
//第一个代码片段定义了一个新的基础类 MediaItem 。这个类为任何出现在数字媒体库的媒体项提供基础功能
class MediaItem {
var name: String
init(name: String) {
self.name = name
}
}
//下一个代码段定义了 MediaItem 的两个子类。第一个子类 Movie 封装了与电影相关的额外信息,在父类(或 者说基类)的基础上增加了一个 director (导演)属性,和相应的初始化器。第二个子类 Song,在父类的基 础上增加了一个 artist (艺术家)属性
class Movie: MediaItem {
var director: String
init(name: String,director: String) {
self.director = director
super.init(name: name)
}
}
class Song: MediaItem {
var artist: String
init(name: String,artist: String) {
self.artist = artist
super.init(name: name)
}
}
//最后一个代码段创建了一个数组常量 library,包含两个 Movie 实例和三个 Song 实例。 library 的类型是在 它被初始化时根据它数组中所包含的内容推断来的。
let aa = Song(name: "Blue Suede Shoes",artist: "Elvis Presley")
let library: [AnyObject] = [
Movie(name: "Casablanca",director: "Michael Curtiz"),
Song(name: "Blue Suede Shoes",artist: "Elvis Presley"),
Movie(name: "Citizen Kane",director: "Orson Welles"),
Song(name: "The One And Only",artist: "Chesney Hawkes"),
Song(name: "Never Gonna Give You Up",artist: "Rick Astley")
]
// the type of "library" is inferred to be [MediaItem]
/*检查类型******************************************************/
var movieCount = 0
var songCount = 0
for item in library {
if item is Movie {
movieCount++
} else if item is Song {
songCount++
}
}
print("Media library contains \(movieCount) movies and \(songCount) songs")
// prints "Media library contains 2 movies and 3 songs"
/*向下转型******************************************************/
for item in library {
if let movie = item as? Movie {
print("Movie: '\(movie.name)',dir. \(movie.director)")
} else if let song = item as? Song {
print("Song: '\(song.name)',by \(song.artist)")
}
}
// Movie: 'Casablanca',dir. Michael Curtiz
// Song: 'Blue Suede Shoes',by Elvis Presley
// Movie: 'Citizen Kane',dir. Orson Welles
// Song: 'The One And Only',by Chesney Hawkes
// Song: 'Never Gonna Give You Up',by Rick Astley
/*Any和AnyObject的类型转换******************************************************/
//Swift为不确定类型提供了两种特殊类型别名:
//? 可以代表任何class类型的实例。
//? 可以表示任何类型,包括方法类型(function types)。
let someObjects: [AnyObject] = [
Movie(name: "2001: A Space Odyssey",director: "Stanley Kubrick"),
Movie(name: "Moon",director: "Duncan Jones"),
Movie(name: "Alien",director: "Ridley Scott")
]
//因为知道这个数组只包含 Movie 实例,你可以直接用( as! )下转并解包到不可选的 Movie 类型:
for object in someObjects {
let movie = object as! Movie
print("Movie: '\(movie.name)',dir. \(movie.director)")
}
//为了变为一个更短的形式,下转 someObjects 数组为 [Movie] 类型来代替下转数组中每一项的方式。
for movie in someObjects as! [Movie] {
print("Movie: '\(movie.name)',dir. \(movie.director)")
}
// Movie: '2001: A Space Odyssey',dir. Stanley Kubrick
// Movie: 'Moon',dir. Duncan Jones
// Movie: 'Alien',dir. Ridley Scott
//这里有个示例,使用 Any 类型来和混合的不同类型一起工作,包括方法类型和非 class 类型。它创建了一个 可以存储 Any 类型的数组 things 。
var things = [Any]()
things.append(0)
things.append(0.0)
things.append(42)
things.append(3.14159)
things.append("hello")
things.append((3.0,5.0))
things.append(Movie(name: "Ghostbusters",director: "Ivan Reitman"))
things.append({ (name: String) -> String in "Hello,\(name)" })
for thing in things {
switch thing {
case 0 as Int:
print("zero as an Int")
case 0 as Double:
print("zero as a Double")
case let someInt as Int:
print("an integer value of \(someInt)")
case let someDouble as Double where someDouble > 0:
print("a positive double value of \(someDouble)")
case is Double:
print("some other double value that I don't want to print")
case let someString as String:
print("a string value of \"\(someString)\"")
case let (x,y) as (Double,Double):
print("an (x,y) point at \(x),\(y)")
case let movie as Movie:
print("a movie called '\(movie.name)',dir. \(movie.director)")
case let stringConverter as String -> String:
print(stringConverter("Michael"))
default:
print("something else")
}
}
// zero as an Int
// zero as a Double
// an integer value of 42
// a positive double value of 3.14159
// a string value of "hello"
// an (x,y) point at 3.0,5.0
// a movie called 'Ghostbusters',dir. Ivan Reitman
// Hello,Michael