teratail header banner
teratail header banner
質問するログイン新規登録

回答編集履歴

2

日本語の微修正

2015/08/30 00:22

投稿

raccy
raccy

スコア21768

answer CHANGED
@@ -1,5 +1,5 @@
1
1
  【普通の解説】
2
- ※ 宗教的な問題で、`unsigned`は全て`unsigned int`と記述しています。
2
+ ※ 宗教的な理由で、`unsigned`は全て`unsigned int`と記述しています。
3
3
  まず、`int_bits()`が`unsigned int`におけるbitsの数になることは理解できているでしょうか?もし、`unsigned int`が32bitsなら`int_bits()`は32を返します(ぶっちゃけ、`sizeof(unsigned int) * CHAR_BIT`でもいい気がするのですが)。次に、`for(i=int_bits()-1;i>=0;i--)`の部分ですが、`i`について、31(-1しているので32ではありません)から0までforループで回すという意味です。あとはforループの中身を見ればわかるはずです。
4
4
 
5
5
  forループの中身ですが、`x>>i`が何をしているかというと、`x`を`i`分だけシフトするという意味です。たとえば、xが55という数字の場合、2進数では下記になります。
@@ -7,11 +7,11 @@
7
7
  x: 0000 0000 0000 0000 0000 0000 0011 0111
8
8
  ※ わかりやすいように、4bits毎にスペースで区切っています。
9
9
 
10
- iは31から始まりますので、最初に31個分左にシフトします。
10
+ そして、iは31から始まりますので、まずは31個分左にシフトし、下記になります。
11
11
 
12
12
  x >> 31: 0000 0000 0000 0000 0000 0000 0000 0000
13
13
 
14
- 全て0になりました。iが31から6までは同じようにすべて0になります。ビットが一切立ってないので、ここまでは0ということです。そして、0は偽なので三項演算子の部分は'0'が返ります。ではiが5の場合はどうなるかというと、
14
+ 全て0になりました。iが31から6までは同じようにすべて0になります。ビットが一切立ってないので、ここまでは0ということです。そして、0は偽なので三項演算子の部分は'0'が返り、0が表示されます。ではiが5の場合はどうなるかというと、
15
15
 
16
16
  x >> 5: 0000 0000 0000 0000 0000 0000 0000 0001
17
17
 
@@ -23,7 +23,7 @@
23
23
 
24
24
  (x >> 5)&1U: 0000 0000 0000 0000 0000 0000 0000 0001
25
25
 
26
- となり、つまり、左から6番目(5番目ではありません。判断するのはi+1番目です)のビットが立っているかがわかると言うことです。そして、1は真なので三項演算子の部分は'1'が返ります。同じように`i`が4の場合は、
26
+ となり、つまり、左から6番目(5番目ではありません。判断するのはi+1番目です)のビットが立っているかがわかると言うことです。そして、1は真なので三項演算子の部分は'1'が返り、1が表示されます。同じように`i`が4の場合は、
27
27
 
28
28
  x >> 4: 0000 0000 0000 0000 0000 0000 0000 0011
29
29
  1U: 0000 0000 0000 0000 0000 0000 0000 0001

1

本編を書き忘れていた。

2015/08/30 00:22

投稿

raccy
raccy

スコア21768

answer CHANGED
@@ -1,3 +1,58 @@
1
+ 【普通の解説】
2
+ ※ 宗教的な問題で、`unsigned`は全て`unsigned int`と記述しています。
3
+ まず、`int_bits()`が`unsigned int`におけるbitsの数になることは理解できているでしょうか?もし、`unsigned int`が32bitsなら`int_bits()`は32を返します(ぶっちゃけ、`sizeof(unsigned int) * CHAR_BIT`でもいい気がするのですが)。次に、`for(i=int_bits()-1;i>=0;i--)`の部分ですが、`i`について、31(-1しているので32ではありません)から0までforループで回すという意味です。あとはforループの中身を見ればわかるはずです。
4
+
5
+ forループの中身ですが、`x>>i`が何をしているかというと、`x`を`i`分だけシフトするという意味です。たとえば、xが55という数字の場合、2進数では下記になります。
6
+
7
+ x: 0000 0000 0000 0000 0000 0000 0011 0111
8
+ ※ わかりやすいように、4bits毎にスペースで区切っています。
9
+
10
+ iは31から始まりますので、最初に31個分左にシフトします。
11
+
12
+ x >> 31: 0000 0000 0000 0000 0000 0000 0000 0000
13
+
14
+ 全て0になりました。iが31から6までは同じようにすべて0になります。ビットが一切立ってないので、ここまでは0ということです。そして、0は偽なので三項演算子の部分は'0'が返ります。ではiが5の場合はどうなるかというと、
15
+
16
+ x >> 5: 0000 0000 0000 0000 0000 0000 0000 0001
17
+
18
+ と、最後に一つだけ残ります。次に`1U`はなにかというと下記のようになっています。
19
+
20
+ 1U: 0000 0000 0000 0000 0000 0000 0000 0001
21
+
22
+ この二つを`&`で演算すれば、
23
+
24
+ (x >> 5)&1U: 0000 0000 0000 0000 0000 0000 0000 0001
25
+
26
+ となり、つまり、左から6番目(5番目ではありません。判断するのはi+1番目です。)のビットが立っているかがわかると言うことです。そして、1は真なので三項演算子の部分は'1'が返ります。同じように`i`が4の場合は、
27
+
28
+ x >> 4: 0000 0000 0000 0000 0000 0000 0000 0011
29
+ 1U: 0000 0000 0000 0000 0000 0000 0000 0001
30
+ (x >> 4)&1U: 0000 0000 0000 0000 0000 0000 0000 0001
31
+
32
+ となり、5番目のビットが立っていると判断できます。では3の場合はどうでしょうか?
33
+
34
+ x >> 3: 0000 0000 0000 0000 0000 0000 0000 0110
35
+ 1U: 0000 0000 0000 0000 0000 0000 0000 0001
36
+ (x >> 3)&1U: 0000 0000 0000 0000 0000 0000 0000 0000
37
+
38
+ おお、0になりますね。つまり4番目のビットは立っていない、なので0なのです。あとは同じように、0までするだけです。
39
+
40
+ x >> 2: 0000 0000 0000 0000 0000 0000 0000 1101
41
+ 1U: 0000 0000 0000 0000 0000 0000 0000 0001
42
+ (x >> 2)&1U: 0000 0000 0000 0000 0000 0000 0000 0001 # 3番目はビットが立ている
43
+
44
+ x >> 1: 0000 0000 0000 0000 0000 0000 0001 1011
45
+ 1U: 0000 0000 0000 0000 0000 0000 0000 0001
46
+ (x >> 1)&1U: 0000 0000 0000 0000 0000 0000 0000 0001 # 2番目はビットが立ている
47
+
48
+ x >> 0: 0000 0000 0000 0000 0000 0000 0011 0111
49
+ 1U: 0000 0000 0000 0000 0000 0000 0000 0001
50
+ (x >> 0)&1U: 0000 0000 0000 0000 0000 0000 0000 0001 # 1番目はビットが立ている
51
+
52
+ 結果、00000000000000000000000000110111が表示されることがわかると思います。
53
+
54
+ ---
55
+ 【おまけ】
1
56
  汎用性を持たせてみました。
2
57
  ```C
3
58
  #include <stdio.h>