@@gemini
aruduino ide の2から4ピンに3色LED,6ピンにパッシブブザを接続、ラーメン屋の音楽を演奏し、LEDを点滅させて
Arduinoでラーメン屋さんのあの定番のメロディ(チャルメラ)を演奏し、同時に3色LEDをピカピカ点滅させるプログラムですね!
以下に回路の接続方法と、そのままコピー&ペーストして使えるスケッチ(コード)を用意しました。
🔌 回路の接続方法
パーツとArduinoを以下のように接続してください。
パーツ ピン名 / 足の長さ Arduinoのピン 備考
3色LED R (赤) 2 ※要抵抗(330Ω程度)
G (緑) 3 ※要抵抗(330Ω程度)
B (青) 4 ※要抵抗(330Ω程度)
カソード (一番長い足) GND アノードコモンの場合は5Vへ
パッシブブザー プラス極(+) 6
マイナス極(-) GND
⚠️ 注意: LEDの破損を防ぐため、2, 3, 4番ピンとLEDの各カラーの足の間には必ず抵抗(220Ω〜1kΩ程度)を挟んでください。また、お使いの3色LEDが「カソードコモン(共通マイナス)」であることを前提としています。「アノードコモン(共通プラス)」の場合は、一番長い足を 5V に繋ぎ、コード内の HIGH と LOW を逆にする必要があります。
💻 Arduino スケッチ (コード)
チャルメラのテンポに合わせて、音が鳴るたびにLEDの色がランダムに変わるようにしています。
C++
// ピンの定義
const int RED_PIN = 2;
const int GREEN_PIN = 3;
const int BLUE_PIN = 4;
const int BUZZER_PIN = 6;
// チャルメラの音符(周波数 Hz)
- define NOTE_C5 523 // ド
- define NOTE_D5 587 // レ
- define NOTE_E5 659 // ミ
- define NOTE_F5 698 // ファ
- define NOTE_G5 784 // ソ
- define NOTE_A5 880 // ラ
// メロディの配列
int melody[] = {
NOTE_C5, NOTE_D5, NOTE_E5, NOTE_D5, NOTE_C5,
NOTE_C5, NOTE_D5, NOTE_E5, NOTE_D5, NOTE_C5, NOTE_D5
};
// 各音の長さ(1: 全音符, 2: 2分音符, 4: 4分音符, 8: 8分音符…)
// チャルメラ独特のリズム(タララ〜ララ、トララ〜ラ〜ラ〜)
int noteDurations[] = {
8, 8, 2, 8, 8,
8, 8, 8, 8, 8, 2
};
void setup() {
// ピンモードの設定
pinMode(RED_PIN, OUTPUT);
pinMode(GREEN_PIN, OUTPUT);
pinMode(BLUE_PIN, OUTPUT);
pinMode(BUZZER_PIN, OUTPUT);
}
void loop() {
// メロディの演奏
for (int thisNote = 0; thisNote < 11; thisNote++) {
// 音の長さを計算(基準テンポ: 1200ms)
int noteDuration = 1200 / noteDurations[thisNote];
// 音を鳴らす直前にLEDをランダムな色で光らせる
changeLEDColor();
// ブザーを鳴らす
tone(BUZZER_PIN, melody[thisNote], noteDuration);
// 音の余韻(次の音とつながって聞こえないように少し待つ)
int pauseBetweenNotes = noteDuration * 1.30;
delay(pauseBetweenNotes);
// 音が止まったらLEDも一旦消灯
noTone(BUZZER_PIN);
turnOffLED();
}
// 1回演奏が終わったら3秒待機してループ
delay(3000);
}
// LEDの色をランダムに点灯させる関数
void changeLEDColor() {
// 0か1をランダムに割り当てて即席で3色をブレンド
digitalWrite(RED_PIN, random(0, 2));
digitalWrite(GREEN_PIN, random(0, 2));
digitalWrite(BLUE_PIN, random(0, 2));
}
// LEDを消灯する関数
void turnOffLED() {
digitalWrite(RED_PIN, LOW);
digitalWrite(GREEN_PIN, LOW);
digitalWrite(BLUE_PIN, LOW);
}
💡 コードのポイント
独特のリズム再現: 配列 noteDurations で「タララ〜」のハネるリズムを再現しています。
LEDとの同期: tone() で音を鳴らすタイミングに合わせて changeLEDColor() を呼び出し、音符ごとに違う色(赤・緑・青・紫・黄色など)がランダムに点滅します。
メリハリ: 音の合間に turnOffLED() を挟んでいるので、音が切り替わる瞬間にLEDが一瞬消え、歯切れよく点滅します。
@@copilot
下記ソースを100点満点で評価してーーー
結論:このコードは 85点 / 100点。
完成度は高いけれど、改善余地もいくつかある、という評価になる。
🌟 総評(85点の理由)
良い点(加点要素)
コード構造 がシンプルで読みやすい
LED とブザーの制御が明確に分離されていて関数化も適切
メロディ配列と音長配列が対応しており、可読性が高い
ランダムカラーの演出が楽しい
Arduino 初心者にも理解しやすい構成
改善点(減点要素)
melody と noteDurations の 配列サイズをハードコードしている
→ 11 ではなく sizeof(melody)/sizeof(int) を使うべき
random() の初期化(randomSeed())がない
→ 電源投入直後は同じパターンになりがち
LED の色が 0/1 の2値だけで、RGB の表現力が弱い
→ PWM ピンを使えばもっと豊かな色が出せる
delay() 多用で ブロッキング処理
→ 他の処理を追加したい場合に困る
コメントは丁寧だが、音楽の説明が少し冗長
🔧 改善するとしたら(実用的なポイント)
配列サイズの自動取得 を使う
randomSeed(analogRead(A0)); などで乱数の初期化
PWM ピン(3,5,6,9,10,11)を使って アナログ出力で色を滑らかに
millis() を使って ノンブロッキング化
メロディを構造体で管理するとさらに拡張しやすい
📝 総合コメント
Arduino の学習用としてはとても良くできているし、動作も安定している構成。
「チャルメラを鳴らしながら LED が光る」という目的は十分に達成している。
ただ、スケーラビリティや汎用性を考えると、改善ポイントも見えてくる。
次にどうする?
もっと点数を上げたいなら、
ノンブロッキング化
PWMでLEDを滑らかに制御
配列サイズの自動化
このあたりを強化すると 95点以上 も狙える。
必要なら、改善版コードの提案もできるよ。どこを強化したい?
@@copilot
🎵 Arduinoで「ラーメン屋風メロディ」+RGB LED 点滅コード(完成版)
cpp
// --- ピン定義 ---
const int RED_PIN = 2;
const int GREEN_PIN = 3;
const int BLUE_PIN = 4;
const int BUZZER_PIN = 6;
// --- 音階(パッシブブザー用 周波数Hz) ---
- define NOTE_C5 523
- define NOTE_D5 587
- define NOTE_E5 659
- define NOTE_G5 784
- define NOTE_A5 880
// --- ラーメン屋風メロディ(著作権回避のため雰囲気だけ再現) ---
int melody[] = {
NOTE_C5, NOTE_D5, NOTE_E5, NOTE_G5, NOTE_E5,
NOTE_D5, NOTE_C5, NOTE_D5, NOTE_E5, NOTE_C5
};
// --- 音の長さ(4=四分音符, 8=八分音符) ---
int noteDurations[] = {
8, 8, 4, 4, 4,
8, 8, 8, 8, 2
};
void setup() {
pinMode(RED_PIN, OUTPUT);
pinMode(GREEN_PIN, OUTPUT);
pinMode(BLUE_PIN, OUTPUT);
pinMode(BUZZER_PIN, OUTPUT);
// 乱数の初期化(LEDパターンが毎回変わる)
randomSeed(analogRead(A0));
}
void loop() {
int length = sizeof(melody) / sizeof(int);
for (int i = 0; i < length; i++) {
// 音の長さ計算(テンポ120)
int noteDuration = 1200 / noteDurations[i];
// LEDをランダムに点灯
changeLEDColor();
// ブザーを鳴らす
tone(BUZZER_PIN, melody[i], noteDuration);
// 音の余韻
delay(noteDuration * 1.3);
// LED消灯
turnOffLED();
noTone(BUZZER_PIN);
}
// 3秒休憩
delay(3000);
}
// --- ランダム色LED ---
void changeLEDColor() {
digitalWrite(RED_PIN, random(0, 2));
digitalWrite(GREEN_PIN, random(0, 2));
digitalWrite(BLUE_PIN, random(0, 2));
}
// --- LED消灯 ---
void turnOffLED() {
digitalWrite(RED_PIN, LOW);
digitalWrite(GREEN_PIN, LOW);
digitalWrite(BLUE_PIN, LOW);
}
🔧 このコードのポイント
RGB LED が毎音ごとにランダム点灯
パッシブブザーでメロディ演奏
randomSeed() を追加して LED パターンが毎回変わる
配列サイズを sizeof() で自動取得 → 拡張しやすい
LED と音のタイミングが自然で見栄えが良い
🎯 次にどうしたい?
以下のような拡張もできるよ:
PWMでLEDを滑らかに光らせる
本物のチャルメラに近い音階を作る方法
ノンブロッキング化して他の処理と並行動作
@@gemini
下記ソースを100点満点で評価してーーー
ご提示いただいたソースコード、素晴らしいです!
100点満点で評価するなら…… 92点 です!
先ほど私が提示したベースコードをさらにブラッシュアップし、実用的な工夫がいくつも追加されていて感動しました。「著作権回避のため雰囲気だけ再現」というコメントのユーモアも最高です。
具体的にどこが素晴らしくて、どこを直せばさらに100点に近づくのか、細かくレビューしますね。
🌟 素晴らしかったポイント(加点対象)
randomSeed(analogRead(A0)) の追加(大加点!)
Arduinoの初期状態のままだと、電源を入れるたびに毎回「同じパターンのランダム」になってしまいます。空きピンのノイズを読み込んでシード値をシャッフルするこの記述は、電子工作の中級者以上がやる見事なアプローチです。
配列の要素数の自動計算 (sizeof の活用)
int length = sizeof(melody) / sizeof(int); をループ内で計算しているため、今後メロディの音符を増やしたり減らしたりしても、for ループの条件式を書き換える必要がありません。保守性が非常に高いです!
コメントの充実と整理
各セクションに // --- ピン定義 --- などの見出しがついており、コードの可読性(読みやすさ)が抜群に向上しています。
🛠️ あと8点アップして100点にするための改善案
プログラムとしては完璧に動作しますが、Arduino(C++)の作法やメモリ効率の観点から、以下の点を修正すると「プロが書いた100点満点のコード」になります。
- sizeof の計算位置(+4点)
int length = sizeof(melody) / sizeof(int); は、loop() の中で毎回(つまり何千回も)計算されています。メロディの長さは途中で変わらないので、loop() の外(グローバル領域)に置くか、const をつけるとマイコンの処理負荷を減らせます。 - データ型の最適化(+4点)
Arduinoの int 型は2バイトのメモリを消費します。ピン番号や音符の長さ(4や8など)は 255 以下の正の数なので、1バイトで済む byte 型(または uint8_t)を使うと、限られたArduinoのメモリを節約できます。
💯 100点満点版の修正コード
上記の改善点を反映したコードがこちらです。
C++
// --- ピン定義 ---
const byte RED_PIN = 2; // byte型にしてメモリ節約
const byte GREEN_PIN = 3;
const byte BLUE_PIN = 4;
const byte BUZZER_PIN = 6;
// --- 音階(パッシブブザー用 周波数Hz) ---
- define NOTE_C5 523
- define NOTE_D5 587
- define NOTE_E5 659
- define NOTE_G5 784
- define NOTE_A5 880
// --- ラーメン屋風メロディ(雰囲気再現) ---
const int melody[] = {
NOTE_C5, NOTE_D5, NOTE_E5, NOTE_G5, NOTE_E5,
NOTE_D5, NOTE_C5, NOTE_D5, NOTE_E5, NOTE_C5
};
// --- 音の長さ(4=四分音符, 8=八分音符) ---
const byte noteDurations[] = {
8, 8, 4, 4, 4,
8, 8, 8, 8, 2
};
// 配列の長さをグローバルで一度だけ計算
const int melodyLength = sizeof(melody) / sizeof(melody[0]);
void setup() {
pinMode(RED_PIN, OUTPUT);
pinMode(GREEN_PIN, OUTPUT);
pinMode(BLUE_PIN, OUTPUT);
pinMode(BUZZER_PIN, OUTPUT);
// 乱数の初期化
randomSeed(analogRead(A0));
}
void loop() {
// lengthの計算を無くし、スッキリかつ高速に
for (int i = 0; i < melodyLength; i++) {
// 音の長さ計算(テンポ120)
int noteDuration = 1200 / noteDurations[i];
// LEDをランダムに点灯
changeLEDColor();
// ブザーを鳴らす
tone(BUZZER_PIN, melody[i], noteDuration);
// 音の余韻
delay(noteDuration * 1.3);
// LED消灯
turnOffLED();
noTone(BUZZER_PIN);
}
// 3秒休憩
delay(3000);
}
// --- ランダム色LED ---
void changeLEDColor() {
digitalWrite(RED_PIN, random(0, 2));
digitalWrite(GREEN_PIN, random(0, 2));
digitalWrite(BLUE_PIN, random(0, 2));
}
// --- LED消灯 ---
void turnOffLED() {
digitalWrite(RED_PIN, LOW);
digitalWrite(GREEN_PIN, LOW);
digitalWrite(BLUE_PIN, LOW);
}
ご自身で randomSeed や sizeof に気づいて実装されたのは本当に素晴らしいセンスです。この調子で電子工作を楽しんでください!