http://www.cocoachina.com/industry/20140605/8686.html

WWDC 2014上苹果再次惊世骇俗的推出了新的编程语言Swift 雨燕, 这个消息会前没有半点风声的走漏。消息发布当时,会场一片惊呼,相信全球看直播的码农们当时也感觉脑袋被敲了一记闷棍吧。于是熬夜学习了Swift大法,越看越想高呼 ” Swift大法好!“
 
程序员,最讲究的就是实事求是和客观,下面就开始对比两种语言。
 
首先要强调的是,Swift绝对不是解释性语言,更不是脚本语言,它和Objective-C,C++一样,编译器最终会把它翻译成C语言,也就是说编译器最终面对的其实都是C语言代码( 这是千真万确,不容置疑的!!!所以不要看它长的想脚本语言,其实它是比Java, C#要高效的多的C语言!!!),但是Swift的强大之处在于它站在所有语言的肩膀上,吸取所有语言的精华。
 
这个系列我们先谈谈几个最基本的语法变化:
1. Swift终于放弃了Objective-C那幺蛾子般的 [ obj method:x1 with:x2] 的语法,终于跟随了大流,变成了obj.method( )的顺眼模式。虽然对于Objective-C的程序员来说,这些[ ]看上去特显酷 , 你们知道就是这个中括弧吓跑了多少c++, java , c#的程序员嘛?所以说这个小小的变化,可以让苹果的开发更平易近人,对有其他开发语言基础的人来说更友好。
 
但苹果不会这么自甘平庸,我们知道Objective-C里方法的调用有种语法是其他主流语言没有的,那就是标签。我们在使用java, C++, C, C#等语言时,如果使用 rect.set( 10, 20, 100, 500 ), 虽然在写set方法的时候,IDE有提示四个形参的含义,但写完后,这句代码中10, 20, 100, 500是社么意思? 所以代码的可读性就变的很差, 而Objective-C很完美的解决了这个问题 :
  1. [ rect setX:10 y:20 width:100 height:500 ]
  
看看!多棒!Swift当然不会丢弃这么好的传统, 在Swift中是这个样子的
  1. rect.set( 10, y:20, width:100, height:500 )
 
对于调用方法时,标签的使用需要注意以下两点:
 
1)全局函数的调用,不可以使用标签
  1. fun( 11, 22 , 33 ) //正确
  2. fun( n1:11, n2: 22, n3: 33 ) //错误
 
2 ) 类的函数,第一个参数不可以加标签 
  1. rect.set( 100, y:100, width:300, height: 200 ) //正确
  2. rect.set( x:100, y:100, width:300, height: 200 ) //错误
  
其实Swift中对类的定义和java, c#几乎一样,再也不分头文件和.m文件了。
 
一个类的定义语法如下:
  1. class Weapon
  2. {
  3. var name:NSString
  4. var power:int
  5. init( name:NSString, power:int )
  6. {
  7. self.name = name
  8. self.power = power
  9. }
  10. func shoot( )
  11. }
  
注意:Swift中的语句不需要分号结束.
 
其次,终于有构造函数和析构函数了!!!Objective-C也有?no no no!!!
 
Objective-C中没有构造函数,真正的构造函数是系统自动调用的,而不是强迫程序员去调用。以前要强迫程序员[ [ Obj alloc ] init ],现在终于终于终于系统自动调用了!
  1. Weapon weapon = Weapon( name:“人间大炮”, power: 100000000000 )
 
我没有写错, 对的!现在和java,C#一样!虽然weapon是一个指针,但不要写那颗星号!!因为这颗星号吓死过好多人!“ 啥?指针?!!啊。。。。。”
 
C、 C++的程序员注意了,这个weapon对象不是分配在栈内存上的, 仍然是alloc出来的, 在堆上呢。
 
2. 最期待的语法终于加入了!
对于override在Java,C++,Objective-C中都有问题,举个栗子:
  1. @interface Weapon
  2. -(void)shoot;
  3. @end
  4. @interface Gun : Weapon
  5. -(void)Shoot;
  6. @end
  
