記事のミス等のお問い合わせはTwitterにてお願いします。ビットシフトカテゴリ:工作の基礎マイコン前回はビット演算のお話をしましたが、今回はビット演算の一部ともいえるビットシフトのお話をします。ビットシフトというのはその名の通り、ビットの位置を移動させる機能です。この機能は主に、値を読み込んだ時に高いビットの値のみを使いたいときや、通信データの作成の時に使います。使う機会はそんなに多くないのでさらっと行きたいと思います。000010101回目の例は右向きに4bitシフトさせた例です。このように右向きにシフトさせると高い位置のビットにあったデータを低いビットに移動させることができます。ここで気を付けないといけないのは、ビットシフトさせて消えるビットと新たに出てくるビットがあることです。この例の場合は操作前の右側(下位)4ビットはシフトさせると消えていることがわかると思います。逆にシフトさせたあとの左側(上位)4ビットが新たに出てきてすべて0が入っていることがわかります。ビットシフトをさせるとシフトさせた方向寄りのシフトさせた数のビットが消えるというわけです。次に左向きにシフトする例です。10100000左向きにシフトすると左側(上位)4ビットが消えていることがわかりますね。ちなみに、左向きのシフトはシフトしたビット分2倍されている(例のように右に4ビットシフトする場合は値を16倍している)とも考えることもできます。このように考えた場合、範囲外に出て消えるビットは「値がオーバーフローした」と考えることができます。同様に右向きの場合はシフトしたビット分1/2倍されていると言えます。C言語でビットシフトを行う場合はこのように書きます。Bはビットシフトさせた後の値)C言語の表記は見た目のままなので簡単かなと思います。int型などで負の数を表したときはいろいろとややこしいことになるようですが、マイコン関連の処理で使うことはまずないと思うので特に詳しいことは書きません。実際にビットシフトを使う例を示してみましょう。PD5からPD7にスイッチが接続されていて、3つのスイッチで値を設定していると考えましょう。今回はPD5とPD6のスイッチがHIGHになっていると考えます。最終的に値は下位3ビット(0からまで)で表したいとします。Atmega328PのデータシートのP67を見ると、ポートDのピンの状態を読み込こむレジスタはPINDであることがわかります。上位3ビットのみを取り出します。(Cとする)続いてビットシフトを行って上位3ビットにいる値を下位3ビットに移動させます。00000101こうすると上位3ビットにスイッチを接続して値を設定しても、下位3ビットの値として取り出すことができます。これをC言語で表すとこのように書けます。5;//左に5ビットシフト(uint8_tは符号なしの8ビットの整数型(Arudinoでいうbyte型)を示しています。)C言語でもそのままに表せますね。ちなみに、先に行っているビットを取り出す作業は今回の場合は必要ありませんが、必要となる場合も多いので安全のために処理に含めています。(本当に必要になるのは中間のビットを取り出してシフトさせる場合などです)次に通信データ作成の場合を考えてみましょう。通信の場合できる限り送信のデータ数を少なくしたい場合が多いです。1バイトで完結させることができるとプログラムがとても楽に書くことができます。そこで、1バイト(8ビット)にビット数の少ない複数のデータを挿入する方法を紹介します。AとBはそれぞれ4ビットのみで表せる値として、送信データはAとBの両方を含めて1バイトにしたい場合を考えます。最初に、AとBから下位4ビットのみを取り出します。(Dlとする)この例の場合Bの最上位ビットにゴミの値が入っていますが、下位4ビットのみを取り出すことでこのゴミの値を除去できます。(普通はゴミの値なんて入らないと思いますが...)続いて、Aを上位ビットとするためにAを4ビット左側にシフトします。(Dhとする)こうすることでDl(元のB)とDh(元のA)でビットの位置が被らないことになります。そのため、DhとDlをOR(+でもいい)することで1つのデータに入れれます。→DATAこうすることでDATAの上位4ビットはゴミを取り除いたAのデータが入っており、下位4ビットにはごみを取り除いたBのデータが入っていることがわかりますね。することで桁が少ない複数の値を1つの値に収めることができるというわけです。これをC言語で書くとこのようになります。次にこのデータをもとのA,Bに戻す方法を紹介します。Aを取り出すために、データAがある上位4ビットのみを抽出します。→A’これで、上位4ビットを抽出できたのでこれを下位4ビットにビットシフトさせます。→Aこうすることで元のデータAが取り出すことができました。続いてデータBを取り出します。データBは下位4ビットにいるので下位4ビットのみを抽出します。→BデータBはビットシフトを行っていないので抽出した値が元のデータBとなります。これらもC言語で表すとこのようになります。前回と今回でマイコンのプログラムで重要なビットの処理のお話をしてきました。このビットの処理は慣れるまではちょっと大変ですが、慣れると簡単に扱えるようになると思います。次回はAVRマイコンのプログラミングを行う環境設定のお話をしたいと思います。