Arduinoのanalog Read・analogWriteの違い|センサー値とPWM制御を徹底解説

Arduino/ブレッドボード基礎知識






Arduinoのanalog Read・analogWriteの違い|センサー値とPWM制御を徹底解説










Arduino analogRead & analogWrite Guide — 2026

「読む」の0〜1023、
「書く」の0〜255。数字が違う理由。

analogRead()で読み取った値をそのままanalogWrite()に渡すと、なぜか動きがおかしい——これはArduinoを触り始めた人がほぼ必ず一度は通る疑問です。実はanalogReadとanalogWriteは、名前は似ていても扱っている数字の範囲がまったく違います。この記事では、センサー値が0〜1023で返ってくる仕組みから、電圧への換算、PWMという仕組みで0〜255の値を送り出すanalogWrite、そして2つの範囲をつなぐmap()関数まで、豊富な具体例を使って専門用語ゼロから徹底的に解説します。

対象読者: プログラミング未経験〜Arduino初級者 対象ボード: Arduino Uno / Nano互換機 収録コード例: 10本以上
専門用語は初出時に解説電圧換算の計算式つきPWMを図解全コードCOPY対応
01

analogReadとanalogWriteは正反対の役割

名前がよく似ているanalogRead()analogWrite()ですが、この2つは矢印の向きがまったく逆の命令です。

analogRead() = 読み取る

  • センサーから「値をもらう」
  • 矢印の向き:センサー → Arduino
  • 返ってくる数字:0〜1023
  • 使えるピン:A0〜A5などアナログ入力ピン

analogWrite() = 送り出す

  • LEDやモーターに「値を渡す」
  • 矢印の向き:Arduino → LED・モーター
  • 渡す数字:0〜255
  • 使えるピン:~マーク付きのPWM対応ピン

可変抵抗(つまみを回すと値が変わる部品)の回転量をanalogRead()で読み取り、その値をそのままanalogWrite()でLEDに渡す——という組み合わせは定番ですが、そのまま渡すと数字の範囲が合わずうまく動きません。この「範囲の違い」こそが、この記事全体を通じての最大のテーマです。

この記事の前提

digitalReadやdigitalWrite、pinModeといった基本のI/O命令をすでに理解している方向けの内容です。基礎から確認したい場合はArduinoのコードの書き方(コピペ可20選)もあわせてご覧ください。

02

analogRead()の基本|0〜1023という数字の正体

analogRead(ピン番号)は、A0〜A5のようなアナログ入力ピンにかかっている電圧を測定し、その結果を0〜1023の整数で返してくれる命令です。なぜ0〜1023というキリの悪い数字なのか、順を追って見てみましょう。

例1:可変抵抗の値を読み取ってみる

example_analogread.ino
const int POT_PIN = A0;  // 可変抵抗の信号線をA0に接続
void setup() {
  Serial.begin(9600);
}
void loop() {
  int value = analogRead(POT_PIN);
  Serial.println(value);  // つまみを回すと、0〜1023の間で数字が変わる
  delay(100);
}

つまみを左いっぱいに回すと0付近、右いっぱいに回すと1023付近の数字がシリアルモニタに表示されます。真ん中あたりでは、だいたい500前後の数字になります。

用語メモ:なぜ「1023」なのか(10ビットという仕組み)Arduino Uno / Nanoのアナログ入力は、電圧を10ビット(2進数10桁)という細かさで測定する部品(ADC=アナログ-デジタル変換回路)を使っています。2進数10桁で表せる数字の個数は2の10乗=1024個なので、0から数えると「0〜1023」というちょうど1024段階になります。段階を増やすほど細かく測定できますが、Arduino Uno / Nanoでは1024段階が標準です。

例2:センサーの種類が違っても、返ってくる数字の形は同じ

example_various_sensors.ino
int lightValue    = analogRead(A0);  // 光センサー:明るいほど数字が変わる
int pressureValue = analogRead(A1);  // 圧センサー:押す強さで数字が変わる
int muscleValue   = analogRead(A2);  // 筋電センサー:筋肉の活動量で数字が変わる
// センサーの種類が違っても、analogRead()が返す形(0〜1023)は共通

光センサーでも圧センサーでも筋電センサーでも、analogRead()が返してくる数字の「形」はいつも0〜1023です。センサーごとに「暗い時は数字が小さい」「強く押すと数字が大きい」といった意味づけが変わるだけで、命令の使い方自体は共通しています。センサーの種類ごとの特徴はArduino用センサー完全ガイド16選で詳しく比較しています。

