一、类的定义
Student.h
#import <Foundation/Foundation.h>
@interface Student : NSObject{
@public
NSString * _name;
int _age;
NSString * _hobby; // aihao
NSString * _address;
}
-(void) sayHello;
-(void) eat;
// getter / setter
@property (getter = getName,assign,nonatomic) NSString * _name;
@property (assign,nonatomic) NSString * _hobby;
@property (getter = getAddress,setter = setAddress:) NSString * _address;
@property int age;
//
@end
成员变量定义:
在objc中,把成员变量定义在一个{ }花括号中,并且可以为成员变量加上可见性前缀 public | private | protected;方法定义:
方法定义的通用格式( -)+(返回值)+(方法名)+(参数列表);
属性定义:
属性定义通过 @property 标注来快速定义 类的getter和setter方法,标注了property的成员变量默认会生成setXXXValue()方法,如果想要生成getXXXValue方法,需要向property标注指定额外的参数;
Student.m
#import "Student.h"
@implementation Student
-(void) sayHello{
NSLog(@"hello da jia hao,wo shi %@, %d years old", _name,_age);
}
-(void) eat{
NSLog(@"wo xiang chi fan. %@", _name);
}
// getter / setter implement
@synthesize _name = name,_address = address,_hobby = hobby;
@end
在objc的类的实现文件中,需要把接口文件中定义的方法实现,如果接口文件中通过 @property 定义了属性,则需要在实现文件中通过 @synthesize 标注来生成 @property指定的属性getter或是setter;
属性设置参数
1、原子性属性:
nonatomic 非原子性,不保证多线程安全。
atomic 原子性,多线程访问时较安全。默认
2、setter 语义属性
assign 直接赋值 适用于基本数据类型。
retain 赋值时做内存优化 适用于对象类型。
copy 复制一个副本 适用于特殊的对象类型。
3、读写属性
readwrite 可读写(既有设置器也有访问器)默认。
readonly 只读(只有访问器没有设置器)。
getter = 方法名 指定访问器的方法名。
setter = 方法名 指定设置器的方法名。
二、类的继承
CollegeStudent.h
@interface CollegeStudent : Student
{
@public NSString * _magor;
}
// init method
-(id) initWithName:(NSString *)name;
-(CollegeStudent *) initWithNameAndAge:(NSString *)name
age:(int)age;
@end
定义一个CollegeStudent类,继承自Student类,该类接口文件定义了两个快速初始化方法;
CollegeStudent.m
#import "CollegeStudent.h"
@implementation CollegeStudent
//
-(void) eat{
NSLog(@"I'm a collegeStudent,I need't eat at all");
}
//
-(id) initWithName:(NSString *)name{
// call super init
self = [super init];
if(self){
_name = name;
}
return self;
}
//
-(CollegeStudent *) initWithNameAndAge:(NSString *)name age:(int)age{
// call method which has called super init
self = [self initWithName:name];
if(self){
_age = age;
}
return self;
}
@end
在快速初始化方法中,我们需要调用 [super init] 或者是已经调用了 [super init] 的快速初始化方法;
需要注意的是,快速初始化方法的返回类型只能是 id 或者是 本类的指针;
三、单例
Teacher.h
#import <Foundation/Foundation.h>
@interface Teacher : NSObject{
@public NSString *name;
}
+(id)getInstance;
@end
单例模式是指整个应用中只出现一个该类的实例对象,通常用getInstance()方法来表示;
Teacher.m
#import "Teacher.h"
@implementation Teacher
static Teacher *teacher1;
// Singleton getInstance
+(id)getInstance{
// static id teacher1 = nil;
if(teacher1 == nil){
NSLog(@"getInstance");
teacher1 = [[Teacher alloc]init];
}
return teacher1;
}
// override
+(id)allocWithZone:(struct _NSZone *)zone{
if( teacher1 == nil){
teacher1 = [super allocWithZone:zone];
teacher1->name = @"Teacher_Zone";
return teacher1;
}
return nil;
}
@end
单例模式的实现步骤:
- 在实现文件中定义一个静态的本类的指针;
- 实现getInstance方法;
- 重写allocWithZone方法;
需要注意的是,在单例模式中,方法的定义和之前的方法定义格式不一样,这里用的是 + 号,这其实是两种方法的标识, - 号定义的方法需要通过类的实例才能调用,而 + 号定义的方法通过类名就能调用,类似java中的静态方法和成员方法的关系;
四、Demo
上面我们定义了几个类,以及实现他们的一些方法,现在我们就来通过一个demo来看如何去调用它们;
@autoreleasepool {
// create a obj(Student);
Student *stu = [[Student alloc]init];
stu->_name = @"ccflying";
stu->_age = 24;
// call method eat;
[stu eat];
// CollegeStudent initWithName
CollegeStudent *collegestu = [[CollegeStudent alloc]initWithName:@"ccflying"];
[collegestu eat];
NSLog(@"collegestu[name=%@]",collegestu->_name);
// CollegeStudent initWithNameAndAge
collegestu = [[CollegeStudent alloc] initWithNameAndAge:@"ccflying" age:24];
// Log name and age
NSLog(@"collegestu[name=%@,age=%d]",collegestu->_name,collegestu->_age);
// getter / setter
NSLog(@"collegestu getName=%@",[collegestu getName]);
// set name
[collegestu set_name:@"my name"];
NSLog(@"collegestu getName=%@",[collegestu getName]);
// set address
[collegestu setAddress:@"my address"];
NSLog(@"collegestu getAddress=%@",[collegestu getAddress]);
// point grammar
collegestu._address = @"my newAddress";
NSLog(@"collegestu getAddress=%@", collegestu.getAddress);
NSLog(@"collegestu age=%d", collegestu.age);
// SingleTon
Teacher *tea = [Teacher getInstance];
NSLog(@"%@",tea->name);
// changeName
tea->name = @"New_Name";
tea = [Teacher getInstance];
NSLog(@"%@",tea->name);
}
上面这段代码的log输入信息为
2015-06-22 09:10:50.143 ObjC01[5339:303] wo xiang chi fan. ccflying
2015-06-22 09:10:50.154 ObjC01[5339:303] I'm a collegeStudent,I need't eat at all
2015-06-22 09:10:50.155 ObjC01[5339:303] collegestu[name=ccflying]
2015-06-22 09:10:50.173 ObjC01[5339:303] collegestu[name=ccflying,age=24]
2015-06-22 09:10:50.176 ObjC01[5339:303] collegestu getName=(null)
2015-06-22 09:10:50.176 ObjC01[5339:303] collegestu getName=my name
2015-06-22 09:10:50.179 ObjC01[5339:303] collegestu getAddress=my address
2015-06-22 09:10:50.182 ObjC01[5339:303] collegestu getAddress=my newAddress
2015-06-22 09:10:50.183 ObjC01[5339:303] collegestu age=24
2015-06-22 09:10:50.184 ObjC01[5339:303] getInstance
2015-06-22 09:10:50.185 ObjC01[5339:303] Teacher_Zone
2015-06-22 09:10:50.186 ObjC01[5339:303] New_Name
注意 point grammar(点语法)
点语法是指通过对象obj.xxx来设置或者获取一个属性的值,要想能够使用点语法,当然也就得使用属性 property;