I've been checking out iOS 9 new features as a developer and some of them like the StackView look awesome.
When I went the the header file of UIStackView I saw this:
@property(nonatomic,readonly,copy) NSArray<__kindof UIView *> *arrangedSubviews;
What is the __kindof on NSArray*. Are we able to specify a type on a NSArray * now?
Little test:
@interface DXTEST () @property (strong, nonatomic) NSMutableArray <__kindof NSString *> *strings; @end @implementation DXTEST - ( instancetype ) init { self = [super init]; if( self ) { _strings = [NSMutableArray new]; [_strings addObject:@(1)]; <-- compiler warning wieeeeee } return self; } @end
NSArray creates static arrays, and NSMutableArray creates dynamic arrays. You can use arrays when you need an ordered collection of objects. NSArray is “toll-free bridged” with its Core Foundation counterpart, CFArrayRef . See Toll-Free Bridging for more information on toll-free bridging.
The main difference is that NSArray is for an ordered collection and NSSet is for an unordered collection. There are several articles out there that talk about the difference in speed between the two, like this one. If you're iterating through an unordered collection, NSSet is great.
arrays can't contain nil.
Sadly the currently top voted answers are a bit incorrect.
You actually can add any subclass of <T>
to a generic collection:
@interface CustomView : UIView @end @implementation CustomView @end NSMutableArray<UIView *> *views; UIView *view = [UIView new]; CustomView *customView = [CustomView new]; [views addObject:view]; [views addObject:customView];//compiles and runs!
But when you'll try to retrieve the object, it will be strictly typed as <T>
and will require casting:
//Warning: incompatible pointer types initializing //`CustomView *` with an expression of type `UIView * _Nullable` CustomView *retrivedView = views.firstObject;
But if you'll add __kindof
keyword the returned type will be changed to kindof T
and no casting will be required:
NSMutableArray<__kindof UIView *> *views; <...> CustomView *retrivedView = views.firstObject;
TLDR: Generics in Objective-C can accept subclasses of <T>
, __kindof
keyword specifies that return value can also be subclass of <T>
.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With