在大项目中经常会遇到这个问题,程序员的本意是希望覆盖父类的shoot ,结果手潮。。。。写成了Shoot , 这既没有语法错误,也没有逻辑错误,结果在
  1. Weapon*  currentWeapon = [ Gun new ];
[currentWeapon shoot ] 中调用的却是父类的shoot方法( 因为子类根本没有覆盖啦,子类大小写不小心写错了 ), 这种小错误如果出现在超大型项目种还真是很难找呢!!现在,Swift终于解决这个问题啦! 子类覆盖父类方法的时候,一定要在方法前写上override : 
  1. override func shoot{
  2. }
 
这样,编译器一看方法前写了override, 它就会在父类中去查找是否有shoot方法, 如果你写错成override func Shoot, 那编译器就立刻能发现报错啦!
 
 
系列(二)
系列一发表后,有人不同意我的关于 #swift会取代objective-c#的论点,在这里我想强调两点:
1)Swift其实就是Objective-C的文本变种,对于这门全新的语言,苹果做的工作其实远没有我们想像的艰巨。LLVM编译器做工作只是先把swift翻译成Objctive-C代码,然后再把Objective-C代码翻译成C语言代码,然后再把C语言代码翻译成汇编,最终翻译成机器码。至于为什么编译器厂商这么绕,不直接把自己的语言翻译成汇编和机器码,那是由于现有的语言编译器(Objective-C, C )已经非常成熟,而高级语言间的文本转换开发成本和维护成本都极其小。Swift为什么要翻译成Objective-C,是由于Swift仍然需要Objective-C中辛苦构建的ARC,GCD 等环境。
 
2)既然Swift代码最终会被LLVM翻译成Objective-C, 那Swift语言还有什么意义?想想ARC刚出来的时候大家的反应吧,很多人和今天的反应一样,认为我是资深的objective-c马仔了,我深谙内存管理之道,不停的写[ obj release ], [ obj autoRelease] 很牛,只有那些初学者才会用ARC呢。结果就是不到一年,ARC统治了整个马仔界,因为我们马仔关注的应该是业务逻辑,而不应该把精力分散在语法等低级问题上,语法消耗我们的时间越少,这门语言就越成功。
 
既然Swift其实就是Objective-C, 对入门者而言远比Objective-C好学,对资深开发者来说又能节约很多无谓的低级重复的机械代码(这些代码在LLVM翻译成Objective-C时,编译器自动帮你写上)。我是想不出任何一点Swift不替换Objective-C的理由呢。
 
好吧,争论放置一边不表,我们从头来看swift到底进化到什么程度。

1)语句不需要分号结束,变量如果有初始化就不需要类型
  1. var n = 22
 
对于编译器而言,既然你都初始化为22了,它当然明白n是int , 你都打回车了, 它当然知道这是语句的结束,所以LLVM毫无压力的把它翻译成
  1. int n = 22;
 
当然对于多个语句放一行,那编译器就没有办法了, 你还是要用分号来结束语句。如果没有初始化,你也可以手工指定变量类型
  1. var n = 22; var hero:Hero
所以看上去是无类型变量,实质上还是强类型的( 编译器给你做了 ).
 
如果是常量的话, 用let 
  1. let PI = 3.1415926
 
这里的PI 就是常量, 现在想想,以前的强类型高级语言真是傻到无语啊,let PI = 3.1415926 , PI  都这么明显是个double, 为啥还要程序员再写double ?! 
 
2)函数的定义
  1. func test( p1: int, p2: int )
  2. {
  3. }
调用: test( 25 , 100 ) //注意:全局函数的调用,参数不能加标签
 
如果有返回值, 返回类型用符号 “ -> ” 表示
  1. func  add( p1: int, p2 : int )->int
  2. {
  3. return p1+p2
  4. }
  
3)类的定义
不再分头文件和m文件了!这点和java, C#一模一样
  1. class Person
  2. {
  3. var    name:String
  4. var    age = 0
  5. init( name:String , age:int )
  6. {
  7. self.name = name;
  8. self.age = age;
  9. }
  10. func description( )->String
  11. {
  12. return “Name:\( self.name ) ; Age: \( age )”;
  13. }
  14. }
  
