1、在 objective-c 中, 我们必须将所要用的标头档在一个 .h 档中 import 它,并在.h档中宣告全域变数或是 storyboard 新增的元件,然后在 .m 档中 import 这个 .h 档,如此一来才能在 .m 中使用刚刚在.h 宣告的变数以及其标头档所包含的 function,但在 swift 中我们只需要一个档案去控制一个 view,而会参考到的标头档以及所用到的全域变数则全部放在这个档案中。
2、swift 不用分号来区隔两行 code, 除非两行 code 写在同一行
a = b + c
x = y / z
a = b + c ; x = y / z
3、swift 没有指标 ,因为指标可以直接存取记忆体,swift注重安全性,避免非法记忆体存取造成crash,所以并没有指标
4、在swift 当中 , 宣告变数用 var , 宣告常数用 let 范例程式
5、在swift 当中用 printfln 来显示字串 , objective-c 则使用 NSLog 范例程式
objective-c:
int a = 5;
NSLog(@" a = %i" , a);
swift:
var a : Int = 5
printfln("\(a)")
以上两段程式码做的是同样的事 将Int型态的变数a以string 的形式显示出来 swift用一个" () " ,括弧内放欲显示的变数
6、swift 和 objective-c 在宣告变数常数上的不同
objective-c:
UITableView *myTableView = [[UITableView alloc] initWithFrame:CGRectZero style:UITableViewStyleGrouped];
swift:
let myTableView: UITableView = UITableView(frame: CGRectZero, style: .Grouped)
swift 在设定某物件的属性时几乎不用中括弧 []
以上两段程式码做的是同样的事宣告一个资料型态为 UITableView 的常数 myTableView,并给予他初值
7、swift 和 objective-c 在定义 function 上的不同 (范例专案 Kotel 中的 HttpController.swift)
objective-c:
- (NSDate *)dueDateForProject:(id *)sender;
swift:
func dueDateForProject(sender: anyobject!) -> NSDate!
以上两段程式码做的是同样的事 ,function 名称为 dueDateForProject , 参数型态为 id/anyobject ,回传值型态为 NSDate
swift 的 anyobject 型态 = objective-c 的 id 型态
8、swift 的 optional 范例程式
第6行: 宣告变数c时一口咬定他之后会有值
第9行 : 一开就强制认为c之后一定会有值,所以此处用c运算时直接使用
第17行 : 一开始宣告变数z时我们不确定,之后使用到z时他会不会有值,所以使用?
第20行 : 在此处的运算需要用到变数z所以不管z是否有值我们都必须用!去强制拆封取得z的值
所幸我们在第21行有给变数z一个值,若是没有给z一个值,在第23行强制拆封要使用却没有值
有可能造成crash
8、swift 和 objective-c 在 closure(闭包)的不同 范例程式
objective-c:
void (^completionBlock)(NSData *, NSError *) = ^(NSData *data, NSError *error) {/* ... */}
swift:
let completionBlock: (NSData, NSError) -> Void = {data, error in /* ... */}
以上两段程式码做的是同样的事,completionBlock 为 closure 名称,void 为回传值型态,data 和 error 为要传入的参数名称,而 NSData 和 NSError 为传入的参数型态
范例专案 Kotel
step1 看 HotelSingle.swift
一开始先建立 HotelSingle 类别,类别中建立了各种属性,像是 name、rank、address 等,目的主要是协助以 Dictionary 型别取得 JSON 资料各种栏位像是 旅宿名称、乡镇、地址 等。
第16~26行:取得Dictionary型别的JSON资料,参数dict代表每家旅馆的详细资料
这个档案包含一个 Httpprotocol 协议和 HttpController 类别,HttpController 类别中的 onSearch() 方法以非同步的方式取得指定网址的 JSON 资料 ,再透过 Httpprotocol 协议的 didReceiveResults 方法将资料传递给 myTableViewController
第3~5行:建立Httpprotocol协议,并在协议中定义didReceiveResult()方法取得第34行委派传送的阵列资料
第9行:建立委派物件delegate
第11~31行:建立onSearch方法,以非同步取得指定网址的JSON资料
第23~28行:连线若是成功,将读取的资料放进array,并透过delegate物件执行委派,也就是执行委派的didReceiveResults方法,将array传出去
step3 看 myTableViewController.swift
这个档案接受 JSON 资料
第3行 : 继承Httpprotocol协议
第23~28行: 实作委派取得所有资料
第28行 : HttpController委託myTableViewController 代理
第29行 : 输入我们欲使用的JSON资料网址
范例专案 Kotel 中的 secondViewController.swift
1、在 swift 中若是要使用地图相关功能必须 import MapKit 若是要使用定位相关功能必须 import CoreLocation
2、地址转经纬度
Code 裡的 MapKit View 元件没办法直接用地址字串去定位,但资料来源只有地址的话我们就必须把地址转成经纬度,在使用经纬度资料在地图上找到我们要的位置
地址转经纬度函式
let geoCoder = CLGeocoder()
geoCoder.geocodeAddressString("这里放欲转换的地址" as! String, completionHandler: {
(placemarks:[AnyObject]!,error:NSError!) -> Void in let placemark = placemarks[0] as! CLPlacemark
})
3、用大头针在地图上标示位置 范例程式
第38行: 宣告地图中心点
第39行:宣告地图缩放比例
第40行:宣告地图中心点,设定地图缩放比例
第41行:设定地图中心点
第43~49行: 在目标位置插上大头针做标示
第43行:新增一个大头针
第45行:设定大头针的座标位址
第46~47行:设定当点击大头针时出现的title以及subtitle
第49行: 把大头针插在地图上
step1 开启终端机输入
sudo gem install cocoapods
这边会等蛮久的,一开始会以为没有反应,但不要关掉重开,等待即可看到" gems installed "代表安装完成
step2 终端机输入
cd 这里输入你的目标专案资料夹路径
这个专案资料夹路径就是欲使用cocoapods的专案所在的资料夹
step3 在专案资料夹内建立一个文字档 Podfile.txt,Podfile.txt 裡面输入要用的函式库以及其版本 一定要叫 Podfile,不可以自己任意取名,建立好之后一定要将副档名删掉
platform :ios, '7.0'
pod "AFNetworking", "~> 2.0"
pod 'Parse', '~> 1.7.1'
pod 'ParseUI', '~> 1.1.3'
step4 终端机输入
pod install
就会开始下载 1.7.1 版本的 Parse 函式库,1.1.3 版本的 ParseUI 函式库以及2.0版本的 AFNetworking 函式库并安装看到终端机显示 Sending stats 代表安装成功,安装成功后资料夹内会出现一个 Podfile.lock 档案,它的作用是纪录以下载的函式库以及其版本还会出现一个新的 专案名.xcworkspace 档,跟原本的 .xcxcodeproj 长得很像,但他是白色的 之后就用这个档案撰写程式。
范例专案 parsePracticeSwift
Parse 是以 objective-c 所撰写的,要在 swift 专案中使用必须先做好设定
step1 安装 cocoapods 以及 Parse 函式库以及 ParseUI 函式库(参照第5点)Podfile 档案内输入以下文字
pod 'Parse', '~> 1.7.1'
pod 'ParseUI', '~> 1.1.3'
step2 在 swift 专案中新增一个 objective-c 档案模板来设置一个 objective-c Bridging Header 假设我们帮新增的 objective-c 档案取名叫做 new,则会自动新增两个档案: new.m 和 new-Bridging-Header.h, new.m我们不会用到可以删掉,new-Bridging-Header.h 在 Framework 资料夹目录下然后开启 new-Bridging-Header.h ,在裡面撰写以下程式码
#import <Parse/Parse.h>
#import <ParseUI/ParseUI.h>
#import <Bolts/Bolts.h>
我们就可以在这个专案使用跟 Parse 有关的各种函式了
step3 在 Parse 中,每个 APP 都有其专属的 APP Key,我们会需要裡面的 Application ID 和 Client Key 这就像帐号密码一样,确保我们的专案读取到正确的资料也添增 APP 的安全性 我们到专案中 AppDelegate.swift 中找到以下程式码并输入第2行程式码
func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?) -> Bool {
Parse.setApplicationId( "这里输入Application ID" , clientKey: "这里输入Client Key" )
return true
}
接著执行看看,若是 sucessed 代表专案与 Parse 以及 cocoapods 已经连接成功
step4 使用存在 Parse 的资料
var query:PFQuery=PFQuery(className: "在Parse中建立的class名称")
ParseUI 函式库包含许多从内建 controller 延伸功能的 controller
PFQueryTableViewController