contributed by < shauming1020
>
homework
if (str[i] & 0x80) /* i.e. (unsigned) str[i] >= 128 */
逐一比較 1 個字元 (8-bits)i = 0, str + i:
Address | 1 byte | Char |
---|---|---|
0x56440dc9e9a0 | 0100 0001 | A |
0x56440dc9e9a1 | 0100 0010 | B |
… | … | … |
0x56440dc9e9a7 | 0100 1000 | H |
i = 8, str + i:
Address | 1 byte | Char |
---|---|---|
0x56440dc9e9a8 | 0100 0001 | A |
0x56440dc9e9a9 | 0100 0010 | B |
… | … | … |
0x56440dc9e9af | 0100 1000 | H |
payload
0100 1000 0100 0111 … 0100 0010 0100 0001 |
---|
Mask (MMM) |
1000 0000 1000 0000 … 1000 1000 1000 1000 |
–- |
已知 in 一定隸屬於 '0', '1', '2', …, '9' 及 'a', 'b', 'c', …, 'f' (小寫) 及 'A', 'B', 'C', …, 'F' (大寫) 這些字元。預期 hexchar2val('F') 和 hexchar2val('f') 回傳 15,且 hexchar2val('0') 回傳 0,其他輸入都有對應的數值。
#3 const uint8_t letter = in & MASK;
#4 const uint8_t shift = (letter >> AAA) | (letter >> BBB);
#4 return (in + shift) & 0xf;
乘法和位移操作 =
#6 uint64_t quotient = ((__uint128_t) M * n) >> 64;
#2 #define M ((uint64_t)(UINT64_C(XXX) / (D) + 1))
,其中 延伸測驗 3,我們想判斷某個數值能否被指定的除數所整除,在 D 和 M 都沿用的狀況下,程式碼如下:
從 #13 if ((*chunk & PACKED_BYTE(VV1)) == 0) { /* is ASCII? */
給的提示可以知道此行程式碼在檢測 *chunk 是否為 ASCII
#5 #define PACKED_BYTE(b) (((uint64_t)(b) & (0xff)) * 0x0101010101010101u)
#define PACKED_BYTE(b) ((uint64_t)(b) * 0x0101010101010101u)
從 strlower 函式觀察,#7 if (s[j] >= 'A' && s[j] <= 'Z')
then s[j] ^= 1 << 5;
#17 *chunk ^= mask;
,*chunk 與 mask 做 XOR
觀察 A = *chunk + PACKED_BYTE(128 - 'A')
和 Z = *chunk + PACKED_BYTE(128 - 'Z')
char | char + (128 - 'A') | char + (128 - 'Z') |
---|---|---|
'A'(65) | 128 | 103 |
'Z'(90) | 153 | 128 |
'a'(97) | 160 | 135 |
'z'(122) | 185 | 160 |
因此若想要透過 #16 uint64_t mask = ((A ^ Z) & PACKED_BYTE(VV4)) >> 2;
來做出 0x00 或是 0x20 的 mask
char | char + (128 - 'A') | char + (128 - 'Z') - 1 |
---|---|---|
'A'(65) | 128 | 102 |
'Z'(90) | 153 | 127 |
'a'(97) | 160 | 134 |
'z'(122) | 185 | 159 |
a byte or code of value zero is appended to each multibyte character sequence that results from a string literal or literals.66) The multibyte character sequence is then used to initialize an array of static storage duration and length just sufficient to contain the sequence.
靜態配置足夠大的陣列空間存放每個字元
It is unspecified whether these arrays are distinct provided their elements have the appropriate values. If the program attempts to modify such an array, the behavior is undefined.
但是修改其內容是未定義的行為
LeetCode 137. Single Number II:
Given a non-empty array of integers, every element appears three times except for one, which appears exactly once. Find that single one.
Note:
Your algorithm should have a linear runtime complexity. Could you implement it without using extra memory?Example 1:
Input: [2,2,3,2]
Output: 3Example 2:
Input: [0,1,0,1,0,1,99]
Output: 99
將整數看成數個獨立 bit,如 2 = 0b0010、3 = 0b0011
當一個數最多出現 2 次時,可以只用 1 bit 來描述,而當一個數最多出現 3 次時,則需要用 2 bit 來描述
00 表一個數未出現、01 表出現一次、10 表出現兩次
當出現三次時應為 11,但將其重置為 00 來表示該數已達上限,即該數不是要找的恰出現一次的數,因此給定一個數,其出現次數的規律為 00 -> 01 -> 10 -> 00
真值表如下,其中 high 表計數過程中的高位,low 表對應的低位,input 表下一個輸入, high' 和 low' 表對應的高低位輸出
high | low | input | high' | low' |
---|---|---|---|---|
0 | 0 | 0 | 0 | 0 |
0 | 1 | 0 | 0 | 1 |
1 | 0 | 0 | 1 | 0 |
0 | 0 | 1 | 0 | 1 |
0 | 1 | 1 | 1 | 0 |
1 | 0 | 1 | 0 | 0 |
最後一行當 high/low 狀態為 10 時,輸入 1 後輸出為 00 而非 11
高低位的邏輯表達式
low' 即表示出現一次的整數,因為 0、2、3次對應的 low' 皆為 0,這也解釋為何要將 11重置為 00,避免兩種情形的 low' 為 1
利用上述式子計算 low' 和 high' 時,皆是沿用舊的 low 值,需要先暫存起來以待計算,嘗試修改真值表,避免用舊值計算
high | low | input | high' |
---|---|---|---|
0 | 0 | 0 | 0 |
0 | 1 | 0 | 0 |
1 | 0 | 0 | 1 |
0 | 1 | 1 | 0 |
0 | 0 | 1 | 1 |
1 | 0 | 1 | 0 |
從上述得 KKK = ~higher,JJJ = ~lower
[參考] https://blog.csdn.net/yutianzuijin/article/details/50597413