更新
好的,首先,感谢大家的大量事件。似乎我没有很好地表达我的问题,因为许多答案(正确地)停留在 id 输入参数上,并且遵循糟糕的设计模式,但这只是一个示例。我将为我的问题添加一些上下文:
- 假设
doSomethingWithParameter: 有多种不同的实现,需要一个特定的实例作为输入参数
- 示例中的我的类只会使用
SpecificClass 的实例作为输入参数调用
通过这些断言,这是我的假设:鉴于您知道参数的类型,类型检查和强制转换没有任何好处,只是为了额外的安全。 p>
原帖
假设我的协议(protocol)声明中有一个通用方法,它采用 id 输入参数:
@protocol MyProtocol <NSObject>
- (void)doSomethingWithParameterid)inputParameter;
@end
在符合 MyProtocol 的类中,我通常更喜欢像这样明确 inputParameter 的类型:
- (void)doSomethingWithParameterSpecificClass *)inputParameter
{
/... do something with param
}
有时我因选择此解决方案而受到批评,而不是以下:
- (void)doSomethingWithParameterid)inputParameter
{
if ([inputParameter isKindOfClass:[SpecificClass class]]) {
SpecificClass *myInstance = (SpecificClass *)inputParameter;
/... do something with param
}
}
我真的更喜欢第一个版本,因为它清楚地说明了我的实例所期望的参数。它更简洁,更清晰。我通常认为我不能从类型检查/强制转换中获得太多 yield 。
我的问题:从编码标准的角度来看,哪一个是更好的解决方案?第一个有什么缺点吗?
Best Answer-推荐答案 strong>
更新
从您的问题的更新来看,您似乎正在尝试实现现代语言中泛型提供的功能的某些变体。
由于 Objective-C 不支持这种模式,您可以牺牲类型安全,或者重新考虑您的设计决策。
如果您选择第一种方式,则应通过其他方式(命名、文档)真正明确您期望的类型。那么假设您的方法只会使用适当的参数调用可能是合理的。
但我仍然会添加 NSParameterAssert 以简化将来的调试。
原答案
如果您使用第一种方法,则方法的声明和定义不匹配。由于 obj-c 的动态特性(方法签名不包括参数类型),编译器不会提示它。
然而,当调用方法时,只有声明是可见的,所以任何关于参数类型的信息都是从它派生的——所有的类型检查(是的,这里是编译器做的)都是基于声明执行的。
总之,为了避免混淆错误和滥用 API,您绝对应该使用第二种方法。或者将声明与定义一起更改。
编辑
另外,我可以想到第三种解决方案,它在某种程度上融合了第一种方法的便利性和第二种方法的类型安全:
- (void)doSomethingWithParameterSpecificClass *)inputParameter
{
NSParameterAssert([inputParameter isKindOfClass:[SpecificClass class]]);
// do something
}
关于ios - Objective-C 中的转换方法参数,我们在Stack Overflow上找到一个类似的问题:
https://stackoverflow.com/questions/30095591/
|