正式な仕様は、Arduino公式のanalogRead()言語リファレンス ↗で確認できます。

03

0〜1023を実際の電圧(ボルト)に変換する

analogRead()が返す0〜1023という数字は、それ自体では「電圧」ではありません。あくまで「0〜1023段階のうちの何番目か」という順位のようなものです。これを実際の電圧(ボルト)に直すには、簡単な計算が必要です。

変換の考え方

Arduino Uno / Nanoの基準電圧は標準で5Vです。0〜1023の1024段階で0〜5Vを表しているので、「今の値 ÷ 1023 × 5」という計算で、実際の電圧に変換できます。

例3:センサー値を電圧(ボルト)に変換して表示する

example_voltage_convert.ino
const int SENSOR_PIN = A0;
void setup() {
  Serial.begin(9600);
}
void loop() {
  int rawValue = analogRead(SENSOR_PIN);         // 0〜1023の生の値
  float voltage = rawValue * (5.0 / 1023.0);     // 電圧(ボルト)に変換
  Serial.print("生の値: ");
  Serial.print(rawValue);
  Serial.print(" / 電圧: ");
  Serial.print(voltage);
  Serial.println(" V");
  delay(200);
}
analogRead()の値 計算式 電圧(約)
0 0 ÷ 1023 × 5 0.00 V
512 512 ÷ 1023 × 5 2.50 V
1023 1023 ÷ 1023 × 5 5.00 V
rawValue * (5.0 / 1023.0)
5.01023.0のように小数点を付けているのがポイントです。もし5 / 1023のように整数だけで計算すると、割り算の結果が0になってしまい(int型の割り算は小数点以下を切り捨てるため)、正しい電圧が求まりません。小数を扱いたい計算では、必ずどこかに小数点を含めておきましょう。
なぜ電圧に変換するのか

0〜1023という数字のままでも動作の判定(しきい値判定など)には十分使えますが、電圧という「誰が見ても意味の分かる単位」に変換しておくと、センサーのデータシート(仕様書)に書かれた数値と見比べたり、他の人にデータを説明したりする時に扱いやすくなります。

04

analogWrite()の基本|PWMと0〜255の意味

analogWrite(ピン番号, 値)は、LEDの明るさやモーターの速さを、0(完全にオフ)から255(完全にオン)までの256段階で指定できる命令です。ここで大きな疑問が出てきます。「Arduinoの出力はHIGH(5V)かLOW(0V)の2択のはずなのに、なぜ中間の明るさを出せるのか?」——その答えがPWMです。

用語メモ:PWM(パルス幅変調)PWM(Pulse Width Modulation)とは、HIGHとLOWを人間の目には分からないほど高速に切り替えることで、あたかも中間の電圧が出ているかのように見せかける技術です。Arduino Unoでは、多くのピンで1秒間に約490回、5番・6番ピンでは約980回というスピードで切り替わっています。1回1回はオンかオフかの2択のままですが、「オンになっている時間の割合」を変えることで、明るさや速さを調整します。

例4:PWMのイメージを図で見る

下の図は、同じ長さの時間の中で「オン(点灯)」の割合をどれだけ増やすかを表したイメージです。オンの時間が長いほど、LEDは明るく(あるいはモーターは速く)感じられます。

analogWrite(255)

analogWrite(191)

analogWrite(127)

analogWrite(64)

analogWrite(0)

オレンジ色の部分が「オン」、グレーの部分が「オフ」の時間です。analogWrite(127)はほぼ半分がオンなので、見た目には「約半分の明るさ」に感じられます。この考え方は、Arduino公式の「Basics of PWM」↗でも図解付きで説明されています。

例5:LEDの明るさを0〜255で指定する

example_analogwrite.ino
const int LED_PIN = 9;  // ~マークの付いたPWM対応ピンを使う
void setup() {
  // analogWrite()を使う時はpinMode()を省略してもOK
}
void loop() {
  analogWrite(LED_PIN, 64);   // 弱め(約25%の明るさ)
  delay(1000);
  analogWrite(LED_PIN, 191);  // 強め(約75%の明るさ)
  delay(1000);
}
PWM対応ピンに注意

analogWrite()はどのピンでも使えるわけではありません。Arduino Unoの場合、ボード上に~(チルダ)マークが付いている3・5・6・9・10・11番ピンだけがPWMに対応しています。マークのないピンにanalogWrite()を使っても、意図した中間の明るさは出せません。

