Microでシリアルモニタを使用する際の注意点を説明します。第21回の記事で「シリアルモニタ」の使い方を習得しました。Microでシリアルモニタを使用する際、注意点がありますのでこの補足記事では問題とその対応方法を説明します。Microのシリアルモニタを使おうとして以下のようなスケッチを書くとうまく動きません。以下のスケッチは、setup関数の中でSerial.printlnを使って「シリアルモニタ開始」という文字を表示する内容です。loopでは何もしない}このスケッチでは、setup関数の中で、最初にシリアルモニタを使用するために「Serial.begin(9600);」、そのあとシリアルモニタに文字を表示するために「Serial.println(“シリアルモニタ開始”);」としています。Microで動作させてみてください。シリアルモニタに何も表示されないと思います。Serial.begin(9600);と書いた後にSerial.println関数で文字を表示しているのに、なぜ表示されないのでしょうか。これから、この原因と対応方法について詳しく説明します。シリアルモニタに文字が表示されない原因Arduinoのシリアルモニタの通信方法として、大きく分けて2種類あります。以下の画像は「ESP32-DevKitC」というWi-FiやBluetoothなどさまざまな機能が搭載されているArduino互換ボードです。このボードには、ESP32-DevKitCを動かしている本体モジュールとは別に、外部とUSBで通信するためのUSB通信モジュールが搭載されています。このように通信モジュールが搭載されているArduinoボードでは、先ほどのようなSerial.println関数でシリアルモニタに文字が表示されない、ということはありません。Microボードを確認してみましょう。Unoにくらべるとずいぶんスッキリしてますよね。MicroにはUSBで通信するための通信モジュールが搭載されていないんです。MicroをUSBケーブルでPCに接続してスケッチを送ったり、シリアルモニタで文字を表示したりしてましたよね。Microのモジュール本体の中に、外部とUSBで通信する機能が入っているためです。この機能は常に動作しているわけではなく、Serial.begin関数によりUSB通信の機能が動作を開始して使えるようになります。Serial.begin(9600);の後、ほんのちょっとの時間(せいぜい数ms)、準備に時間がかかります。MicoroはUSBで外部と通信する機能を使えるように準備しますが、その準備が終わる前にSerial.println関数を処理したため、シリアモニタに文字列がきちんと表示されなかったわけです。Microが通信モジュールの準備が終わるまで待つ必要があるんです。それでは、具体的にスケッチではどのように書けばいいのか説明します。Microでシリアルモニタを使用する場合、スケッチには以下のように書きます。以下は先ほどのsetup関数部分です。Serial.println("シリアルモニタ開始");}シリアルモニタの準備ができるまで待つためには、以下のようにスケッチに追加すればOKです。{}この具体的な動作を完全に理解するには新しい知識が必要になりますので、ここでは簡単に説明しておきます。IDEが裏で宣言してくれているものです。この変数はシリアルモニタの準備ができていない場合は「0」、準備ができた場合は「1」になります。「Serial」の前についている「!」は否定の意味の記号です。準備ができていない場合の「Serial」の値は0ですので、その否定で「1」になります。)」は、準備ができていない間繰り返す、という意味になります。MicroのUSB通信モジュールが準備できるまでの間、while文で何もしないで待つ、ということをしています。第21回の記事のスケッチはなぜ動いていたのかかなり前の記事になりますので、すっかり忘れてしまっているかもしれません。第21回のシリアルモニタを使用した記事では、シリアルモニタの準備ができるまで待つ、ということをしていませんでした。Microボードに送ってシリアルモニタを動作させると、問題なく「シリアルモニタのテスト」という文字が表示されていましたよね。答えを読む前にちょっと考えてみてください。Microがこのスケッチをどのように実行するか順を追って確認してみましょう。setup関数で「Serial.begin(9600);」によりシリアルモジュールの準備を開始します。この段階ではUSBモジュールはまだ動作していません次にloop関数を実行します。loop関数の最初はSerial.println関数でシリアルモニタに文字列を表示しようとしますが、この段階ではUSBモジュールがまだ準備できていませんので、この文字列は表示されません次にdelay(1000);で1秒待ちます。この間にUSBモジュールの準備が完了しますloop関数は繰り返されますので、またSerial.println関数に戻って文字列の表示をします。この時USBモジュールの準備は完了していますので、シリアルモニタに文字列が表示されますdelay(1000);で1秒待ちます以下、(4)と(5)の動作の繰り返しなりますまとめると、1回目のSerial.println関数は失敗していたのですが、2回目以降はUSBモジュールが動作しているためうまく出力されているように見えた、というわけです。本来でしたら第21回の記事で説明すべきですが、while文の説明がその後でしたので、この説明は補足記事にしました。