前言
最近在看李明杰的底层视频,每看一点,就想整理下原来的笔记。一整笔记,就又想弄看下苹果的官方文档。一看不要紧,发现要弄的东西好多啊。就想着写篇技术文,写下自己的理解,还有就是自己也可以巩固下。有些注释写的不是很完整,后面再慢慢补充吧!!!
还有就是大家看到的排版可能会比较丑,我自己喜欢用印象笔记,在印象笔记里看的还是蛮好看,有想要的,可以直接联系我,我可以导出给你们!!!以下是我笔记在印象笔记中的样子
屏幕快照 2019-02-10 下午4.24.42.png
框架结构
先说一下,和我原先认知不一样的,NSObject,苹果是把他放在了Object Runtime里面,还有kvc也放在了Object Runtime里。啃爹的KVO居然放到了Notification里。
1549785977607.jpg
1. NSObject Api
我尽量把官方的解释和自己的理解做了注释,但是有些,官方没有解释的。我就没有放到了不知道干啥的这个分类里了。以下是我根据自己的使用习惯的分的类,希望大家喜欢。
1.1 类方法
1.1 类的生命周期
// 类被加载到内存中的时候回调
// Invoked whenever a class or category is added to the Objective-C runtime; implement this method to perform class-specific behavior upon loading.
+ (void)load;
// 类第一个被使用的时候回调
// Initializes the class before it receives its first message.
+ (void)initialize;
1.2 对象生命周期
// 创建一个类的实例
// Returns a new instance of the receiving class.
+ (instancetype)alloc;
// 创建一个对象:等于 +alloc + -init
// Allocates a new instance of the receiving class, sends it an init message, and returns the initialized object.
+ (instancetype)new;
1.3 常用
// 返回一个类对象
// Returns the class object.
+ (Class)class;
// 返回父类的类对象
// Returns the class object for the receiver’s superclass.
+ (Class)superclass;
// 判断调用者是否是一个类的子类
// Returns a Boolean value that indicates whether the receiving class is a subclass of, or identical to, a given class.
+ (BOOL)isSubclassOfClass:(Class)aClass;
// 判断是否有这个方法
// Returns a Boolean value that indicates whether instances of the receiver are capable of responding to a given selector.
+ (BOOL)instancesRespondToSelector:(SEL)aSelector;
// 判断是否遵守了这个协议
// Returns a Boolean value that indicates whether the receiver conforms to a given protocol.
+ (BOOL)conformsToProtocol:(Protocol *)protocol;
1.4 少用
// 一般会重写这个方法,拿来调试用的
// Returns a string that represents the contents of the receiving class.
+ (NSString *)description;
// 恶汉单例会重写这个方法
// Returns a new instance of the receiving class.
+ (instancetype)allocWithZone:(struct _NSZone *)zone;
// 恶汉单例会重写这个方法
// Returns a new instance of the receiving class.
+ (id)copyWithZone:(struct _NSZone *)zone;
// 恶汉单例会重写这个方法
// Returns a new instance of the receiving class.
+ (id)mutableCopyWithZone:(struct _NSZone *)zone;
// 返回这个方法选择器对应的实例IMP指针
// Locates and returns the address of the implementation of the instance method identified by a given selector.
+ (IMP)instanceMethodForSelector:(SEL)aSelector;
// 返回一个NSMethodSignature对象,该对象包含由给定选择器标识的实例方法的描述。
// Returns an NSMethodSignature object that contains a description of the instance method identified by a given selector.
+ (NSMethodSignature *)instanceMethodSignatureForSelector:(SEL)aSelector;
// 调用了一个不存在的类方法的时候回调。
// Dynamically provides an implementation for a given selector for a class method.
+ (BOOL)resolveClassMethod:(SEL)sel;
// 调用了一个不存在的实例方法的时候回调。
// Dynamically provides an implementation for a given selector for an instance method.
+ (BOOL)resolveInstanceMethod:(SEL)sel;
1.5 不知道干嘛的
// 可能是返回一个类的hash值
+ (NSUInteger)hash;
// 返回一个类的调试信息
+ (NSString *)debugDescription;
1.2 实例方法
2.1 生命周期
// 初始化对象
// Implemented by subclasses to initialize a new object (the receiver) immediately after memory for it has been allocated.
- (instancetype)init;
// 一般被重写这个方法,在对象被释放的时候,做一些事情
// Deallocates the memory occupied by the receiver.
- (void)dealloc;
2.2 常用
// 内部会调用 -copyWithZone:
// Returns the object returned by copyWithZone:
- (id)copy;
// 内部会调用 +mutableCopyWithZone
// Returns the object returned by mutableCopyWithZone
- (id)mutableCopy;
2.3 少用
// 找到该方法选择的IMP指针
// Locates and returns the address of the receiver’s implementation of a method so it can be called as a function.
- (IMP)methodForSelector:(SEL)aSelector;
// 返回一个NSMethodSignature对象,该对象包含给定选择器标识的方法的描述。
// Returns an NSMethodSignature object that contains a description of the method identified by a given selector.
- (NSMethodSignature *)methodSignatureForSelector:(SEL)aSelector;
// resolveInstanceMethod: 返回NO的时候执行,指定谁响应这个方法
// Returns the object to which unrecognized messages should first be directed.
- (id)forwardingTargetForSelector:(SEL)aSelector;
// 由子类重写以将消息转发到其他对象。
// Overridden by subclasses to forward messages to other objects.
- (void)forwardInvocation:(NSInvocation *)anInvocation;
// 处理接收方无法识别的消息。
// Handles messages the receiver doesn’t recognize.
- (void)doesNotRecognizeSelector:(SEL)aSelector;
2.3 不知道干啥的
- (BOOL)allowsWeakReference UNAVAILABLE_ATTRIBUTE;
- (BOOL)retainWeakReference UNAVAILABLE_ATTRIBUTE;
2. <NSObject> 协议的APi
这里写的,都是大家常用的,就没写的那么详细了。
3.1 常用
@property (readonly) Class superclass;
@property (readonly, copy) NSString *description;
- (instancetype)self;
- (Class)class;
- (BOOL)isKindOfClass:(Class)aClass;
- (BOOL)isMemberOfClass:(Class)aClass;
- (BOOL)conformsToProtocol:(Protocol *)aProtocol;
- (BOOL)respondsToSelector:(SEL)aSelector;
// 判断两个对象是否相等:先走hash方法,再走isEqual方法
@property (readonly) NSUInteger hash;
- (BOOL)isEqual:(id)object;
3.2 optional 可选
@property (readonly, copy) NSString *debugDescription;
3.3 消息相关
- (id)performSelector:(SEL)aSelector;
- (id)performSelector:(SEL)aSelector withObject:(id)object;
- (id)performSelector:(SEL)aSelector withObject:(id)object1 withObject:(id)object2;
3.4 ARC不可用
- (instancetype)retain OBJC_ARC_UNAVAILABLE;
- (oneway void)release OBJC_ARC_UNAVAILABLE;
- (instancetype)autorelease OBJC_ARC_UNAVAILABLE;
- (NSUInteger)retainCount OBJC_ARC_UNAVAILABLE;
- (struct _NSZone *)zone OBJC_ARC_UNAVAILABLE;
3.5 不知道干啥用的
- (BOOL)isProxy;
3. NSObject(NSKeyValueCoding)
这里是KVC,苹果是把KVC的接口,放到了NSObject的分类里了
// 一种机制,通过该机制可以通过名称或键间接访问对象的属性。
A mechanism by which you can access the properties of an object indirectly by name or key.
4.1 Getting Values 取值
—> ForKey
- (nullable id)valueForKey:(NSString *)key;
- (BOOL)validateValue:(inout id _Nullable * _Nonnull)ioValue forKey:(NSString *)inKey error:(out NSError **)outError;
- (NSMutableArray *)mutableArrayValueForKey:(NSString *)key;
- (NSMutableOrderedSet *)mutableOrderedSetValueForKey:(NSString *)key API_AVAILABLE(macos(10.7), ios(5.0), watchos(2.0), tvos(9.0));
- (NSMutableSet *)mutableSetValueForKey:(NSString *)key;
- (NSDictionary<NSString *, id> *)dictionaryWithValuesForKeys:(NSArray<NSString *> *)keys;
—> ForKeyPath
- (nullable id)valueForKeyPath:(NSString *)keyPath;
- (BOOL)validateValue:(inout id _Nullable * _Nonnull)ioValue forKeyPath:(NSString *)inKeyPath error:(out NSError **)outError;
- (NSMutableArray *)mutableArrayValueForKeyPath:(NSString *)keyPath;
- (NSMutableOrderedSet *)mutableOrderedSetValueForKeyPath:(NSString *)keyPath API_AVAILABLE(macos(10.7), ios(5.0), watchos(2.0), tvos(9.0));
- (NSMutableSet *)mutableSetValueForKeyPath:(NSString *)keyPath;
4.2 Setting Values 设值
- (void)setValue:(nullable id)value forKey:(NSString *)key;
- (void)setNilValueForKey:(NSString *)key;
- (void)setValue:(nullable id)value forKeyPath:(NSString *)keyPath;
- (void)setValuesForKeysWithDictionary:(NSDictionary<NSString *, id> *)keyedValues;
4.3 异常处理
- (nullable id)valueForUndefinedKey:(NSString *)key;
- (void)setValue:(nullable id)value forUndefinedKey:(NSString *)key;
4.4 other
@property (class, readonly) BOOL accessInstanceVariablesDirectly;
4.5 案例
—-> 0. 准备
// 准备一个数值数据
NSArray *values = @[@"1",@"2",@"3",@"4",@"a",@"4”];
// 准备数据
NSArray *dictArr = @[@{@"name":@"hare1",@"age":@(21)},
@{@"name":@"hare2",@"age":@(22)},
@{@"name":@"hare3",@"age":@(23)},
@{@"name":@"hare4",@"age":@(24)},
@{@"name":@"hare4",@"age":@(24)}];
NSArray *stuArr = @[[Student studentWithName:@"hare5" andAge:25],
[Student studentWithName:@"hare6" andAge:26],
[Student studentWithName:@"hare7" andAge:27],
[Student studentWithName:@"hare8" andAge:28],
[Student studentWithName:@"hare9" andAge:29]];
NSArray *stuDictArr = @[@{@"hare10":[Student studentWithName:@"hare10" andAge:10]},
@{@"hare11":[Student studentWithName:@"hare11" andAge:11]},
@{@"hare11":[Student studentWithName:@"hare11" andAge:12]},
@{@"hare13":[Student studentWithName:@"hare13" andAge:13]},
@{@"hare12":[Student studentWithName:@"hare14" andAge:14]}];
—-> 1. 数值
// 求和,结果:14
int sum = [[values valueForKeyPath:@"@sum.intValue"] intValue];
// 求最小值,结果:0
int min = [[values valueForKeyPath:@"@min.intValue"] intValue];
// 求最大值,结果:4
int max = [[values valueForKeyPath:@"@max.intValue"] intValue];
// 求平均值,结果:4
int avg = [[values valueForKeyPath:@"@avg.intValue"] intValue];
// 去重,结果:[3,1,4,2,a]
NSArray *result = [values valueForKeyPath:@"@distinctUnionOfObjects.self”];
—-> 2. 对象
// 提取字典数组中的所有dict[@“name”]的值
NSArray *result = [dictArr valueForKeyPath:@"name”]
// 提取字典数组中的所有dict[@“name”]的值,并将结果去重
NSArray *result = [dictArr valueForKeyPath:@"@[distinctUnionOfObjects.name](http://distinctunionofobjects.name/)"]
// 提取对象数组中的所有对象的“name”属性值
NSArray *result = [stuArr1 valueForKeyPath:@"name”]
// 提取对象数组中的 包含有“hare11”的key的字典 中的“name”的值
NSArray *result = [stuArr2 valueForKeyPath:@"[hare11.name](http://hare11.name/)”]
NSObject(NSKeyValueObserving)
这里是KVO相关的,因为刚好看到这一块,所以写的比较详细
// 对象采用的非正式协议,用于通知其他对象的指定属性的更改。
An informal protocol that objects adopt to be notified of changes to the specified properties of other objects.
5.1 NSObject(NSKeyValueObserving)
// 当相对于观察对象的指定键路径处的值发生更改时,通知观察对象。
// Informs the observing object when the value at the specified key path relative to the observed object has changed.
- (void)observeValueForKeyPath:(nullable NSString *)keyPath ofObject:(nullable id)object change:(nullable NSDictionary<NSKeyValueChangeKey, id> *)change context:(nullable void *)context;
5.2 NSObject(NSKeyValueObserverRegistration)
// 停止观察者对象接收由关键路径指定的属性相对于接收此消息的对象的更改通知。
// Stops the observer object from receiving change notifications for the property specified by the key path relative to the object receiving this message.
- (void)removeObserver:(NSObject *)observer forKeyPath:(NSString *)keyPath;
// 在给定上下文的情况下,停止观察者对象接收由关键路径指定的属性相对于接收此消息的对象的更改通知。
// Stops the observer object from receiving change notifications for the property specified by the key path relative to the object receiving this message, given the context.
- (void)removeObserver:(NSObject *)observer forKeyPath:(NSString *)keyPath context:(nullable void *)context;
// 注册观察者对象以接收相对于接收此消息的对象的密钥路径的KVO通知。
// Registers the observer object to receive KVO notifications for the key path relative to the object receiving this message.
- (void)addObserver:(NSObject *)observer forKeyPath:(NSString *)keyPath options:(NSKeyValueObservingOptions)options context:(nullable void *)context;
5.3 NSObject(NSKeyValueObserverNotification)
// 通知被观察对象,给定属性的值即将发生变化。
// Informs the observed object that the value of a given property is about to change.
- (void)willChangeValueForKey:(NSString *)key;
// 通知被观察对象给定属性的值已更改。
// Informs the observed object that the value of a given property has changed.
- (void)didChangeValueForKey:(NSString *)key;
// 通知观察到的对象,指定的更改将在指定的有序到多对关系的给定索引处执行。
// Informs the observed object that the specified change is about to be executed at given indexes for a specified ordered to-many relationship.
- (void)willChange:(NSKeyValueChange)changeKind valuesAtIndexes:(NSIndexSet *)indexes forKey:(NSString *)key;
// 通知观察到的对象已在指定的有序多对多关系的索引上发生了指定的更改。
// Informs the observed object that the specified change has occurred on the indexes for a specified ordered to-many relationship.
- (void)didChange:(NSKeyValueChange)changeKind valuesAtIndexes:(NSIndexSet *)indexes forKey:(NSString *)key;
// 通知观察到的对象,即将对指定的无序多对多关系进行指定的更改。
// Informs the observed object that the specified change is about to be made to a specified unordered to-many relationship.
- (void)willChangeValueForKey:(NSString *)key withSetMutation:(NSKeyValueSetMutationKind)mutationKind usingObjects:(NSSet *)objects;
// 通知观察对象指定的更改是针对指定的无序多对多关系。
// Informs the observed object that the specified change was made to a specified unordered to-many relationship.
- (void)didChangeValueForKey:(NSString *)key withSetMutation:(NSKeyValueSetMutationKind)mutationKind usingObjects:(NSSet *)objects;
5.4 NSObject(NSKeyValueObservingCustomization)
// 返回一个指针,该指针标识有关向观察对象注册的所有观察者的信息。
// Returns a pointer that identifies information about all of the observers that are registered with the observed object.
@property (nullable) void *observationInfo;
// 返回一个布尔值,指示观察对象是否支持给定键的自动键值观察。
// Returns a Boolean value that indicates whether the observed object supports automatic key-value observation for the given key.
+ (BOOL)automaticallyNotifiesObserversForKey:(NSString *)key;
// 返回其值影响指定键值的属性的一组键路径。
// Returns a set of key paths for properties whose values affect the value of the specified key.
+ (NSSet<NSString *> *)keyPathsForValuesAffectingValueForKey:(NSString *)key;
网友评论