正式な仕様は、Arduino公式のanalogWrite()言語リファレンス ↗で確認できます。

05

比較表:analogReadとanalogWriteの違いまとめ

ここまでの内容を、一覧表に整理しておきましょう。迷ったらこの表に戻ってくると、頭の中が整理しやすくなります。

項目 analogRead() analogWrite()
役割 値を「読み取る」 値を「送り出す」
数字の範囲 0〜1023(1024段階) 0〜255(256段階)
使えるピン A0〜A5などアナログ入力ピン ~マーク付きのPWM対応ピン
仕組み 電圧をADC(アナログ-デジタル変換回路)で測定 PWM(高速なオン・オフの繰り返し)
pinModeの要否 基本的に不要(入力扱いされる) 省略しても動作するが、明示してもよい
典型的な用途 可変抵抗、光センサー、圧センサー、筋電センサーなど LEDの明るさ調整、モーターの速度調整
POINT

「analog」という名前が付いていても、内部で扱っている実体はどちらも0か1(デジタル)の組み合わせです。analogReadは電圧を細かい段階のデジタル数値に変換して読み取り、analogWriteは高速なオン・オフの組み合わせ(PWM)でアナログらしい効果を作り出しています。どちらも「デジタルの仕組みで、アナログの世界を扱う工夫」という点では共通しています。

06

map()関数で範囲を変換する

ここまでで、analogReadは0〜1023、analogWriteは0〜255という、異なる範囲の数字を扱うことが分かりました。では、センサーで読み取った0〜1023の値を、そのままLEDの明るさ(0〜255)として使いたい時はどうすればいいでしょうか。ここで登場するのがmap()関数です。

map()の書き方

concept_map.ino
map(変換したい値, 変換前の最小, 変換前の最大, 変換後の最小, 変換後の最大)

「変換前の範囲でこの値だったら、変換後の範囲では何番目に相当するか」を自動で計算してくれる命令です。

例6:0〜1023を0〜255に変換する

example_map.ino
const int SENSOR_PIN = A0;
const int LED_PIN = 9;
void loop() {
  int sensorValue = analogRead(SENSOR_PIN);           // 0〜1023
  int ledValue = map(sensorValue, 0, 1023, 0, 255);   // 0〜255に変換
  analogWrite(LED_PIN, ledValue);
}
sensorValue(0〜1023) map()後のledValue(0〜255)
0 0
512 約128
1023 255
map(sensorValue, 0, 1023, 0, 255)
「sensorValueは0〜1023の範囲の中のどのあたりか」を調べて、それと同じ位置(割合)になるように0〜255の範囲の中の数字を計算してくれます。可変抵抗を右いっぱいに回した時(sensorValue=1023)は、ledValueも最大の255になる、という具合です。

例7:範囲を反転させる(値を逆にする)

example_map_reverse.ino
// 変換後の範囲を逆順に書くと、値の大小関係も反転する
int ledValue = map(sensorValue, 0, 1023, 255, 0);
// sensorValueが大きいほど、ledValueは小さくなる(値の大小関係を逆にしたい場合に使う)

例えば「センサー値が大きいほどLEDを暗くしたい」「つまみを右に回すほどモーターを遅くしたい」といった、直感とは逆向きの反応をさせたい場合にこの書き方が役立ちます。

注意:map()は整数(int)で計算する

map()は小数を扱わず、整数だけで計算します。そのため、割り切れない計算では小数点以下が切り捨てられます。0〜1023を0〜255に変換するような大まかな用途では問題になりませんが、より正確な計算が必要な場面では注意してください。詳しい仕様はArduino公式のmap()言語リファレンス ↗にまとまっています。

07

実践コード:センサー値でLEDの明るさを連続的に変える

最後に、ここまで学んだ内容をすべて組み合わせた実践的なコードを見てみましょう。センサーの値を読み取り、電圧としてシリアルモニタに表示しつつ、同じ値をmap()で変換してLEDの明るさとして反映させます。

practical_example.ino
const int SENSOR_PIN = A0;  // 可変抵抗や光センサーなど
const int LED_PIN = 9;      // ~マーク付きのPWM対応ピン

void setup() {
  Serial.begin(9600);
}

