类对象存储对象方法,元类对象存储类方法
-
1.给实例对象发送消息的过程(调用对象方法)
- 根据对象的isA指针去该对象的类方法中查找,如果找到了就执行
- 如果没有找到,就去该类的父类类对象中查找
- 如果没有找到就一直往上找,直到跟类(NSObject)
- 如果都没有找到就报错
-
2.给类对象发送消息(调用类方法)
- 根据类对象的isA指针去元对象中查找,如果找到了就执行
- 如果没有找到就去父元对象中查找
- 如果如果没有找到就一直往上查找,直到根类(NSOject)
- 如果都没有找到就报错
@interface Person : NSObject
{
@public
// 属性
int _age;
double _height;
double _weight;
}
// 行为
- (void)eat:(char *)food;
- (void)sleep;
- (void)walk;
+ (void)demo;
@end
@implementation Person
- (void)eat:(char *)food
{
NSLog(@"吃%s", food);
}
- (void)sleep
{
NSLog(@"开始睡觉");
}
- (void)walk
{
NSLog(@"开始遛弯");
}
+(void)demo
{
NSLog(@"demo");
}
@end
int main(int argc, const char * argv[]) {
Person *p = [Person new];
p->_age = 30;
p->_height = 1.75;
p->_weight = 65.0;
NSLog(@"age = %i , height = %f, weight = %f", p->_age, p->_height, p->_weight);
Person *p2 = [Person new];
p2->_age = 50;
p2->_height = 188;
p2->_weight = 100;
return 0;
}
类与对象的存储
1、从Person代码块加载代码
2、系统创建Person类对象,存储在堆区
其中存储当前类中的所有方法(类方法,对象方法)
3、Person *p = [Person new];
[Person new]
- 每new一次,都是实例化一个对象,在堆内存中开辟了一块新的存储空间 对象的地址就是isa的地址(对象的第一个成员),isa指向类对象
new方法的内部会分别调用两个方法来完成3件事情:
(1)使用alloc方法来分配存储空间(返回分配的对象);
alloc 方法为对象分配存储空间,将所有的属性设置为0,返回当前实例对象的地址.
(2)使用init方法来对对象进行初始化。
init方法是初始化方法(构造方法),用来对象成员变量进行初始化,默认实现是一个空方法,返回初始化后的实例对象地址。
alloc 与 init合起来称为构造方法,表示初始化一个对象, 让某个对象一创建出来就拥有某些属性和值
alloc返回的地址, 和init返回的地址是同一个地址
iOS 程序通常使用[[类名 alloc] init] 的方式创建对象,因为这个可以与其他initWithXX:...的初始化方法,统一来。代码更加统一
(3)返回对象的首地址
- 2.初始化成员变量(写在类声明大括号中的属性就叫成员变量,也叫实例变量)
- 3.返回指针地址
Person *p
-
定义一个指向Person类型的指针变量,存储在栈
-
将对象地址赋值给指针变量,即指针指向该对象
调用类方法与对象方法
调用类方法:
直接查看Person类对象的方法,不需要经过Person实例对象
调用对象方法:
指向实例对象的指针-->实例对象isa-->isa指向的类对象-->调用类对象的对象方法
通过isa指针我们可以在运行的时候知道当前对象是属于那个Class(类)的
类方法与对象方法对比:
-
类方法的好处:
- 节省内存空间
- 不依赖于对象,执行效率更高;
- 能用类方法解决的问题,尽量使用类方法;
-
类方法的场合:
- 当方法内部不需要使用到成员变量时,可以改为类方法
- 类方法一般用于编写工具方法
类对象
- 类的本质:
类其实也是一个对象, 这个对象会在这个类第一次被使用的时候创建,在整个程序中只有一份,类名其实就是类对象
只要有了类对象, 将来就可以通过类对象来创建实例对象
实例对象中有一个isa指针, 指向创建自己的类对象
类对象中保存了当前对象所有的对象方法
当给一个实例对象发送消息的时候, 会根据实例对象中的isa指针去对应的类对象中查找
- 如何获取类对象
[实例对象 class];或[类名 class];
Person *p2 = [[Person alloc] init];
Class c2 = [p2 class];
Class c3 = [Person class];
//类对象的应用场景
// 2.1用于创建实例对象
Person *p3 = [[c1 alloc] init];
//2.2用于调用别的类的方法
[Dog test];
Class c = [Dog class];
[c test];