在块中返回非指针对象时出现问题

Posted

技术标签:

【中文标题】在块中返回非指针对象时出现问题【英文标题】:Trouble when returning non pointer object in a block 【发布时间】:2013-11-19 23:32:16 【问题描述】:

我正在使用 Mantle 帮助我将模型对象转换为 JSON。我的一个对象包含一个centroid 属性,定义如下:

@property (assign) CLLocationCoordinate2D centroid;

当我与服务器打交道时,我收到这种格式的属性:

centroid: 
      lat: "38.416600086777166",
      lon: "-88.29868011101323"
    

所以我决定实现一个自定义 JSON 转换器,该转换器在 MTLJSONSerializing 协议中可用,定义如下:

+ (NSValueTransformer*)centroidJSONTransformer 
    return [MTLValueTransformer transformerWithBlock:^CLLocationCoordinate2D(NSDictionary *dict) 
        NSNumber *latitude = dict[@"lat"];
        NSNumber *longitude = dict[@"lon"];

        return CLLocationCoordinate2DMake([latitude doubleValue], [longitude doubleValue]);
    ];

我遇到的问题是MTLValueTransformer 内部的+ (instancetype)transformerWithBlock:(MTLValueTransformerBlock)transformationBlock 方法接受typedef id (^MTLValueTransformerBlock)(id); 类型的块,它返回id 类型的值或任何objective-c 指针对象。

但是我想做的是返回 CLLocationCoordinate2D 类型,它是一个标量,非id 类型。没有定义我自己的 transformerWithBlock: 自定义实现,有没有一种干净的方法可以实现这一点?

【问题讨论】:

尝试用NSValue包装它 哪个 API? NSValue 的唯一通用 API 是 + valueWithNonretainedObject:,它接受 id 类型的对象而不是标量。 @AndrewLauerBarinov,看看我的回答,但那不是真的。 NSValue 有几种包装各种值的方法,包括任意标量值、指针和 NSRange。 +valueWithNonretainedObject: 可能是 NSValue 便利函数中使用最少的。 是的@AndrewMadsen 我现在注意到了。我只是在查看自动完成功能中可用的 API。 【参考方案1】:

您可以将原始/标量值包装在 NSValue 中,以将它们传递到/从方法、函数或块传递到期望 id 的块:

NSValue *value = [NSValue valueWithBytes:&coordinate objCType:@encode(CLLocationCoordinate2D)];

然后,让CLLocationCoordinate2D 退出:

CLLocationCoordinate2D coordinate;
[value getValue:&coordinate];

ios 6 开始(大概是 OS X 10.8,虽然我还没有检查),有 NSValue MapKit Additions category 向 NSValue 添加方法来包装和解开 CLLocationCoordinate2Ds:

NSValue *value = [NSValue valueWithMKCoordinate:coordinate];
CLLocationCoordinate2D coordinate = [value MKCoordinateValue];

【讨论】:

很好的答案。谢谢!

以上是关于在块中返回非指针对象时出现问题的主要内容,如果未能解决你的问题,请参考以下文章

Android ViewBinding 有时会在绑定对象处返回 null,因此在尝试访问视图时出现空指针异常

AFHttpclient 在块中获取 json 主体但外部函数返回 null

尝试在块中保存对象时崩溃。 (CoreData 无法满足...的错误)

如何在块外快速创建指向自身的弱指针

返回指针时出现分段错误[关闭]

返回指针时出现分段错误[重复]