contributed by < hankluo6
>
1
(~0UL) >> (LEFT)
將所有 bit 向右移,所以其 MSB 數來 bit 為 0 的數目與 LEFT
相等。可推出 (~0UL) >> (l) << (RIGHT)
需將從 LSB 數來的 bit 設為 0。
可得 LEFT = 63 - h
,(~0UL) >> (l) << (RIGHT)
需把 LSB 部分的 bit 清空,故 RIGHT = l
。
3
(x >> 4) | (x << 4)
將前四個位元與後四個位元交換,((x & 0xCC) >> 2) | (EXP2)
應要將每兩個位元互換,0xCC
表示將 3, 4, 7, 8 個位元又移,則須將 0xFF ^ 0xCC = 0x33
的位元左移,得 EXP2 = (x & 0x33) << 2
,((x & 0xCC) >> 2) | (EXP2)
將每一個位元互換,0xFF ^ 0xAA = 0x55
,故 EXP2 = (x & 0x55) << 1
。
3
利用 Variadic Macros 實現 foreach
,其中 _foreach_i
用來記錄迴圈的次數,i
為目前的可變參數。
unsigned _foreach_i = (((i) = ((int[]){__VA_ARGS__})[0]), 0
剛進入迴圈時,透過 (i) = ((int[]){__VA_ARGS__})[0]
將 i
設定為可變參數的第一個 element,並使用 ,
operator 將 _foreach_i
設定為 0。
迴圈的條件式 _foreach_i < sizeof((int[]){__VA_ARGS__}) / sizeof(int)
為 _foreach_i
小於可變參數大小。
(i) = ((int[]){__VA_ARGS__, 0})[EXP4]
則需要得到下個可變參數,故 EXP4 = ++_foreach_i
。另外 _foreach_i
會在可變參數大小後額外加一,才會跳出迴圈,故 (int[]){__VA_ARGS__, 0}
多一個 0 取不到陣列的值。
與 foreach_ptr
相同,只是迴圈終止條件改為判斷 i
是否為 null
,而 i
會在跑完可變變數時被設為 null
,故 EXP5 = ++_foreach_i
。