Raspberry PiとDHT11で温度・湿度を測る

# はじめに
Raspberry Piでセンサーを接続し、部屋の温度・湿度を測ります。
今回は「DHT11」という温湿度センサーを使用します。

# 温湿度センサー「DHT11」
DHT11は、価格も安価で入手し易い温湿度センサーです。
![dht11.png](https://qiita-image-store.s3.amazonaws.com/0/43330/9ee029ad-e73d-aa42-8f51-3b91b39b5826.png)

センサー単体、基盤に設置されたものなど、用途に応じた様々な形態で販売されており、秋月電子通商では３００円で購入することができます。（左の画像がセンサー単体です）
【秋月電子通商】
[秋月電子通商 温湿度センサ モジュール ＤＨＴ１１](http://akizukidenshi.com/catalog/g/gM-07003/)

# 回路を組む
秋月電子で公開されている[データシート](http://akizukidenshi.com/download/ds/aosong/DHT11_20180119.pdf)を参考に回路図を組んでみます。使用するのはDHT11のセンサー単体のものです。
DHT１１のピン構成は、
　１番：5V
　２番：GPIO
　３番：NC（Non-Connected = 使用していない）
　４番：GND
という構成になっています。（３番の使用していないピンがあるというのは謎ですね…）
ざっくり説明すると、1番ピン、４番ピンにRaspberry Piの５V、GNDを接続し、２番ピンに任意のGPIOの端子を割り当てて情報を取得する、ということになります。

回路の組み方はいくつかあると思いますが、私は下図のように組んでみました。この後で温度・湿度を取得するプログラムでピンの番号が重要になりますので、ピンの位置は間違えないように注意してください。
![dht11_ブレッドボード.png](https://qiita-image-store.s3.amazonaws.com/0/43330/c32d22c9-e807-1106-d0cf-68016638b375.png)

# 温度・湿度を取得するスクリプトを作成する
DHT11から情報を取得するPythonのライブラリがGitHubで公開されています。
こちらのライブラリを使って、センサーから温度・湿度の情報を取得します。
[DHT11 Python library](https://github.com/szazo/DHT11_Python)

Raspberry PiからGitHubにアクセスして、ライブラリを取得しましょう。
そのためにも、apt-getを使用して、gitクライアントをインストールします。

```shell
sudo apt-get install git
```

インストールが完了したら、上記のサイトからクローンしましょう。

```shell
git clone https://github.com/szazo/DHT11_Python.git
```

クローンが完了すると、DHT11_Pythonというフォルダが作成され、以下のファイルが取得されています。

```shell
LICENSE.md
README.md
__init__.py
dht11.py
dht11_example.py
```
dht11.pyがDHT11から情報取得するライブラリ本体、dht11_example.pyがライブラリを使った温度・湿度の情報を取得するサンプルスクリプトです。

# サンプルスクリプトを読み解く
dht11_example.pyを少し読み解いてみます。

```python:dht11_example.py
import RPi.GPIO as GPIO
import dht11       # ・・・ ①
import time
import datetime

# initialize GPIO
GPIO.setwarnings(False)       # ・・・ ②
GPIO.setmode(GPIO.BCM)
GPIO.cleanup()

# read data using pin 14
instance = dht11.DHT11(pin=14)      # ・・・ ③

while True:
    result = instance.read()    # ・・・ ④
    if result.is_valid():    # ・・・ ⑤
        print("Last valid input: " + str(datetime.datetime.now()))
        print("Temperature: %d C" % result.temperature)    # ・・・ ⑥
        print("Humidity: %d %%" % result.humidity) 

    time.sleep(1)    # ・・・ ⑦
```

① import文でライブラリ「dht11.py」を読み込みます。
② GPIOの初期化をしています。各コマンドには次のような意味になります。
　　GPIO.setwarnings(False)  ： ワーニングを非表示にします。※1
　　GPIO.setmode(GPIO.BCM)   ： GPIOの数字で指定します。
　　GPIO.cleanup()           ： GPIOの設定を初期化します。
※1.ピンが既に使用中の場合等にワーニングが表示されます。今回のサンプルではワーニングは表示されないため、設定は必須ではありません。
③ データ読み込みのピン番号を設定します。②の初期化でGPIOの番号で設定するようにしているため、引数のpinには今回接続している14を設定します。
④ センサーから温度・湿度情報を取得します。
⑤ センサーから温度・湿度情報が取得できたか判定します。取得できた場合に結果をコンソールに出力します。
⑥ 温度・湿度情報をコンソールに出力します。
　　temperature ： 温度（摂氏）の値です。
　　humidity    ： 湿度の値です。
⑦ 1秒処理を停止します。

# 実行結果
サンプルスクリプトのdht11_example.pyを実行します。コマンドは次の通りです。

```shell
$ python dht11_example.py 

```
成功すると下記のような結果を得られます。
```shell
Last valid input: 2018-03-10 05:08:35.590508
Temperature: 24 C       <= 温度
Humidity: 47 %          <= 湿度
```

上記は１回の結果ですが、サンプルスクリプトは停止させるまで１秒毎に温度・湿度を取得して出力しています。（詳細は「サンプルスクリプトを読み解く」をご覧ください）
また、実行直後の結果には多少の誤差が生じるようで、数値が揺れているように感じます。数回実行すると収束し、安定した結果が得られるようになります。
※揺れは高性能なセンサーにすると解消するかもしれません。手に入れる機会があれば試してみたいと思います。

# おわりに
安価な機材、簡単なスクリプトで温度・湿度を測定することができました。
温度のセンシングを活用するアイデアは電子工作の中でもよく利用される手段なので、みなさんも試してみてください。