[英]Getting the min/max coordinates of NSValue transformed CGPoints in an NSArray using KVC
我最近阅读了一些关于Key-Value Coding
文档和一些博客文章,发现它非常有用。 我想把它用于我的案子,但到目前为止我还没有成功。
在我的例子中,我有一个NSMutableArray
包含CGPoint
转换为NSValue
的。 我将为这个数据数组添加许多点,我想获得最小/最大x和y值。 例如:
NSMutableArray *data = [[NSMutableArray alloc] init];
[data addObject:[NSValue valueWithCGPoint:CGPointMake(20.0f, 10.0f)]];
[data addObject:[NSValue valueWithCGPoint:CGPointMake(5.0f, -15.0f)]];
[data addObject:[NSValue valueWithCGPoint:CGPointMake(-5.0f, 20.0f)]];
[data addObject:[NSValue valueWithCGPoint:CGPointMake(15.0f, 30.0f)]];
// min X: -5.0, max X: 20.0
// min Y: -15.0, max Y: 30.0
到目前为止我有两种方法。 第一个是将这四个值存储在类实例变量中,并在添加新对象时将其与这些变量进行比较,并在必要时更新它们。 第二个涉及for循环以找到极值,但是这种方法效率低下。
如果可能的话,我想使用KVC来完成这项任务,我相信这将是一个比我的更普遍的解决方案。 在将来,我可能还需要从数组中删除一些对象,这将使我的第一个方法不适用,而我剩下的就是for-loop。
我尝试使用一些关键路径,即@"@max.x"
, @"@max.position.x"
但我得到的只是一个NSUnknownKeyException
。
如果您使用类别告诉NSValue
如何访问CGPoint
的x
和y
值,您可以使它工作:
@interface NSValue (MyKeyCategory)
- (id)valueForKey:(NSString *)key;
@end
@implementation NSValue (MyKeyCategory)
- (id)valueForKey:(NSString *)key
{
if (strcmp([self objCType], @encode(CGPoint)) == 0) {
CGPoint p = [self CGPointValue];
if ([key isEqualToString:@"x"]) {
return @(p.x);
} else if ([key isEqualToString:@"y"]) {
return @(p.y);
}
}
return [super valueForKey:key];
}
@end
然后
CGFloat maxx = [[yourArray valueForKeyPath:@"@max.x"] floatValue];
实际上有效。 但请注意,一个简单的循环会更快,特别是如果你必须计算所有4个值@max.x
, @max.y
, @min.x
, @min.y
使用您当前的方法这是不可能的。 CGPoint
不是obj-c对象,因此您无法通过KVC探索其值。 NSValue
将CGPoint
视为二进制数据,并且没有对数据的内部结构进行任何理解。 编译后甚至无法访问CGPoint
字段的名称x
和y
。
(KVC可以访问CGPoint
值的唯一例外是CAAnimation
和CALayer
,它们会覆盖键值搜索)。
可能最好的解决方案是自己实现它,注意你可以做一些聪明的缓存 - 在添加点时测试当前最大/最小值,并在移除当前最小值/最大值时清除最小值/最大值。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.