瞭解位移枚舉以前,咱們先回顧一下C語言位運算符。git
1 << : 左移,好比1<<n,表示1往左移n位,即數值大小2的n次方; 例如 : 0b0001 << 1 變爲了 0b0010 2 >> : 右移,相似左移,數值大小除以2的n次方 3 & : 按位與,1與任意數等於任意數自己,0與任意數等於0,即1&x=x,0&x=0 4 | : 按位或,x|y中只要有一個1則結果爲1;反之爲0 5 ^ : 按位異或,x^y相等則爲0,不等則爲1
開發中,你也許見到過或用過相似這種的枚舉類型:github
typedef NS_OPTIONS(NSUInteger, BDRequestOptions) { BDRequestOptionSuccess = 1 << 0, // 1 BDRequestOptionFailure = 1 << 1, // 2 BDRequestOptionProcessing = 1 << 2, // 4 BDRequestOptionAnimate = 1 << 3, // 8 };
這種枚舉類型,稱之爲按位掩碼(bitmask),他的語法和枚舉相同。測試
從枚舉定義來看,NS_ENUM和NS_OPTIONS本質是同樣的,而iOS使用兩種方式定義的目的是區分使用場景 : 是否能夠多選spa
NS_OPTION枚舉 : 多個枚舉值同時使用按位或( | )相加表示進行多選操做。位移不一樣位數獲得值不一樣即數值表明的枚舉值不一樣,多個枚舉同時使用仍具備惟一性。code
NS_ENUM枚舉 : 不可多選,惟一互斥性。blog
示例:開發
// 首先定義一組 typedef NS_OPTIONS(NSUInteger, BDRequestOptions) { BDRequestOptionSuccess = 1 << 0, BDRequestOptionFailure = 1 << 1, BDRequestOptionProcessing = 1 << 2, BDRequestOptionAnimate = 1 << 3, }; // 而後調用咱們定義的方法 #pragma mark - View lifeCycle - (void)viewDidLoad { [super viewDidLoad]; self.view.backgroundColor = [UIColor orangeColor]; [self test:BDRequestOptionSuccess | BDRequestOptionFailure | BDRequestOptionProcessing | BDRequestOptionAnimate]; } - (void)test:(BDRequestOptions)type { if (type & BDRequestOptionSuccess) { NSLog(@"BDRequestOptionSuccess"); } if (type & BDRequestOptionFailure) { NSLog(@"BDRequestOptionFailure"); } if (type & BDRequestOptionProcessing) { NSLog(@"BDRequestOptionProcessing"); } if (type & BDRequestOptionAnimate) { NSLog(@"BDRequestOptionAnimate"); } } // 查看打印結果: 2016-04-04 14:09:44.946 OC測試[5869:719056] BDRequestOptionSuccess 2016-04-04 14:09:44.947 OC測試[5869:719056] BDRequestOptionFailure 2016-04-04 14:09:44.947 OC測試[5869:719056] BDRequestOptionProcessing 2016-04-04 14:09:44.947 OC測試[5869:719056] BDRequestOptionAnimate
分析:get
// 首先定義一組 typedef NS_OPTIONS(NSUInteger, BDRequestOptions) { BDRequestOptionSuccess = 0b0001 << 0, BDRequestOptionFailure = 0b0010 << 1, BDRequestOptionProcessing = 0b0100 << 2, BDRequestOptionAnimate = 0b1000 << 3, }; #pragma mark - View lifeCycle - (void)viewDidLoad { [super viewDidLoad]; self.view.backgroundColor = [UIColor orangeColor]; [self test:BDRequestOptionSuccess | BDRequestOptionFailure | BDRequestOptionProcessing | BDRequestOptionAnimate]; /** BDRequestOptionSuccess | BDRequestOptionFailure | BDRequestOptionProcessing | BDRequestOptionAnimate 等同於:0b0001 | 0b0010 | 0b0100 | 0b1000 結果爲:0b1111 */ } - (void)test:(BDRequestOptions)type { // 0b1111 & 0b0001 ---> 0b0b0001 if (type & BDRequestOptionSuccess) { NSLog(@"BDRequestOptionSuccess"); } // 0b1111 & 0b0010 ---> 0b0b0010 if (type & BDRequestOptionFailure) { NSLog(@"BDRequestOptionFailure"); } // 0b1111 & 0b0100 ---> 0b0b0100 if (type & BDRequestOptionProcessing) { NSLog(@"BDRequestOptionProcessing"); } // 0b1111 & 0b1000 ---> 0b0b1000 if (type & BDRequestOptionAnimate) { NSLog(@"BDRequestOptionAnimate"); } }
另,默認的,若是開發中枚舉值傳0,意味着不作任何操做。string
例如:it
// 傳0,不打印任何值 [self test:0];
具體用途:
// 如下所說的 0 或 1,均指二進制數字中的 0 或 1 // 一、賦值。 self.requestOption = BDRequestOptionSuccess | BDRequestOptionFailure | BDRequestOptionProcessing | BDRequestOptionAnimate; // 二、判斷是否包含。 // &:按位與,1與任意數等於任意數自己,0與任意數等於0,即1&x=x,0&x=0 if (self.requestOption & BDRequestOptionSuccess) { NSLog(@"已包含了該枚舉值"); } else { NSLog(@"不包含該枚舉值"); } // 三、累加。 累加已經累加過的枚舉值, 雖然枚舉變量的值不會有變更,但這樣將會誤導閱讀代碼的人。 // |: 按位或,x|y中只要有一個1則結果爲1;反之爲0 self.requestOption |= BDRequestOptionSuccess; // 四、累減。 若是累減不存在的枚舉值, 那麼本次累減的枚舉值,會自動累加上去。 // ^:按位異或,x^y相等則爲0,不等則爲1 self.requestOption ^= BDRequestOptionSuccess;
OC中的用法:
NSString *string = @"Learning"; [string boundingRectWithSize:CGSizeMake(CGRectGetWidth(self.view.frame), MAXFLOAT) options:NSStringDrawingUsesLineFragmentOrigin | NSStringDrawingTruncatesLastVisibleLine attributes:@{NSFontAttributeName : [UIFont systemFontOfSize:12.f]} context:nil];
上面傳值:NSStringDrawingUsesLineFragmentOrigin | NSStringDrawingTruncatesLastVisibleLine
邏輯處理:
1 // 對傳入的option邏輯處理 2 if (option & NSStringDrawingUsesLineFragmentOrigin) { 3 // 包含 NSStringDrawingUsesLineFragmentOrigin 4 } else { 5 // 未包含 NSStringDrawingUsesLineFragmentOrigin 6 } 7 if (option & NSStringDrawingTruncatesLastVisibleLine) { 8 // 包含 NSStringDrawingTruncatesLastVisibleLine 9 } else { 10 // 未包含 NSStringDrawingTruncatesLastVisibleLine 11 }
對於位移枚舉的具體使用方法,建議能夠查看一些三方庫,例如SDWebImage等!
尊重做者勞動成果,轉載請註明: 【kingdev】