《IOS开发系列教程》objective c学习之 objective c和c/c++的比较
因为本人学习c/c++已经有些年头了,因此打算通过比较来学习,这样学习起来会比较快,因为只需要理解和记住不同的地方。
objective c和c++都是c的扩展,c是纯面向过程的语言,而objective c和c++则是在c的基础之上加入了面向对象的概念,objective c是借鉴了smalltalk中面向的对象的语法。
c中所有的语法都可以用到 objective c和c++中。
这样我们比较的话,就只需要比较objective c和c++了。
如果用一句话来描述objective c和c++的最大的区别,那就是对象(指针)的方法的访问方式不同,objective c是用方括号,而c++是用点或者指针符号。
下面就各个不同点加以描述
Objective C和C++的区别 |
||
---|---|---|
|
C++ |
Objective C |
1. 类的定义不一样 |
定义类是用关键字class表示。 例如:
class classA |
定义类是用关键字interface和implementation共同完成,并且这2个关键字前面需要加上@这个符号,并且需要使用 @end 来表明类声明(@interface)和类实现(@implementation)的结束 @interface
-(void) func1; -(void)func1() {
}
|
2. 对基类强制性 |
定义一个类,可以不从任何类继承,也可以从某个继承 |
所有的类,必须继承自某一个类,否则xcode会报错。所有类的祖先类是NSObject,所以你的类可以继承自NSObject |
3. 默认的函数返回类型 |
如果没有为函数定义返回类型,c++默认是void,这和c是一致的 例如: testFunc(){} |
如果没有为函数定义返回类型,默认是id,这和c是不同的。id就是objective c |
4. 多继承 |
支持多继承 |
不支持不继承 |
5. 类的静态成员的定义 |
使用关键字static 例如: class classA { public: static staticFunc(); } |
使用加号(+),相对于私有是使用减号(-) 例如: @interface classA : NSObject -(void) privateFunc; +(void) staticFunc; @end |
6. 虚函数 |
使用关键字virtual修饰类的方法 |
Objective C可以说所有的方法都是虚函数,或者说Objective C中根本没有这个概念。子类可以重写父类的任何的方法。 |
7. 一些常量的声明 |
bool à true/false 空指针 à 0或者NULL |
BOOL à YES/NO 空指针 à nil |
8. 类函数的声明 |
Private: void func1( int input );
参数使用逗号分开 Void func1( int input, int input1 ); |
不管是返回值的类型还是参数的类型均是用小括号括起来 -(void) func1:(NSInteger)input;
-(void) func1:(NSInteger)input AnotherInput:(NSInteger)intpu1; |
9. 构造函数和析构函数 |
存在构造和析构函数 分别是类名和~类名的函数。并且如果没有其他的构造函数,无参数的构造函数一定会被系统调用,析构函数也一定会被调用。 |
Init和dealloc,但是,即使你定义了init这个函数,系统不会自动调用它,除非你显示的调用,例如: ClassA *a = [ClassA alloc];//不会调用 ClassA *a = [[ClassA alloc] init];//会调用 Dealloc这个会被调用 |
10.抽象类 |
可以定义抽象类或者接口,类中方法是纯虚函数。 |
没有抽象类。如果一定要找个类似的,那就是protocol,使用@protocol的定义的类 |
11. 类的成员变量 |
使用类型+变量的命的方式,是在类声明的时候加以说明。所以一般是在.h文件中,当然也可以在cpp文件中 |
多了一个叫做属性的功能,通过关键字 @property 并且有额外属性说明,如strong, weak, nonatomic, copy等 然后才是变量类型和名字 并且支持自动这个变量的私有变量名 多一个前置下划线,可以通过 Self._变量名来访问 同时生成这个变量的set和get方法 还可以定义私有变量,这个是在实现文件 .m文件中, @interface xxxx() { [变量类型] [变量名字] } |
12. self & this |
对象自身使用this |
对象自身使用self |
13. 栈中创建类对象 |
允许 |
不允许,所有的类对象都必须在堆上创建,所以在函数中,你也需要 ClassA *aa =[ [ClassA alloc] init]; 不可以 ClassA aa; |
14. 自动计数机制(ARC) |
C++原生是不支持的,如果使用这个特性,需要使用智能指针 |
使用ARC技术,如果在创建工程的时候配置了ARC支持,那么你的创建 Objective C的对象,不需要再去调用release,系统会自动根据引用计数来确定是否释放该对象所占用的堆空间。 |
15. 命名空间 |
支持,使用关键字 namespace |
不支持,所以一般是通过前缀来区分不同库(这是默认的机制),例如所有的cocoa提供的类都是NS开头的 |
16. 模板 |
支持 template |
不支持,但是似乎在Objective C中不支持此特性,依然可以完成类似的任务,因为Objective C不是一个强类型的语言,例如NSArray就可以承载任何类型的对象,这个不像C++中,一个容器类型(模板类)在定义的时候就需要指明类型,如 Std::vector<int> |
17. id vs void* |
对象指针是类名加星号或者void* |
对象指针是类名加星号或者id |
18. 基类super |
C++中没有类似关键字,必须使用基类的名字 |
在子类中可以使用super代表基类,例如: [super init]; |
19. 类成员的访问属性 |
使用public, protected, private, static |
没有public,protected,private这些关键字,定义可以外部访问的方法,在头文件中定义该函数,前面使用减号 -(void) func1; @end 如果定义私有方法则在实现文件中声明和是实现 @interface ClassA() {
-(void) func2;
@implementation ClassA -(void) func2 { } @end 静态方法的定义则是头文件中定义,减号改为加号 @interface ClassA:NSObject -(void) func1; +(void) func3; @end |
20. selector,运行时动态方法调用 |
不支持,最多做到多态的动态方法调用,也只是对同一继承树上同一方法的调用 |
可以通过 @selector来决定调用那个方法,例如 SEL mySelector = @selector(func1); 或者是通过字符串的方式制定,通过这种方式就可以达到动态调用的效果 SEL mySelector = NSSelectorFromString(@”funcName”); 从这个角度看,selector就是一个函数指针选择器 |
21. 对空指针的方法调用 |
会导致程序崩溃,例如 ClassA *pa = NULL; pa->func(); |
不会导致程序崩溃,例如: ClassA *pa = nil; [pa func]; |
22. 函数调用还是发送消息 |
ClassA *pa = NULL; pa->func(); 上面func()就是函数调用。 函数的调用在编译时刻就已经确定好了,就是函数的偏移地址,调用的时候直接跳去这个地址执行。 |
ClassA *pa = nil; [pa func]; 上面的[pa func]是发送消息到pa这个对象。在Objective C中所有的这种行为实质上是发送消息,消息被对象接受到之后,可以将消息在传送给其他的对象,或者调用方法,虽然看起来效果跟函数调用一样。在编译时刻根本不知道某个对象是否能够相应某个消息(这就是为什么xcode给出一个警告而不是错误,当你把一个方法拼写错误的时候) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
版权所有,禁止转载. 如需转载,请先征得博主的同意,并且表明文章转载自:IT夜班车,否则按侵权处理.