質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.47%
M5Stack

M5Stackは、小型のマイコンモジュールです。拡張モジュールが豊富に用意されており、センサと組み合わせることで測定機能を自由に追加することができます。

Arduino

Arduinoは、AVRマイコン、単純なI/O(入出力)ポートを備えた基板、C言語を元としたArduinoのプログラム言語と、それを実装した統合開発環境から構成されたシステムです。

Q&A

2回答

1194閲覧

delay関数、millis関数の使い方について

mno_

総合スコア0

M5Stack

M5Stackは、小型のマイコンモジュールです。拡張モジュールが豊富に用意されており、センサと組み合わせることで測定機能を自由に追加することができます。

Arduino

Arduinoは、AVRマイコン、単純なI/O(入出力)ポートを備えた基板、C言語を元としたArduinoのプログラム言語と、それを実装した統合開発環境から構成されたシステムです。

0グッド

0クリップ

投稿2023/07/19 12:01

###実現したいこと
M5StickCplusの画面に正確な経過時間を表示させたい。

前提

loop部分を1周する事に1カウントされる変数iを用いて、delayの数字×iで経過時間を表示していた。

実際の時間(スマホ等のストップウォッチ)とのズレがあるため、ズレを無くすにはどうすれば良いか教えて頂けると助かります。 delayやmillsを用いて実現できますでしょうか、

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

y_waiwai

2023/07/19 12:33

どれぐらいのずれがあるんでしょうか
mno_

2023/07/19 13:36

delay200でやった時は60秒経過時点で数秒の遅れでした。
YAmaGNZ

2023/07/19 22:32

loop1回で 色々な処理+delay200 でしょうから200ms+αでしょう。 それを1回200msとしているのだからα分はずれるでしょう。 タイマーの開始時にmillsを取得して、そこからの差分を用いればいいのでは?
YAmaGNZ

2023/07/20 11:41

loopの開始でmillsにて値を取得・・・① loopの最後でmillsにて値を取得・・・② ②-①でloop1回分の時間が出る・・・③ サンプリング間隔-③で得た値をdelayで待てば期待する間隔になるのでは? ③の値がサンプリング間隔より大きい場合など考えないとダメですけど。
tmp

2023/07/23 23:23

その方法でも③の後の計算したdelayから次の開始の①のmillsまでの時間が蓄積される誤差がでてきます。なので最初の1回以外は、①②2回図るのではなく、前回の値の比較で時間を計測すると、蓄積される誤差ではなくなります。
guest

回答2

0

シングルタスクのArduino UNO等ならともかく、内部でRTOSを使っているESP32等の場合、delay()などの待ち関数は一旦OSに動作の権利を返上して、時間が経った後に自分より優先度の高いタスクがなければまた実行権を貰うというものです。つまり、優先度の高いタスクが裏で走っていたら、指定した時間よりも待たされる可能性がある、というのは覚悟しておくべきです。

また、delay()の回数を数えるやり方では、当然ながらdelay()以外の部分でかかる時間は考慮されません。他の処理が十分に軽いなら無視できるだろう、という期待が前提ですが、それがどのくらい持っていい期待なのかは要検討かもしれません(期待精度にもよりますし)。

もう一つ、回数を数える場合は毎回の誤差が蓄積していきます。長時間に渡ってある程度の精度が欲しいのなら、通算時間を扱うmillis()のほうが有利です。

それ以前に、マイコンのクロックが絶対精確かというとそんなことはありません。ESP以外も含めてマイコンの内蔵発振器の場合数%の誤差を持ったりもします。私はESP32のクロック精度のスペックを把握していませんが。
高精度が必要なら、外部に水晶発振器をつけるとか、一般人が手に入れられる最高クラスのタイムベースというとGNSS(GPS)の1pps信号を使うとかいう話にもなってくるでしょう。

投稿2023/07/20 14:48

thkana

総合スコア7647

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

0

とりあえず、
時間計測開始時に、millis関数の戻り値(①)をおいておいて、
計測終了時のmillis関数の戻り値(②)を読み出し、
②から①を引くと、計測時間が出てきます 

投稿2023/07/19 23:00

編集2023/07/20 00:57
y_waiwai

総合スコア87784

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

mno_

2023/07/20 06:28

コメント頂いたところは理解出来たのですが、loop部分1回分の周期?を決めることってできるのでしょうか。サンプリング周期を一定にして処理をしたいのですが…
y_waiwai

2023/07/20 12:59

それでサンプリング周期を決めるってのはムリです。 ふつうはタイマ割り込みなんかを設定して、その割り込みでサンプリングするようにしますな
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

まだベストアンサーが選ばれていません

会員登録して回答してみよう

アカウントをお持ちの方は

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.47%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問