【Objective-C 篇】 ☞ 3. self、数据类型、编码规范

1. self关键字 

self 是一个指针,哪个对象调用方法就指哪个对象,其作用是区分不同对象。

1.1 在实例方法中的self,代表当前对象

当前对象,通过哪个对象调用了这个方法,方法中的self就指向那个对象。这个对象就叫当前对象.

1.2 在类方法中的self,代表当前类

类方法中,self代表类方法所在的类本身。所以在类方法中,self会被直接当类来使用

我们推荐在类方法使用self代替类,因为便于子类继承

总结:

如果self在对象方法中,那么self就代表调用当前对象方法的那个对象

如果self在类方法中,那么self就代表调用当前类方法的那个类

我们只用关注self在哪一个方法中,如果在类方法那么就代表当前类,如果在对象方法那么就代表"当前调用该方法的对象"

super关键字

super 也是一个指针,指向当前类的对象中父类的成员。

  • super代表类的父亲
  • [super init]是通知父类区做底层的初始化操作。
  • super是指向对象中继承过来的父类部分的指针。
  • 利用super可以调用由于子类重写而被隐藏的父类函数。

2. OC中对象类型和非对象类型

2.1 概念

1) 对象类型,@interface定义的类,可以创建对象。所以这种类型叫对象

2) 非对象类型,OC语言是完全兼容C语言,所以C语言中的基本数据类型,结构体,枚举等在OC都可以用,这些类型叫非对象类型。

2.2 内存分配

1) OC中所有的对象都在堆中。但指向对象的引用可能在栈中,当然也可能在全局区,或堆中。

2) OC中所有的对象类型的参数传递都是地址传递,我们只能将对象的地址传给一个函数或方法,不可能将对象本身传给函数或方法。

3) OC中的非对象类型,内存分配可能会在栈中,或全局区。也可能在堆中(当做为一个对象的属性时)

3. OC语言中经常使用的非对象类型

3.1 基本数据类型

  NSInteger:

    typedef int NSInteger;32位系统)   

    typedef long NSInteger;64位系统)

    在32bitiOS系统中,NSInteger4个字节,而在64bit系统中,是8个字节。这样做的兼容性好。 

    所以,在iOS实际开发中,尽量使用NSInteger来定义变量,属性,参数等,而不要使用intlong等。

  NSUInteger: 是无符号的NSInteger

  typedef unsigned int NSUInteger;32位系统)

    typedef unsigned long NSUInteger; 64位系统)

  CGFloat:

  在32bitiOS系统中,CGFloat4个字节,相当于float类型;而在64bit系统中,8个字节,相当于double,这样做的兼容性好。

  所以,在iOS实际开发中,尽量使用CGFloat来定义变量,属性,参数等,而不要使用floatdouble等。

     typedef double NSTimeInterval; //NSTimeInterval double类型,通常用于表示时间(多少秒)

  BOOL: 

  逻辑数据类型BOOL

  C语言中布尔类型:bool b1 = false; //true 1 false 0

  Objective-C中布尔类型:  BOOL b2 = YES; //YES 1 NO 0

3.2 结构体:CGPointCGSizeCGRectNSRange

     

3.3 实际的iOS开发中经常定义的全局常量

需要在一个文件中声明全局常量,再在一个.m文件中定义全局常量。这个常量就可以在应用的任何位置使用了。使用前需要#import头文件

3.4 枚举

OC语言中使用的枚举就是C语言中的枚举

OC语言现在使用枚举都是按照C++11的标准规范定义。C++11中规定,枚举值可以规定类型。

enum 枚举类型名 : 枚举值类型{枚举值...};

OC语言中定义枚举使用新的方式:

typedef NS_ENUM(枚举值类型, 枚举名){...};

typedef NS_OPTIONS(枚举值类型, 枚举名){...};

4. OC语言基本编程规范 

怎么定义类名,方法名,属性名,代码风格....

4.1 标准符(identifier )

给类,属性,方法,变量,结构体,枚举等起的名字

最基本的规定,违反规定会导致编译错误

1) 必须以字母或下划线开头

2) 可以包含字母、下划线和数字

  +-*/肯定是不行的

3) 不能和关键字冲突  float int = 3.14;//ERROR

4) 大小写敏感(case sensitive)

5) 长度不限

4.2 命名规范

1)类,分类,扩展,协议,结构,枚举等类型起名时,一般要加前缀

TRMyFirstClass: TR是前缀

NSString : NS是前缀

CGPoint : CG是前缀

UIButton : UI是前缀

主要目的是减小命名冲突。苹果公司默认保留所有两个字母前缀的权利,所以非苹果官方的类建议都使用三个字母的前缀。

2)使用驼峰命名方式

  • 给类,分类,扩展,协议,结构,枚举等类型起名时,每个单词的首字母大写。(如:TRMyFirstClass
  • 给属性、方法、变量起名时,第一个单词的首字母小写,其他单词的首字母大写。

mySalary

setName:

isGirl

changeYourName:

3) 一般使用#define定义的宏都是大写的

但是,OC中,不建议大量使用宏。如果要定义常量,应该在头文件中声明,在.m中定义,命名使用驼峰方式

4.3 特殊方法的命名

1)初始化方法

无参的初始化方法一定叫"init"

有参的初始化方法一定以"initWithXxx.."开头,后面单词首字母大写

2)工厂方法

绝大部分工厂方法的名字都是类名开头(首字母小写),如果有参数,加With

+ point

+ pointWithX:...

有特殊含义的方法可以不遵守这个规定,比如

UIColor类中的 red, green, blue等类方法

3) 普通方法

普通的实例方法和类方法尽量不要以new开头。因为以new开头的方法往往是用来创建对象的,系统会做特殊的内存管理。

[TRPoint new]; ==> [[TRPoint alloc]init];

4.4 其他需要注意的事项

1) 代码一写要有缩进,代码就有层次感

2) 当一个方法的参数较多时,可以分多行,每行将用":"号对齐

3) 方法不要太长,争取一屏能显示得下一个方法的所有代码

如果方法太长,可以拆成若干个私有方法。

5. @class

  • #import
    • 由于import是一个预编译指令, 他会将""中的文件拷贝到import所在的位置
    • 并且import有一个特点, 只要""中的文件发生了变化, 那么import就会重新拷贝一次(更新操作)
  • @class
    • @class仅仅是告诉编译器, @class后面的名称是一个类, 不会做任何拷贝操作
    • 注意: 由于@class仅仅是告诉编译器后面的名称是一个类, 所以编译器并不知道这个类中有哪些属性和方法, 所以在.m中使用这个类时需要import这个类, 才能使用
    • .h中用@class可以提升编译效率

因为在.h中用@class,.m中用import,如果一个文件发生了变化,只有和这个文件有直接关系的那个文件才会重新拷贝

       

        Q:如果两个类相互拷贝,例如A拷贝B,B拷贝A,这样会报错

        A:因为如果.h中都用import, 那么A拷贝B, B又拷贝A, 会形成死循环

               如何解决?

             在.h中用@class, 在.m中用import

             如果在.h中用@class, 那么不会做任何拷贝操作, 而在.m中用import只会拷贝对应的文件, 并不会形成死循环

  • 在实际开发中,在.h中要使用某个类建议用@class,在.m中要使用某个类用#import

 

原文地址:https://www.cnblogs.com/bossren/p/6425337.html