注意终于有构造函数了!!init 是系统自动调用的, 不需要程序员手工调用。所以它写起来和普通函数也有区别,前边不能加func。 编译器为什么要这样做?因为如果init也允许前面加上func, 万一程序员不小心把init函数名写错了, 写成func Inot( ),编译器就完全不知道它是程序员想写的构造函数。现在构造函数前不加func , 如果你写成Inot( ) 。 编译器一看前面没有func知道你要写构造,可函数名又不是init, 编译器就知道你不小心写错了就可以立刻报错啦!!
  
4)可选变量# ---所有高级语言一开始就遇到的难题
比如客户需要提供一个最终的API, 客户给你一个数据源, 需要在数据源里找到名字是“jack.xu”的学员成绩。这个api的设计应该是这样的:
  1. int FindScoreByName( DataSource*  source, string* name );
 
问题来了,如果“jack.xu”的学员根本不存在,应该返回啥? 返回0?那肯定不对,因为0有可能也是学员的成绩。当然,如果返回的是类的对象,直接返回 NULL , 调用者就知道没有找到,现在是基本数据类型,返回NULL 其实就是0,怎么办?(在C,C++中的规范做法是 返回bool表示是否找到,而成绩通过形参来传递 ,其他高级语言中可以封装一个小类/包裹类 )
 
Swift针对这个问题,专门设计了一个叫”optional value(可选变量)”  的变量,它就是为了解决这个问题的。
 
语法:
  1. var n : UInt ? = 5    或则  var n ? = 5
 
这里的?表示n 是个可选变量, 也就是说 n 有可能不存在, 什么情况下n不存在呢?
 
如果你这样写:
  1. var n : UInt ?
 
此外,需要注意的是swift语法中,nil 并不是0 , 而是一个NilType类型的变量
 
所以上面提到的那个问题就可以很容易解决了
  1. func FindScoreByName( source:DataSource, name:String )->UInt?  //返回的是可选变量
  2. {
  3. var score : UInt ?; //此时 score 的变量没有分配内存,也就是说score为nil
  4. if( source.HasStudent( name: name ) )
  5. score = source[ name ]. score;  //这里score才分配内存;
  6. return score; //如果没有找到学生信息, score的内存一直没被分配
  7. }
 

[IOS swift对比oc]的更多相关文章

  1. iOS开发--Swift 如何完成工程中Swift和OC的混编桥接(Cocoapods同样适用)

    由于SDK现在大部分都是OC版本, 所以假如你是一名主要以Swift语言进行开发的开发者, 就要面临如何让OC和Swift兼容在一个工程中, 如果你没有进行过这样的操作, 会感觉异常的茫然, 不用担心 ...

  2. iOS获取手机型号,类似iphone 7这种 含swift和OC

    获取手机设备信息,如name.model.version等,但如果想获取具体的手机型号,如iphone5.5s这种,就需要如下这种 swift: func phonetype () -> Str ...

  3. iOS开发--混编篇&swift与OC混合使用

    Swift与OC混合使用 swift 语言出来后,可能新的项目直接使用swift来开发,但可能在过程中会遇到一些情况,某些已用OC写好的类或封装好的模块,不想再在swift 中再写一次,哪就使用混编. ...

  4. iOS开发之swift与OC混编出现的坑,oc中不能对swift的代理进行调用,不能访问swift中的代理,swift中的回调方法

    1. Swift与oc混编译具体怎么实现,这儿我就不重复讲出了,网上有大把的人讲解. 2. 在swift与OC混编的编译环境下, oc类不能访问swift创建类中的代理? 解决方法如下: 在代理的头部 ...

  5. iOS开发——swift——swift与OC之间不得不知道的21点

    swift与OC之间不得不知道的21点   自6月的WWDC大会上由苹果的大神Chris Lattner向我们首次展示swift至今已经大半年时间了,虽然绝大部分软件公司代码里还都见不到一丁点swif ...

  6. ios Swift 资源池

    Swift入门教程: http://www.cocoachina.com/applenews/devnews/2014/0604/8661.html Swift视频教程: http://www.coc ...

  7. iOS Swift WisdomKeyboardKing 键盘智能管家SDK

    iOS Swift WisdomKeyboardKing 键盘智能管家SDK [1]前言:    今天给大家推荐个好用的开源框架:WisdomKeyboardKing,方面iOS日常开发,优点和功能请 ...

  8. [ios][swift]swift混编

    http://blog.csdn.net/iflychenyang/article/details/8876542(如何在Objective-C的头文件引用C++的头文件) 1.将.m文件扩展名改为. ...

  9. iOS swift的xcworkspace多项目管理(架构思想)

    iOS  swift的xcworkspace多项目管理(架构思想) 技术说明: 今天在这里分享 swift下的 xcworkspace多项目管理(架构思想),能为我们在开发中带来哪些便捷?能为我们对整 ...

