根据 Xcode 发行说明,Apple 一直在“审核”他们现有的 API,以删除隐式展开的可选值。这意味着他们的 API 将在适当的地方返回 T
或 T?
而不是 T!
。
他们在哪里做这件事?我如何注释/包装我现有的 Objective-C 代码(尤其是库)以使其更易于在 Swift 中使用?
最佳答案
Xcode 6.3/swift 1.2
Xcode 6.3 添加了对在 Objective-C 中注释可空性的官方支持。
可空性
可以通过使用关键字 __nullable
注释类型来声明值的可空性。 , __nonnull
和 __null_unspecified
(默认值)。在属性和方法中,关键字是 nullable
, nonnull
和 null_unspecified
.
Xcode 发行说明中的示例
- (void)registerNib:(nonnull UINib *)nib
forCellReuseIdentifier:(nonnull NSString *)identifier;
- (nullable UITableViewCell *)cellForRowAtIndexPath:(nonnull NSIndexPath)indexPath;
@property (nonatomic, readwrite, retain, nullable) UIView *backgroundView;
更改默认值
null_unspecified
(转换为 T!
)是所有现有代码的默认值。一项有用的功能是能够更改 API 部分的默认值。
NS_ASSUME_NONNULL_BEGIN
// nonnull is the default here
NS_ASSUME_NONNULL_END
这消除了很多噪音,因为接受和处理 nil 的方法通常是异常(exception),而不是规则。就个人而言,我会将其用于所有经过审核的 API。
null_resettable
null_resettable
是一个附加注释,用于您可以将 属性设置为 nil 的罕见情况,但它永远不会 nil(因为它重置为默认值)。
@property (nonatomic, retain, null_resettable) UIColor *tintColor;
就个人而言,我会在新代码中避免这种行为。此类属性的混合性质不适合 Swift。
Xcode 7/Swift 2(测试版)
Xcode 7 添加了对在 Objective-C 中注释泛型类型的支持。
集合的通用类型注释
NSArray
, NSSet
和 NSDictionary
(自动桥接到 Swift 的 Array
、 Set
和 Dictionary
可以用它们的内容类型进行注释。
@property NSArray<NSString *> *stringArray;
@property NSSet<NSString *> *stringSet;
@property NSDictionary<NSString *, NSString *> *stringDict;
还有 __kindof
告诉 Objective-C 编译器不那么严格并允许向下转换的关键字。但它不会影响 Swift 方面。
自定义类的通用类型注释
@interface MyArray1<__covariant T> : NSObject
- (void)addObject:(T)object;
@end
@interface MyArray2<__covariant T : NSObject *> : NSObject
- (void)addObject:(T)object;
@end
@interface MyArray3<__covariant T : id<NSCopying>> : NSObject
- (void)addObject:(T)object;
@end
@implementation
不知道 T
并使用 id
/NSObject *
/id<NSCopying>
一如既往。
关于objective-c - 如何注释 Objective-C API 以便在 Swift 中使用(例如返回类型),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25747377/