Object C基础
10/100
发布文章
ChaseRaod

最近开始接触ios开发,需要学习下object C,此文记录学习内容。

Object C关键字:@

1,@interface:声明类
2,@implementation:实现类
3,@optional:声明协议。与@protocol配合使用,说明协议中的某个或者某几个方法可以不实现
4,@required:与@protocol配合使用,说明协议中的某个方法或者某几个方法必须实现
5,@end:与@interface ,@implementation,@protocol配合使用,代表声明或者实现结束
6,@encode:@encode为编译器宏,它可以将类型转换为相应的字符串。
7,#include & #import & @class & @import
(1)#include
在编译预处理阶段,预处理器会将一些引入的头文件替换成其对应的内容。
(2)#import
#import 可以说是 #include 的一个升级,有关 “” 和 <> 的使用与 #include 相同。除此之外,#import 解决了”重复引用“的问题。
(3)@class
@class 是告诉编译器有这样一个类,但是具体这个类里面有什么不知道。好比只给了你一本书的目录,但是没有给你书的内容。那么什么情况下使用 @class 呢?在编译预处理阶段,会将文件中的 .h 文件替换为对应的内容,如果 .h 文件中还引入了其他的 .h 文件,则进行逐级替换,依次递归。因此,尽量不要在 .h 文件中引入其他的 .h 文件。如果在声明一下方法或者属性时,需要用到某个类,这时可以用 @class,并且需要在 .m 文件中以 #improt 的方式再次引入这个文件。

// .h 文件中
#import <UIKit/UIKit.h>
@class UserModel;@interface ViewController : UIViewcontroller
- (instancetype)initWithUserModel:(UserModel *)userModel;  // 此处用到了 UserModel 定义参数类型
@end// .m 文件中
#import "UserModel.h"
@implementation
// 在这里需要使用 UserModel 中的具体内容,此时需要以 #import 的方式引入。
@end

(4)@import
在说和这个关键字之前,先说一下 Moudles。#import 相对于 #include 解决了重复引用的问题,但同时也带来另外一个问题:当引用关系很复杂时,编译时引用所占的代码量就会大幅上升。如果想解决这个问题,可以在项目文件中的 Supporting Files 组内的 .pch 文件中将经常引用的一些头文件添加进去,解决编译时间问题。默认情况下,里面会引入 UIKit,这是每个文件中经常引用到的文件。

但是并不能把所有的文件都放到 .pch 文件中,因为放入 .pch 中的头文件,每个文件都能访问,这样有些文件就能访问它本不应该访问的文件。

为了解决这个问题,Moudles 出现了。Modules 相当于将框架进行了封装,然后加入在实际编译之时加入了一个用来存放已编译添加过的 Modules 列表。如果在编译的文件中引用到某个 Modules 的话,将首先在这个列表内查找,找到的话说明已经被加载过则直接使用已有的;如果没有找到,则把引用的头文件编译后加入到这个表中。这样被引用到的 Modules 只会被编译一次,提升速度,从而解决了编译时间和访问混乱的问题。

Apple 在 LLVM5.0 引入了一个新的编译符号 @import,使用 @ 符号将告诉编译器去使用 Modules 的引用形式。

#import <Foundation/FoundationErrors.h>// 下面等价于 #import <UIKit/UIKit.h>,同时还增加了 Moudles 的特性。
@import Foundation.FoundationErrors;

(5)pragma
pragma 是一个预处理指令,在 OC 中主要有两个作用:整理代码 和 防止警告。

整理代码
代码是一种艺术,代码写的优雅整洁是艺术的提现。使用 pragma 能够是代码结构看起来更加整洁。具体语法为 #pragma mark 描述内容,或者 #pragma mark - 描述内容。

@implementation ViewController#pragma mark - Lifecycle Method- (void)viewDidLoad {[super viewDidLoad];...
}- (void)viewWillAppear:(BOOL)animated {...
}- (void)dealloc {...
}#pragma mark - Private Method- (void)setupView {...
}- (void)layoutSubviews {...
}#pragma mark - UIScrollViewDelegate- (void)scrollViewDidScroll:(UIScrollView *)scrollView {...
}
@end

