可选值
如果一个值可能为nil
,那么这个值就是可选类型,用?标识
var a1 : String?
a1 = "可选类型"
可选类型不能直接使用,必须进行强制解包 用!强制解包,对nil强制解包会早成崩溃
print(a1!)
print(a1 ?? "强制解包,如果为nil,双引号内是默认值")
用if let
对可选值进行有值绑定
if let image = UIImage(contentsOfFile: "MyImage.png") {
// loaded the image successfully
} else {
// could not load the image
}
可变与不可变
let
var
let maximumNumberOfLoginAttempts = 10
var currentLoginAttempt = 0
指明类型
let name: String = "我是名字内容"
布尔值:在Swift中的bool值是true
和false
,而不是OC中的YES和NO
let onSaleInferred = true
let onSaleExplicit: Bool = false
打印输出:在Swift中的打印输出使用的是print,也可以兼容使用NSlog
print(10)
//将值转化为字符串,需要将值写在括号中并在前面加上斜杠”\”
print("this is \(10)")
//格式化打印
print(String.init(format: "%@ %@ %.2f", "asd","dd",10.123))
print("this is \(String.init(format: "%@ %@ %.2f", "asd","dd",10.123))")
// 也可以使用
NSLog("this is %@ %.f", "asd","1.12")
字符串
var emptyString = "" // 空字符串字面量
var anotherEmptyString = String() // 初始化方法
// 其它的初始化方法…
判断是否为空
if emptyString.isEmpty {
print("Nothing to see here")
}
// 字符串拼接的拼接可以使用”+”来完成
let string1 = "hello"
let string2 = " there"
var welcome = string1 + string2
数组
//创建数组
var shoppingList: [String] = ["Eggs", "Milk"]
shoppingList[0...1] = ["Bananas", "Apples"]
//判断数组是否为空
if shoppingList.isEmpty{
print("kong")
}else{
print("feikong")
}
//添加数据
shoppingList += ["haha"]//添加数据
//遍历
for item in shoppingList{
print(item)
}
for (index, value) in shoppingList.enumerated() {
print("Item \(String(index + 1)): \(value)")
}
// 包含任意类型的数组
var array2: [Any] = [Any]()
array2.append(1)
array2.append(2.0)
array2.append([3,4])
array2.append("asdasd")
array2.append(["key1":"value1","key2":"value2"])
array2.append(sunClass2)
for iterm in array2{
print("this is \(iterm)")
}
Any:可以表示任何类型,包括函数类型
AnyObject:可以表示任何类类型的实例
字典
// 字典的创建
var airports: [String: String] = ["key1": "value1", "key2": "value2"]
//字典中某个value的访问
let theValue = airports["key1"]
print(theValue ?? "你打印了一个空字符串")
//增加
airports["key3"] = "value3"
//更新
airports.updateValue("value22222222", forKey: "key2")
//删除
airports.removeValue(forKey: "key1")
属性的写法
class Shape {
var name = "shape"
var string:String{
set{
}
get{
return "string"
}
}
}
Swift中的只读属性
var redOnly:String{
get{
return "asd"
}
}//get 和括号都可以去掉
默认strong nonatomic, 用weak申明
class Shape {
var name = "shape"
weak var delegate: UITextFieldDelegate?
}
对外readonly对内readwrite
private(set) var property: Int
定义类变量
通过static定义的类变量无法在子类重写,通过class定义的类变量则可在子类重写。
class Aclass {
static var storedTypeProperty = "Some value."
static var computedTypeProperty: Int {
return 1
}
class var overrideableComputedTypeProperty: Int {
return 107
}
}
解决闭包中循环引用
[unowned 捕获对象]或者 [weak 捕获对象]
__weak typeof(self) weakSelf = self;
self.block = ^{
__strong typeof(self) strongSelf = weakSelf;
[strongSelf doSomething];
};
self.closure = { [unowned self] in
self.doSomething()
}
类型判断
is
关键词
相当于OC的isKindofClass:
单例写法
class singletonClass {
static let sharedInstance = singletonClass()
private init() {} // 这就阻止其他对象使用这个类的默认的'()'初始化方法
}
lazy写法
class ClassA {
lazy var str: String = {
let str = "Hello"
print("只在首次访问输出")
return str
}()
}
if写法语句里的条件不再需要使用()包裹了。Swift里没有OC的非零即真的说法,判断条件要明确
let number = 23
if number < 10 {
print("The number is small")
}
for写法
for index in 1...5 {
print(index)
}
区间运算符
•闭区间[a,b]-------> a...b•前闭后开区间[a,b)------->a..<b
闭区间运算符(a...b)定义一个包含从a到b(包括a和b)的所有值的区间
半闭区间(a..b)定义一个从a到b但不包括b的区间。 之所以称为半闭区间,是因为该区间包含第一个值而不包括最后的值。
元组遍历字典
let dictionary = ["firstName":"Mango","lastName":"Fang"]
for (key,value) in dictionary{
print(key+" "+value)
}
SWitch写法,无需breadk
下面这两种写法是等价的。
let character = "a"
switch character{
case "a":
print("A")
break
case "b":
print("B")
break
default: print("character")
let character = "a"
switch character{
case "a":
print("A")
case "b":
print("B")
default: print("character")
SWitch并列处理
switch some value to consider {
case value 1,value 2:
statements
}
在OC中,Swtich只支持int类型,char类型作为匹配。
if ([cardName isEqualToString:@"Six"]) {
[self setValue:6];
} else if ([cardName isEqualToString:@"Seven"]) {
[self setValue:7];
} else if ([cardName isEqualToString:@"Eight"]) {
[self setValue:8];
} else if ([cardName isEqualToString:@"Nine"]) {
[self setValue:9];
}
switch carName{
case "Six":
self.vaule = 6
case "Seven":
self.vaule = 7
case "Eight":
self.vaule = 8
case "Night":
self.vaule = 9
}
函数(类方法与实例方法)写法
1. 通过func关键词定义函数
2. 返回值在->关键词后标注
class func blackColor() -> UIColor
//类方法, 通过 class func 关键词声明
func addSubview(_ view: UIView)
//实例方法
如果你调用的方法是没有参数的,调用时也得加上在点方法后也得加上括号
myTableView.layoutIfNeeded()
协议
protocol SampleProtocol
{
func someMethod()
}
class AnotherClass: SomeSuperClass, SampleProtocol
{
func someMethod() {}
}
代理写法 weak
protocol MyDelegate : class {
}
class MyClass {
weak var delegate : MyDelegate?
}
检测代理更优雅
以前我们要在Objective-C这样检查:
if (self.dataSource && [self.dataSource respondsToSelector:@selector(titleForSegmentAtIndex:)]) {
thisSegmentTitle = [self.dataSource titleForSegmentAtIndex:index];
}
在Swift中,非常的优雅简洁。
if let thisSementTitle = dataSource?.titleFroSegmentAtIndex?(index){
}
在Swift中,protocol变得更加强大,灵活:
class,enum,structure都可以遵守协议。Extension也能遵守协议。利用它,我们不需要继承,也能够让系统的类也遵循我们的协议。例如:
protocol myProtocol {func hello() -> String}
extension String: myProtocol{
func hello() -> String {
return "hello world!"
}
}
扩展(Extension),相对于OC来说没有名字
extension SomeType {
func hello(){}
}
id
与AnyObject
在Swift中,没有id类型,Swift用一个名字叫AnyObject的protocol来代表任意类型的对象。
id myObject = [[UITableViewCell alloc]init];
var myObject: AnyObject = UITableViewCell()
我们知道id的类型直到运行时才能被确定,如果我们向一个对象发送一条不能响应的消息,就会导致crash。
我们可以利用Swift的语法特性来防止这样的错误:
myObject.method?()
如果myObject没有这个方法,就不会执行,类似检查delegate是否有实现代理方法。
在Swift中,在AnyObject上获取的property都是optional
的。
闭包
OC中的block在Swift中无缝地转换为闭包。函数实际上也是一种特殊的闭包。
void (^completionBlock)(NSData *) = ^(NSData *data) {
// ...
}
let completionBlock: (Data) -> Void = { data in
// ...
}
错误处理
OC写法
NSFileManager *fileManager = [NSFileManager defaultManager];
NSURL *URL = [NSURL fileURLWithPath:@"/path/to/file"];
NSError *error = nil;
BOOL success = [fileManager removeItemAtURL:URL error:&error];
if (!success) {
NSLog(@"Error: %@", error.domain);
}
Swift写法
let fileManager = FileManager.default
let URL = NSURL.fileURL(withPath: "/path/to/file")
do {
try fileManager.removeItem(at: URL)
} catch let error as NSError {
print("Error: \(error.domain)")
}
尾随闭包简写
func someFunctionThatTakesAClosure(closure: () -> Void) {
// 函数体部分
}
//不使用尾随闭包进行函数调用
someFunctionThatTakesAClosure(closure: {
// 闭包主体部分
})
//使用尾随闭包进行函数调用
someFunctionThatTakesAClosure() {
// 闭包主体部分
}
泛型运用
static func httpPost<T:CKKBaseModel>(url: String, pamas: [String: AnyObject]? = nil, success:((T) -> Void)? = nil, successList:((Array<T>) -> Void)? = nil, failure:((String) -> Void)? = nil) {
}
混编注意
写Swift类可以继承自OC类,但是如果要写一个OC类就不能继承自 Swift 类。
为了在 Objective-C 中可以访问并使用,Swift 类必须是一个 Objective-C 类的子类,或者被标记为@objc。