Swift Is Objective-C without the C, Period.

楼主: uranusjr (←這人是超級笨蛋)   2014-06-04 00:09:34
Blog post 原文
https://uranusjr.com/blog/post/57/swift-is-objective-c-without-the-c-period/
苹果在美国时间周一发表了新的程式语言 Swift,然后 Internet 就高潮了,突然冒
出一堆键盘语言专家(包括我自己)争先恐后发表自己的看法。或许因为每个人都有
自己不同的背景,而且 Objective-C 本身也不是很多人特别熟悉的语言,所以看法似
乎颇为分歧,甚至连原以已经在 OS X/iOS 界的工程师似乎也不是完全理解。这里是
一些我自己的想法,其中不少是针对我觉得大家对于 Swift、Objective-C、甚至苹果
本身的误解。
该从哪里开始呢?嗯…
SWIFT 是编译语言,但这不代表他不如你最喜欢的脚本语言
没错,Swift 有独立的编译器,而且需要被编译才能执行。但这不代表他比不上那个
脚本语言(请自行对号入座)。毕竟不管怎么说,绝大多数脚本语言的主流实作都会
在 runtime 时及时将源码编译为 bytecode 才交由直译器执行,而 Swift 的编译器
基于 LLVM(如同近期大多数的语言),与一般脚本语言在实务上的差异其实只有编译
是否自动而已。
不论你打算将 Swift 用于 iOS 或 OS X apps(目前除了这些大概 Swift 也没什么其
他用途),都需要对你的最终成品进行额外处理,例如打包、key signing(除非你不
上 App Store)等等。苹果在这部分的手续超级繁杂,一般而言都需要 IDE 辅助。既
然有 IDE 存在,编译这件事情造成的 overhead 其实很小。如果你看了 WWDC 展示的
Swift Playground,它及时反应源码修改的能力其实和直译器的差距没那么大。既然
这个步骤本身对开发流程影响不大,它就是加分了。编译还是能带来很多好处;以
Swift 而言,除了可以进行语法检查之外,还可以带来许多最佳化(尤其 Swift 使用
静态型别)。以苹果的定位,Swift 必须被用在效能吃重的场合,所以这很重要。
编译本身不是罪,苹果只是选择了适合 Swift 用途的路。但这只是实作。当然 Swift
目前看来似乎是 proprietary language,所以这个实作就是一切;不过就语言本身而
言,编译与否仍然不是很重要。但语言本身嘛…
SWIFT 应该没有大量借鉴你想的那个语言
Swift 本身有不少有趣的特点,让许多人开始讨论它究竟从什么语言借ㄔㄠ鉴ㄒㄧˊ
了什么概念。包括 Rust 的原设计者都有些想法。但这些想法还是有点偏差,甚至一
部份根本是错的。
很明显因为对程式语言历史毫无概念产生的错误(Generics 源自 C#?别闹了吧。)
就跳过,多数误解似乎还是源自于很多人(即使 Objective-C programmers)其实不
特别熟 Objective-C。可能是一厢情愿,不过我认为如果想理解 Swift 风格背后的
理由,必须先理解 Objective-C。
从 OBJECTIVE-C 物件到 SWIFT 物件
在 Swift 中,几乎所有的 object instances 都是以 reference 参照。没有指标。
这其实应该就是延续 Objective-C 的做法而已。所有的 Objective-C 物件都必须在
heap 上被 allocated,在程式码中永远是以指标参照:
// aString 指向一个在 heap 上被建立,形态是 NSString 的物件实例。
NSString *aString = [[NSString alloc] init];
这在 Swift 里就直接对应到物件参考:
// aString 指向一个(应该也是)在 heap 上被建立的 String 物件实例。
let aString = String()
当然,Objective-C 本身偶尔也会用到 pointer to a pointer。但通常是用来回传多
个值,或者作为 error-handling 的手段。Swift 可以把变量组成 tuple 轻松回传多
个值,所以这种需求其实不大。在真的有必要时,也有 inout 参数可以用。
由于 Objective-C 物件永远是用指标参照,所以 nil(空指标)就被用来代表物件不
存在。推到 Swift 上就是 optionals 了。当然语法本身肯定是有借ㄔㄠ鉴ㄒㄧˊ别
人,不过概念上还是很必然。
前面说“几乎”所有的 Swift 变量都是物件参考。例外就是 struct。这或许受到 C#
的用法影响,不过无论如何都很明显源自 C 的 structure。Objective-C 在很多地方
使用 struct 描述 POD,所以它有专属的 type 或许也很合理。
顺带一提,虽然文件好像都没有特别提,不过我个人猜测 Swift 的 error-handling
应该还是和 Objective-C 一样基于 return codes 和 error messages。由于使用同
样的 runtime(据苹果说),Swift 的 exceptions 应该也和 Objective-C 类似,
可能得避免使用。
参数冠名(ARGUMENT NAMES)延续了 OBJECTIVE-C 的 METHOD 语法
Objective-C 的 method 语法非常特殊,喜欢的人很爱,讨厌的人也很多。在
Objective-C 中,method 被呼叫时,signature 本身和传入参数会互相交织。例如
如果有个发送 email 的 method,可能就会长成这样:
// 送出一封标题为 "Hello",内容为 "This is a test message." 的信件。
// 寄件人为 me,收件人为 user1 与 user2。
[mailSender sendMailWithTitle:@"Hello"
content:@"This is a test message."
from:me
to:@[user1, user2]];
第一眼看上去可能很怪,但可读性却非常高。在 Swift 中,同样作用的 method 可
能会这样宣告:
func sendMail(title: String, content: String, from: User, to: User[]) {
// 实作…
}
然后这样用:
sendMail("Hello", "This is a test message.", me, [user1, user2])
这和大多数程式语言的语法相符,但 Objective-C programmers 应该会觉得可读性
变差了。如果使用 parameter names,就可以这样写:
func sendMailWithTitle(
title: String, content: String, from: User, to: User[]) {
// 实作…
}
然后
sendMailWithTitle("Hello",
content:"This is a test message.",
from:me,
to:[user1, user2])
有没有比较开心!至少我有。:D 当然这个 syntax 本身还是有可能是参考其他语言
而来,不过精神上肯定是从 Objective-C 传承来的。
SWIFT 在概念上就是 OBJECTIVE-C
Swift 的很多概念根本是从 Objective-C 照抄的。这在很多地方都看得出来。我在
PTT 讲过内存管理,另外单继承与 protocols 的概念也是如此(而不是来自 C#)。
当然这有好有不好,不过至少对于已经熟悉 Objective-C 的人而言,这应该非常亲
切。
苹果在设计 Swift 时,完全没有改变它背后的理念,只是为了这些理念创造了全新
的语言,而不再继续使用基于 C,而需要背负许多包袱的 Objective-C。你从
Objective-C 学到的东西还是能够继续使用,只是因为它们现在不再基于 C,而会有
些语法上的变化(通常是简化)。
Tim Cook 在 keynote 讲的话不是效果而已,其实 Swift 真的就是 Objective-C
without the C 啊。

作者: TsaoCCFGOGO (书唸累时,就算数学吧)   2014-06-04 01:29:00
专业好文!推!
作者: Piceman (派斯面)   2014-06-04 02:08:00
推一下,讲的很清楚
作者: manlike ( )   2014-06-04 09:48:00
ObjectiveC的method超废,呼叫一个method写一大串 LOL根本神经病,什么可读性,还不是要靠IDE和文件~ XDDD不要讲可读性,可用性更是笑话,写参数名称浪费时间又干扰写程式的顺畅度和思考逻辑,阅读上一堆字,视力要很好LOL
作者: kiii210 (HelloWorld!)   2014-06-04 10:06:00
作者: manlike ( )   2014-06-04 10:13:00
话说,不知道有没有人用vi写 Objective-C ? XD
作者: Deltaguita (伯利兹)   2014-06-04 10:38:00
不要讲这么白,果粉会生气...
作者: tommy60703 (白菜)   2014-06-04 10:49:00
Manlike大,Obj-C的方法是可以不取参数名称只用冒号分开的,但我还是爱用落落长的名字,对我来说真的增加很多可读性,反正Xcode的自动完成很方便弹指就写完了
作者: kiii210 (HelloWorld!)   2014-06-04 11:03:00
我觉得Obj-C这样写method还满清楚明白的呀ps.我只写过Obj-CSwift这样要习惯一下就是
楼主: uranusjr (←這人是超級笨蛋)   2014-06-04 11:38:00
@manlike 你开心就好, 没人逼你写; 反正你也只会随口凭感觉放话, 讲错被电就离脱嘛, 别人说什么也没用
作者: Blueshiva (龙野南云)   2014-06-04 11:42:00
a("manlike",0,null,false,"shit") <-可读性多好啊!
作者: Deltaguita (伯利兹)   2014-06-04 12:52:00
你看,生气了
作者: tom19830924 (Tom Hsu)   2014-06-04 14:14:00
我也觉得Objective-C的方法名称很清楚 我记得以前看语言教学的时候还有提到这是优点啊 越长越清楚越好
作者: SwiftLang (Swift-Lang)   2014-06-04 14:26:00
大家好以后请大家多多指教喔!
作者: tkdmaf (皮皮快跑)   2014-06-04 15:24:00
楼上昨天刚出生???以后每年的6月2日(美国时间)就是SwiftLang的生日了。
作者: Killercat (杀人猫™)   2014-06-04 18:32:00
Obj-c的method算是一种用ide enhanced下的可读性很难说好还是不好,当一个method参数是20个string的时候应该是不会有人觉得C-like的写法让人愉悦啦至少Obj-c里面20个String在使用的时候都会有清楚的名字在C/C++底下也是得靠很强大的IDE才不至于弄混(我知道20个String的arguments很烂 不过这只是举例 举例不过我始终无法对无法定型的容器有好感 =___=
作者: Deltaguita (伯利兹)   2014-06-04 20:08:00
20个String 不考虑用vararg 或struct?有没有"更"合理的解释方式
作者: Killercat (杀人猫™)   2014-06-04 20:30:00
不用20啊 四个就够你受了好吗...尤其是POD :D有个人没说错,Obj-C method写法的确是比较吃IDE才好用但是这不代表你可以用“你看果粉生气了”来扯烂污啊...你觉得它烂 sure 我甚至能理解 但是嘴巴干净点一堆人上班眼睛已经吃够多屎了 大家包容点吧吵架在所难免 讨骂真的就免了 没建设性
作者: Blueshiva (龙野南云)   2014-06-05 00:59:00
"更"合理的解释方式?没有,也不需要,偏见是非理性的
作者: ian90911 (xopowo)   2014-06-05 01:18:00
作者: ZZB (亨亨)   2014-06-05 05:35:00
扣帽子喷一句话的没建设性发言就省省吧
作者: sorkayi (寻找奶昔)   2014-06-06 14:06:00
不管 Obj-C 才是全世界最棒的语言
作者: cha122977 (CHA)   2014-06-07 13:08:00
吃IDE其实也没什么关系,很少人不用X-CODE写obj-c的吧
作者: wfgh (lyle)   2014-06-08 11:06:00
不知道有没有人用vim开发android
作者: Killercat (杀人猫™)   2014-06-08 11:44:00
当然有 开发NDK程式的时候还是vim好用(这是语病吗 XD)我家老板以前开发iphone也用vim写obj-c 看得我直皱眉XD不过天才都有一些怪僻啦 既然我家老板是个天才 那就算了
作者: TsaoCCFGOGO (书唸累时,就算数学吧)   2014-06-08 18:34:00
vim 应该也可以 auto-completion, 只是 terminal size要够大,不然自动换行很痛苦 XD

Links booklink

Contact Us: admin [ a t ] ucptt.com