(6)id

id是指向Objective-C类对象的指针,它可以声明为任何类对象的指针,当在Objective-C中使用id时,编译器会假定你知道,id指向哪个类的对象。与void是不同的是,void编译器不知道也不假定指向任何类型的指针。

(7)nil

定义为一个常量,如果一个指针的值为nil,代表这个指针没有指向任何对象。

(8)self

在Objective-C中,关键字self与c++中this是同一概念,就是类对象自身的地址,通过self可以调用自己的实例变量和方法

(9)Super

当子类需要调用父类的方法时,会用到Super关键字. Super指向的是父类的指针,子类重写父类的方法时,调用父类的方法是一个比较好的习惯。因为当我们不知道父类在该方法中实现的功能时,如果不调用父类的方法,有可能我们重写的方法会失去该功能,这是我们不愿意看到的情况。

(10)NSNull

NSNull是没有的意思,如果一个字典的值为NSNull,那说明与该值对应的Key是没有值的,例如Key为address,说明与address对应的是值是没有。

(11)new

1 Objective-C有一个特性,就是可以把类当成对象来发送消息,这种用法通常用于新建对像时,例如 XXX *object = [XXX new];

(12)类方法 +

如果想声明属于类而不属于类对象的方法,用+。+用来修饰类的方法,使用+修饰的类方法,是整个类的方法,不属于哪一个类对象,这与C++中的static在类中使用的概念一样,

(13)%@

在NSLog中,使用%@表示要调用对象的description方法。

(14)类

是一种结构,它表示对象的类型,就像int与 char 一样,也可以声明类的变量(对像)

(15)实例化

为类的对象分配内存和初始化,达到可以使用该 类对象的目的。

(16)对象(实例)

类的实例化后的产物

(17)消息

在Object-C中,类的对象执行的操作,是通过给该类或者该类对象发送消息实现,如:[object func];就是给object对象发送func消息,类似C++中的方法调用。给object对象发送func消息后,object对象查询所属类的func方法执行。

(18)方法调度

当向一个对象发送消息时(调用方法),这个方法是怎么被调用的呢?这就依赖于方法高度程序,方法调度程序查找的方法如下:

在本类的方法中,找被调用的方法,如果找到了,就调用,如果找不到被沿着继承路径去查找,从哪个类找到,就调用哪个类的方法,如果到最根上的类还是没有找到,那编译就会出错。

(19)继承与复合

在Objective-C中支持继承,但只是支持单一继承(有且只有一个父类有),如果想使用多继承的特性,可以使用分类和协议技术。

继承是is-a,复合是has-a。复合是通过包含指向对象的指针实现的,严格意义上讲,复合是针对于对象间来说,对于基本数据类型来说,它们被认为是对象的一部分。

(20)装箱与拆箱

由于NSArray,NSDirectory等类不能直接存储基本数据类型,所以要想在NSArray\NSDirectory中使用基本数据类型,就得使用装箱与拆箱。

在Objective-C中,可以使用NSNumber和NSValue来实现对数据类型的包装,NSNumber可以实现对基本数据类型的包装,NSValue可以实现对任意类型数据的包装。

将基本类型封装成对象叫装箱,从封装的对象中提取基本类型叫拆箱(取消装箱),其它语言如Java原生支持装箱与拆箱,Ojbective-C不支持自动装箱与拆箱,如果需要得需要自己来实现装箱与拆箱。

(21)OC程序的开发过程

编辑,编译,链接(把所有的相互关联的.o文件合并在一起,加上函数库),运行。

和c类似,先编写.m文件(文件名可以是中文),然后编译器编译,链接,运行。


(22)NSLog与printf的区别

1、NSLog接收OC字符串作为参数,printf接收C语言字符串作为参数

2、NSLog输出后会自动换行,printf输出后不会自动换行

