22,073 total views, 26 views today
超音波距離センサー(HC-SR04)を買ったので、使ってみた。
測定
超音波距離センサーでは、音速(20.055 (セルシウス温度 + 273.15 )^1/2 )を利用して距離を測定しているので、測定する数値は温度に影響を受けるという。
なので、温・湿度センサー(DHT11)で測定した温度を用いて音速を算出することにした。
また、スイッチを押すごとに距離を測定し、測定した距離と温度をLCDに表示するようにした。
使用した物
5cmと10cmの測定結果
まず、5cmと10cmの距離をそれぞれ5回ずつ測定した結果、下表の通りとなった。
| 回数 | 5cm | 10cm |
|---|---|---|
| 1回目 | 4.63cm | 10.88cm |
| 2回目 | 4.75cm | 10.88cm |
| 3回目 | 4.75cm | 10.83cm |
| 4回目 | 4.77cm | 10.85cm |
| 5回目 | 4.75cm | 10.83cm |
| 平均 | 4.73cm | 10.854cm |
距離が5cmの場合には平均で3mm程度の誤差が見られ、10cmの場合には平均で8mmほどの誤差が見られた。
15cmと20cmの測定結果
次に、15cmと20cmの距離をそれぞれ5回ずつ測定した結果、下表の通りとなった。
| 回数 | 15cm | 20cm |
|---|---|---|
| 1回目 | 15.09cm | 20.05cm |
| 2回目 | 15.07cm | 20.07cm |
| 3回目 | 15.07cm | 20.04cm |
| 4回目 | 15.07cm | 20.06cm |
| 5回目 | 15.03cm | 20.09cm |
| 平均 | 15.066cm | 20.062cm |
15cm、20cmともに、平均で0.6mm程度の誤差があった。
25cmと30cmの測定結果
最後に、25cmと30mの距離を5回ずつ測定した結果、下表の通りとなった。
| 回数 | 25cm | 30cm |
|---|---|---|
| 1回目 | 25.01cm | 30.02cm |
| 2回目 | 24.98cm | 29.97cm |
| 3回目 | 25.01cm | 30.00cm |
| 4回目 | 25.01cm | 30.00cm |
| 5回目 | 24.98cm | 30.01cm |
| 平均 | 24.998cm | 30.00cm |
25cm、30cmともに、1mm未満の誤差しか見られなかった。
とりあえず、今回測定した距離での誤差は全て1cm未満に収まっていた。
スポンサーリンク
もう何個か買って、段差や障害物を自動で避けて動くものを作るのに使おうと思う。
配線とプログラム
配線
プログラム
#!/usr/bin/ebv python
#-*- coding: utf-8 -*-
import time
import RPi.GPIO as GPIO
import smbus
import math
import dht11
GPIO.setwarnings(False)
GPIO.setmode(GPIO.BCM)
#超音波距離センサーの入力(ECHO)と出力(TRIG)
TRIG = 5
ECHO = 6
GPIO.setup(TRIG, GPIO.OUT)
GPIO.setup(ECHO, GPIO.IN)
GPIO.output(TRIG, GPIO.LOW)
#スイッチの入力
GPIO.setup(21, GPIO.IN)
#温・湿度センサーのインスタンス生成(ピン番号4)
instance = dht11.DHT11(pin=4)
# Define some device parameters
I2C_ADDR = 0x27 # I2C device address
LCD_WIDTH = 16 # Maximum characters per line
LCD_CHR = 1 # Mode - Sending data
LCD_CMD = 0 # Mode - Sending command
LCD_LINE_1 = 0x80 # LCD RAM address for the 1st line
LCD_LINE_2 = 0xC0 # LCD RAM address for the 2nd line
LCD_BACKLIGHT = 0x08 # On
#LCD_BACKLIGHT = 0x00 # Off
ENABLE = 0b00000100 # Enable bit
# Timing constants
E_PULSE = 0.0005
E_DELAY = 0.0005
#Open I2C interface
#bus = smbus.SMBus(0) # Rev 1 Pi uses 0
bus = smbus.SMBus(1) # Rev 2 Pi uses 1
def lcd_init():
# Initialise display
lcd_byte(0x33,LCD_CMD) # 110011 Initialise
lcd_byte(0x32,LCD_CMD) # 110010 Initialise
lcd_byte(0x06,LCD_CMD) # 000110 Cursor move direction
lcd_byte(0x0C,LCD_CMD) # 001100 Display On,Cursor Off, Blink Off
lcd_byte(0x28,LCD_CMD) # 101000 Data length, number of lines, font size
lcd_byte(0x01,LCD_CMD) # 000001 Clear display
time.sleep(E_DELAY)
def lcd_byte(bits, mode):
# Send byte to data pins
# bits = the data
# mode = 1 for data
# 0 for command
bits_high = mode | (bits & 0xF0) | LCD_BACKLIGHT
bits_low = mode | ((bits<<4) & 0xF0) | LCD_BACKLIGHT
# High bits
bus.write_byte(I2C_ADDR, bits_high)
lcd_toggle_enable(bits_high)
# Low bits
bus.write_byte(I2C_ADDR, bits_low)
lcd_toggle_enable(bits_low)
def lcd_toggle_enable(bits):
# Toggle enable
time.sleep(E_DELAY)
bus.write_byte(I2C_ADDR, (bits | ENABLE))
time.sleep(E_PULSE)
bus.write_byte(I2C_ADDR,(bits & ~ENABLE))
time.sleep(E_DELAY)
def lcd_string(message,line):
# Send string to display
message = message.ljust(LCD_WIDTH," ")
lcd_byte(line, LCD_CMD)
for i in range(LCD_WIDTH):
lcd_byte(ord(message[i]),LCD_CHR)
def reading(sensor):
result = instance.read() #温度取得
c = result.temperature
if result.is_valid():
lcd_init()
if sensor == 0:
time.sleep(0.3)
GPIO.output(TRIG, True)
time.sleep(0.00001)
GPIO.output(TRIG, False)
while GPIO.input(ECHO) == 0:
signaloff = time.time()
while GPIO.input(ECHO) == 1:
signalon = time.time()
t = signalon - signaloff
v = 20.055 * math.sqrt(c + 273.15) #絶対温度を用いない場合:v = 331.5 + 0.61 * result.temperature
print(str(v))
d = v * t * 50
temp = "Temp: " + str(c + 273) + "K("+ str(c) + "C)"
distance = str(math.floor(d *100) /100)+ "cm"
print(temp)
print(distance)
lcd_string(distance, LCD_LINE_1)
lcd_string(temp, LCD_LINE_2)
else:
print "Incorrect usonic() function varible"
try:
while True:
if GPIO.input(21) == GPIO.HIGH:
reading(0) #超音波距離センサーの値取得
time.sleep(1.5)
print("ready")
except KeyboardInterrupt:
pass
finally:
LCD_BACKLIGHT = 0x00
lcd_byte(0x01, LCD_CMD)
GPIO.cleanup()
まとめ
- 超音波距離センサー(HC-SR04)を使ってみた
- 誤差はそれほど大きくなかった(1cm未満)
- 障害物を避けて動くものを作るのに使う

“Raspberry Pi 3(ラズベリーパイ3)で超音波距離センサー(HC-SR04)を使う” への1件のフィードバック