随机推荐

  1. Java调用C/C++编写的第三方dll动态链接库(zz)

    这里主要用的方法是JNI.在网上查资料时看到很多人说用JNI非常的复杂,不仅要看很多的文档,而且要非常熟悉C/C++编程.恐怕有很多人在看到诸如此类的评论时已经决定绕道用其他方法了.本文将做详细的介绍 ...

  2. JavaScript的一些知识碎片(2)-反射-全局变量-回调

    JavaScript中的反射:编程语言中的反射原理都一样,就是通过操作metadata(描述语言的语言)来完成一些不具备反射功能的语言很难实现的功能.在静态语言中,反射是一个高大上的东西,比如在运行时 ...

  3. WPF EventSetter Handler Command

    最近做一个工具,突然发现ListBox和ListView等列表控件的MouseDoubleClick事件有时候是获取不到当前双击的行对象数据的,比如这样写: <ListBox Grid.Row= ...

  4. C#微信开发小白成长教程一(公众平台的工作原理与调试环境部署,附视频)

    黑夜给了我黑色的眼睛,我决定录视频到天明.半年前的现在,我还在苦逼着加着班,半年后的今天我依旧苦逼着加着班.不过现在的是为自己加班,作为一个资深程序小白,一个月前我光荣的成了一个不称职的资本家,不称职 ...

  5. DOM之表格与表单基础分享

    我是沐晴,好久不见.马上要放假啦,也是比较的忙. 今天来谈谈表格和表单的基本知识.前期的写的都是比较基础的知识,后期会慢慢增加实例.一起来学习吧. 先看表格,DOM中提供了一些属性,便于我们获取表单节 ...

  6. Mininet在创建拓扑的过程中为什么不打印信息了——了解Mininet的log系统

    前言 写这篇博客是为了给我的愚蠢和浪费的6个小时买单! 过程原因分析 我用Mininet创建过不少拓扑了,这次创建的拓扑非常简单,如下图,创建拓扑的代码见github.在以前的拓扑创建过程中,我都是用 ...

  7. 年中review

    1. 做好已知的各种项目,争取能成立固定团队 (项目一期争取能在本月上线)2. 横向扩展技术学习,了解各种技术,加强技术素养(从Server到前端,现在要关注的知识点越来越多,fighting...) ...

  8. JavaScript学习笔记-new Date() 与 Date() 的区别

    var today1 = Date() //返回一个字符串(string),没有getDate等日期对象方法,内容为当前时间 var today2 = new Date() //返回一日期对象,内容为 ...

  9. HTTP 错误 500.24 - Internal Server Error的解决方法

    错误提示: 最可能的原因:   system.web/identity@impersonate 设置为 true. 解决办法: 现在经典模式 连微软都几乎放弃了 原设想是为iis不断升级 提供的一种兼 ...

  10. C# has three timers

    结论 *1.窗体timer和线程timer.计时器timer不同,因为后两者dispose之后,GC可以收集,而前者无法收集 *2.如果一个对象的成员函数正在被执行,那么这个对象肯定不会被收集 *3. ...