3、使用NSLog需要#import <Foundation/Foundation.h>,里面有NSLog函数的声明。不需要刻意记忆,想不起来,就编译,出错就会提示缺少什么。

4、可以只包含框架的主头文件,效果等价包含了这个框架里的所有的头文件。头文件在Xcode里面,路径很深,不好找。使用printf需要#include <stdio.h>

(23)oc的布尔和c++有区别,在C++里一切非 0 值的东西都为 true,而为0值的为false。但是Object-c里必须是1为 true ,且并被宏定义为 YES,0 为 false 并被宏定义为 NO。

(24)
方法开头的(-)号或者(+)号表示:
(-) 该方法是实例方法(对类的特定实例执行一些操作) ;
(+)是类方法(即对类本身执行某些操作的方法,例如创建类的新实例)

(25)
oc 一般的方法的声明示例:

-(void)setNumerator :(int)n

第一个表示方法类型(对象方法-),返回类型(空void),接着是方法名(包括冒号:),方法接受的参数类型int和参数名n
注:如果不带参数则不用使用“:”号

如果没有指定任何返回类型, 那么默认是id类型, 所有的输入参数默认也是id类型 (id类型可用来引用任何类型的对象,属于万能指针类型) 。

oc 里具有多个参数的方法声明示例:

-/+ (return type) function_name : (parameter type) parameter1 otherParameter : (parameter_type) parameter2;

(26)利用类创建对象
oc里,想执行一些行为,必须写上一个中括号[],方括号左面是类的名称或者该类实例的名称,空格后面是方法(即消息)

[classOrInstance method];

执行Car这个类的new行为来创建对象,分配了内存,每个对象都有自己的存储空间来存储自己的成员变量等元素

youCar = [Car new];//创建了一个Car类的对象,返回对象的地址(返回对象)。之后内存里存在这个对象了。

oc里想操作对象,只能用指针去间接操作!

Car *p = [Car new];//把地址保存到指针里,p指向的是Car类型的对象

给p指向的对象的属性赋值

 p->speed = 200;

(27)内存分析(对象在内存中有成员)
[Car new]每次都会创建出新的对象,并且返回对象的地址,那么就应该用一个指针变量保存对象的地址

Car *c = [Car new];//用一个指针变量c指向内存中的Car对象

设置车子对象的属性,跟用指向结构体的指针访问结构体属性一样,用->

c->wheels = 3;

c->speed = 300;

(28)oc 类成员的访问属性:

oc类属性,默认是@protected,本类内部和继承的类能访问,而外部无法访问,需要手动设置为public。

@public

(29) 和c++的不同,oc的类占据一份内存空间!
在第一次使用类的时候,类被加载到内存里,即在创建对象之前,先给类分配内存空间。
1、存放类的内存只被加载一次(第一次使用对象的时候,加载对象属于的类)即可,且里面只存放方法的列表。

2、内存里每个类的对象的存储空间内部,默认都有一个指针叫isa指针,每个对象都有,作用是:指向这个对象所对应的类(存放类的内存块,帮助找到对象所属的类),所以所有的对象都共用一份方法,所以类只被加载一次即可。成员变量每个对象都有自己的那一份内存,但是方法就共用一份内存

3、调用方法的过程:

[person1 walk]; 

执行:

给指针person1指向的对象发送一条walk消息,去调用那个对象的walk方法,然后对象会顺着isa指针找到对应的类,去类里找方法,找到walk方法,就前往对应的代码去执行,就在walk方法里访问当前对象的成员变量age和weight(因为成员变量,每个对象都有自己的一份)

再次强调:将对象赋给id类型变量不会有问题。

注:无论在哪里,对象总是携带它的isa的保护成员(一个指针,可以用来确定对象所属的类) ,所以即使将它存储在id类型的通用对象变量中,也总是可以确定它的类 。