void loop() {
  // 1. センサー値を読み取る(0〜1023)
  int sensorValue = analogRead(SENSOR_PIN);

  // 2. 参考用に電圧へ変換して表示する
  float voltage = sensorValue * (5.0 / 1023.0);

  // 3. LEDの明るさ用に0〜255へ変換する
  int brightness = map(sensorValue, 0, 1023, 0, 255);

  // 4. LEDの明るさに反映する(PWM出力)
  analogWrite(LED_PIN, brightness);

  // 5. 状態をシリアルモニタで確認する
  Serial.print("センサー値: ");
  Serial.print(sensorValue);
  Serial.print(" / 電圧: ");
  Serial.print(voltage);
  Serial.print("V / LED明るさ: ");
  Serial.println(brightness);

  delay(100);
}
// 1〜5の流れ
「読み取る(analogRead)→ 換算する(電圧・map)→ 送り出す(analogWrite)」という一連の流れが、この記事全体のまとめになっています。同じsensorValueという1つの数字から、人間が読むための電圧表示と、LEDを動かすための明るさ指定という、2つの異なる使い道を同時に作り出しています。

握力や圧力をセンサーで読み取ってゲーム化する応用例はリアルタイム握力計測ゲームのコード解説 ↗、センサー値の変化に応じてLEDの色を変える作例はセンサーで色が変わる電子工作 ↗で詳しく紹介しています。配線に不安がある場合はブレッドボード完全攻略ガイドもあわせてご確認ください。

08

よくある間違い・注意点

1

analogReadの値をそのままanalogWriteに渡してしまう。0〜1023の値を0〜255の命令にそのまま渡すと、255を超えた分は無視されたり、意図しない明るさになったりします。必ずmap()などで範囲を合わせましょう。

2

analogWriteをPWM非対応のピンに使ってしまう。~マークのないピンでは、中間の明るさが正しく出ません。ボードのピン配置図で対応ピンを確認してください。

3

電圧計算で整数同士の割り算をしてしまう。5 / 1023のように整数だけで書くと結果が0になります。5.0 / 1023.0のように小数点を含めましょう。

4

analogReadをデジタルピンに使ってしまう。A0〜A5のようなアナログ入力ピン以外では使用できません。

5

map()の変換前・変換後の範囲を書き間違える。特に3番目と4番目(変換前の最小・最大)、5番目と6番目(変換後の最小・最大)を混同しないよう、コメントを付けておくと安心です。

09

FAQ・まとめ

analogRead()とanalogWrite()は何が違うのですか?

analogRead()はセンサーなどから「値を読み取る」命令で、0〜1023の1024段階で返ってきます。analogWrite()はLEDやモーターへ「値を送り出す」命令で、0〜255の256段階でPWMという方式の信号を出力します。読み取りと書き込みで、扱う数字の範囲も向きも逆になる点が最大の違いです。

analogRead()の値はどのピンでも使えますか?

いいえ。analogRead()はA0〜A5のようなアナログ入力ピンでのみ使えます。デジタルピン(0〜13など)では使用できません。一方analogWrite()は、ボード上で~マークが付いたPWM対応のデジタルピンでのみ使用でき、Arduino Unoでは3・5・6・9・10・11番ピンが該当します。

PWMは本当にアナログ電圧を出しているのですか?

厳密には違います。PWMはHIGHとLOWを非常に高速に切り替えているだけで、実際に中間の電圧が出ているわけではありません。しかし人の目やモーター、LEDにとっては、その高速な点滅の「オンの時間の割合」が、あたかも中間の電圧であるかのように感じられます。これが擬似的なアナログ出力と呼ばれる理由です。

map関数を使えば必ず正確な値になりますか?

map()は整数(int)だけで計算するため、小数点以下は切り捨てられます。0〜1023を0〜255に変換するような大まかな範囲変換では問題になりませんが、正確な小数の計算が必要な場面では誤差が出ることがあるため、必要に応じてfloat型での計算に置き換えることも検討してください。

analogRead()とanalogWrite()は、名前は似ていても「読む」と「書く」という正反対の役割を持ち、扱う数字の範囲も0〜1023と0〜255でまったく違います。この違いさえ体に染みつけば、センサーの値をLEDやモーターに反映させる工作は驚くほどスムーズになります。まずは7章の実践コードを実際に書き換えて、センサー値・電圧・LEDの明るさが連動して変化する様子を、その目で確かめてみてください。

ARDUINO ANALOG READ & WRITE GUIDE 2026 — 「読む」と「書く」、範囲の違いを制する者がセンサー工作を制す。



関連記事

特集記事

コメント

この記事へのコメントはありません。

TOP
CLOSE