Object C基础相关推荐

  1. 【亡羊补牢】JS灵魂之问 第18期 修炼内功 Object.creat()基础

    引言 有几天没有更新JS灵魂之问的专栏系列文章了,秋招季,也在忙着备战笔试面试.今天得空再来写一篇文章,本篇要讲解的内容是关于 Object.creat()基础 ,那今天这篇看能不能问倒你了,一起来探 ...

  2. Object c 基础知识

    原地址:http://www.cnblogs.com/gbyukg/p/3265565.html 件类型说明: .h 头文件,用于定义类.实例变量及类中的方法等定义信息(interface). .m ...

  3. PHP5中PDO(PHP DATA OBJECT)模块基础详解

    PHP5自从2004年发布以来PDO就有了,但是现在纵观周边开发的情况还是4世代的mysql或者mysqli占据大部分江山,就像ie6一样.也许改革需要时间的推动,在即将发行的PHP6中PDO会作为默 ...

  4. TypeScript 基础类型

    基础类型 基础类型可以依据是否含有类型关键字分为两类: 含:boolean.number.string.symbol.object.null.undefined.any.never 不含:数组.元组. ...

  5. Object 转 String

    https://zhidao.baidu.com/question/646511027869477405.html?fr=iks&word=Object++%D7%AA++String& ...

  6. 小汤学编程之JavaScript学习day01——认识JS、JS基础语法

    一.认识JS 1.JavaScript的组成     2.浏览器执行js简介     3.JavaScript是什么?     4.扩展内容 二.JS基础语法 1.代码书写位置     2.变量    ...

  7. (整理)Ruby的基础知识

    xzyxuanyuan0我的:收件箱资源博客空间设置|帮助|退出 首页 业界 移动 云计算 研发 论坛 博客 下载 更多 千月星跡 アイをも求めて彷徨っている孤独なヒーロー 目录视图 摘要视图 订阅 ...

  8. LINQEF任我行LinQ to Object

    LinQ to Objects是LinQ家庭的核心,其它的LinQ也使用了与LinQ to Objects相同的查询句法.最终编译器都是把LinQ句法翻译成扩展方法的链式表达式,同时把扩展方法中的la ...

  9. 第13章 LINQ to Object

    第13章 LINQ to Object 在第12章,我们学习了很多C#3的新特性,包括匿名类型.扩展方法.隐式类型等,而这些新特性都是为LNQ服务的. LINQ to Object将查询语句转换为委托 ...

最新文章

  1. CLion 控制台输出内容乱码问题的解决方法
  2. Linux安装python3.6 和pip
  3. CG CTF RE Hello,RE!
  4. 阿里云cloudmonitor服务导致CPU暴增的异常
  5. axios 全局配置
  6. 立方体和球形体积的计算
  7. eclipse的安装与环境配置
  8. 【eoeAndroid特刊】第一期到第十八期
  9. HTML&CSS:制作简易电商网站
  10. 360安全卫士卸载干净-笔记
  11. sqlserver2005 安装图解教程以及SQL 2005 SP3补丁安装图文教程
  12. IDL多进程批处理遥感数据
  13. (十二)c#Winform自定义控件-分页控件
  14. wps office 办公软件下载
  15. Autosar MCAL-GTM之定时输入TIM
  16. 【电子数据取证】8个门道儿
  17. 图表色彩运用原理的全面解析
  18. ATTck 入口点 —— 水坑攻击
  19. ubuntu拨号上网
  20. 钉钉企业内部应用获取登录用户信息

热门文章

  1. 具有路线规划功能的外卖平台(Qt,C++,C/S架构,MySql)
  2. 在线流程图和思维导图开发技术详解(五)
  3. 2023年高新技术企业认定申报注意事项
  4. 微信扫码背后的图像超分辨率技术
  5. disable属性导致后台接收值为null解决方法
  6. Python调用百度AI接口体验人像动漫化
  7. solr mysql 导入命令_Solr 07 - Solr从MySQL数据库中导入数据 (Solr DIH的使用示例)
  8. 2020ICPC上海 C.Sum of Log
  9. unity3d 中能画出漂亮图案的函数之玫瑰图案
  10. 最简单的Greenplum节点扩展操作步骤