回答編集履歴

3

まとめ

2020/08/10 02:32

投稿

thkana
thkana

スコア7703

test CHANGED
@@ -1,3 +1,43 @@
1
+ 8/10追記
2
+
3
+ そもそもの質問は
4
+
5
+ > 一般的な対策があれば教えていただきたいと思います。
6
+
7
+
8
+
9
+ でしたっけ。それに答えるならば、
10
+
11
+ **起こっている現象・事実をしっかり観察し、その結果から原因を推察し、必要に応じて実験するなど推察の正当性を確認し、その原因に対してなんらかの手を打ち、効果を確認する**
12
+
13
+ ということになるでしょうか。
14
+
15
+
16
+
17
+ >「一つのファイルに保存する上限容量が決まっている」ということ
18
+
19
+
20
+
21
+ 起こっている現象をちゃんと観察せず、誤った推測に飛びついて
22
+
23
+
24
+
25
+ > 一つのファイルに一定以上の容量が溜まったら新しいファイルを作成するなどで
26
+
27
+
28
+
29
+ 適切でない対応を考えていたわけで。そういうことのないように。
30
+
31
+
32
+
33
+ 以下元の回答
34
+
35
+
36
+
37
+ ---
38
+
39
+
40
+
1
41
  出来たファイルの容量が一定...というのは結果です。
2
42
 
3
43
 

2

実験結果

2020/08/10 02:32

投稿

thkana
thkana

スコア7703

test CHANGED
@@ -119,3 +119,509 @@
119
119
  場合によっては、データの書き込み毎にファイルをopen/closeするのをやめた方がいいかも知れません。そうすると、測定終了時にはボタンを押すなどしてファイルをクローズしてやるという操作方法になるかも知れませんが。
120
120
 
121
121
  この辺は後で(明日か)ちょっと実験してみようかしら。
122
+
123
+
124
+
125
+ ---
126
+
127
+ 追記。
128
+
129
+ M5Stackで実験してみました。多分ライブラリは一緒だと思います。
130
+
131
+ ソースは、loop()関数を以下のように変更。
132
+
133
+ ```C++
134
+
135
+ unsigned long cnt=0;
136
+
137
+ const int delay_time=1;//待ち時間に耐えられないので変更
138
+
139
+ void loop() {
140
+
141
+ unsigned long t0=millis();
142
+
143
+ Serial.print(++cnt);
144
+
145
+ Serial.print(" ");
146
+
147
+ Serial.print(__LINE__);//__LINE__はソースの行数を得るマクロ。ここは110行
148
+
149
+ Serial.print(" ");
150
+
151
+ Serial.println(millis()-t0);
152
+
153
+
154
+
155
+ //BME280 デバイスがないので暫定データを与えるだけ
156
+
157
+ //Temp = mySensorA.readTempC();
158
+
159
+ Temp=25.01;
160
+
161
+ //Hum = mySensorA.readFloatHumidity();
162
+
163
+ Hum=50.01;
164
+
165
+ //hPa = mySensorA.readFloatPressure() / 100;
166
+
167
+ hPa=1000.01;
168
+
169
+
170
+
171
+ //NTP
172
+
173
+ getLocalTime(&timeInfo);//tmオブジェクトのtimeInfoに現在時刻を入れ込む
174
+
175
+ sprintf(s, "%04d/%02d/%02d %02d:%02d:%02d",
176
+
177
+ timeInfo.tm_year + 1900, timeInfo.tm_mon + 1, timeInfo.tm_mday,
178
+
179
+ timeInfo.tm_hour, timeInfo.tm_min, timeInfo.tm_sec);//人間が読める形式に変換
180
+
181
+
182
+
183
+ //Serial.print
184
+
185
+ Serial.println(s);
186
+
187
+ Serial.print("Temp: ");
188
+
189
+ Serial.print(Temp);
190
+
191
+ Serial.println(" ℃");
192
+
193
+ Serial.print("Hum: ");
194
+
195
+ Serial.print(Hum);
196
+
197
+ Serial.println(" %");
198
+
199
+ Serial.print("Press: ");
200
+
201
+ Serial.print(hPa);
202
+
203
+ Serial.println(" hPa");
204
+
205
+
206
+
207
+ //SD_writting
208
+
209
+ Serial.print(cnt);
210
+
211
+ Serial.print(" ");
212
+
213
+ Serial.print(__LINE__);//ここは143行
214
+
215
+ Serial.print(" ");
216
+
217
+ Serial.println(millis()-t0);
218
+
219
+ //String backLog = SD_read(); //変更点
220
+
221
+ Serial.print(cnt);
222
+
223
+ Serial.print(" ");
224
+
225
+ Serial.print(__LINE__);//ここは149行
226
+
227
+ Serial.print(" ");
228
+
229
+ Serial.println(millis()-t0);
230
+
231
+ myFile = SD.open(FILE_NAME, FILE_APPEND); //変更点,元はFILE_WRITE
232
+
233
+ Serial.print(cnt);
234
+
235
+ Serial.print(" ");
236
+
237
+ Serial.print(__LINE__);//ここは155行
238
+
239
+ Serial.print(" ");
240
+
241
+ Serial.println(millis()-t0);
242
+
243
+ if (myFile) {
244
+
245
+ Serial.print("Writing to ");
246
+
247
+ Serial.println(FILE_NAME);
248
+
249
+ //myFile.print(backLog); //変更点
250
+
251
+ myFile.print(s);
252
+
253
+ myFile.print(",");
254
+
255
+ myFile.print(Temp);
256
+
257
+ myFile.print(",");
258
+
259
+ myFile.print(Hum);
260
+
261
+ myFile.print(",");
262
+
263
+ myFile.print(hPa);
264
+
265
+ myFile.println();
266
+
267
+ myFile.close();
268
+
269
+ Serial.println("done.");
270
+
271
+ } else {
272
+
273
+ Serial.print("error opening ");
274
+
275
+ Serial.println(FILE_NAME);
276
+
277
+ }
278
+
279
+ Serial.print(cnt);
280
+
281
+ Serial.print(" ");
282
+
283
+ Serial.print(__LINE__);//ここは178行
284
+
285
+ Serial.print(" ");
286
+
287
+ Serial.println(millis()-t0);
288
+
289
+ delay(delay_time); // Wait time
290
+
291
+ Serial.print(cnt);
292
+
293
+ Serial.print(" ");
294
+
295
+ Serial.print(__LINE__);//ここは184行
296
+
297
+ Serial.print(" ");
298
+
299
+ Serial.println(millis()-t0);
300
+
301
+ Serial.println();
302
+
303
+ }
304
+
305
+ ```
306
+
307
+ //変更点の3箇所を元のソースのままで実行した場合、シリアル出力は
308
+
309
+ ```Text
310
+
311
+ (測定1回め)
312
+
313
+ 1 110 0
314
+
315
+ 2020/08/09 12:47:35
316
+
317
+ Temp: 25.01 ℃
318
+
319
+ Hum: 50.01 %
320
+
321
+ Press: 1000.01 hPa
322
+
323
+ 1 143 20
324
+
325
+ 1 149 21
326
+
327
+ 1 155 22
328
+
329
+ Writing to /log.csv
330
+
331
+ done.
332
+
333
+ 1 178 1025
334
+
335
+ 1 184 1026
336
+
337
+ (10回目)
338
+
339
+ 10 110 0
340
+
341
+ 2020/08/09 12:47:36
342
+
343
+ Temp: 25.01 ℃
344
+
345
+ Hum: 50.01 %
346
+
347
+ Press: 1000.01 hPa
348
+
349
+ 10 143 0
350
+
351
+ 10 149 10
352
+
353
+ 10 155 17
354
+
355
+ Writing to /log.csv
356
+
357
+ done.
358
+
359
+ 10 178 29
360
+
361
+ 10 184 30
362
+
363
+ (100回目)
364
+
365
+ 100 110 0
366
+
367
+ 2020/08/09 12:47:44
368
+
369
+ Temp: 25.01 ℃
370
+
371
+ Hum: 50.01 %
372
+
373
+ Press: 1000.01 hPa
374
+
375
+ 100 143 0
376
+
377
+ 100 149 103
378
+
379
+ 100 155 110
380
+
381
+ Writing to /log.csv
382
+
383
+ done.
384
+
385
+ 100 178 130
386
+
387
+ 100 184 131
388
+
389
+ (500回目)
390
+
391
+ 500 110 0
392
+
393
+ 2020/08/09 12:51:01
394
+
395
+ Temp: 25.01 ℃
396
+
397
+ Hum: 50.01 %
398
+
399
+ Press: 1000.01 hPa
400
+
401
+ 500 143 0
402
+
403
+ 500 149 903
404
+
405
+ 500 155 911
406
+
407
+ Writing to /log.csv
408
+
409
+ done.
410
+
411
+ 500 178 963
412
+
413
+ 500 184 964
414
+
415
+ (1000回目)
416
+
417
+ 1000 110 0
418
+
419
+ 2020/08/09 13:06:18
420
+
421
+ Temp: 25.01 ℃
422
+
423
+ Hum: 50.01 %
424
+
425
+ Press: 1000.01 hPa
426
+
427
+ 1000 143 0
428
+
429
+ 1000 149 2802
430
+
431
+ 1000 155 2810
432
+
433
+ Writing to /log.csv
434
+
435
+ done.
436
+
437
+ 1000 178 2876
438
+
439
+ 1000 184 2877
440
+
441
+ ```
442
+
443
+ となり、読み込み/書き込みの時間がどんどん増えていっていることがわかります。特に`SD_read()`関数ですね。1000回測定した時点で、1回の測定で3秒弱かかるようになってしまいました。
444
+
445
+
446
+
447
+ //変更点のところをコメントアウト、FILE_APPENDに変更した場合は
448
+
449
+ ```Text
450
+
451
+ (1回目)
452
+
453
+ 1 110 0
454
+
455
+ 2020/08/09 13:21:48
456
+
457
+ Temp: 25.01 ℃
458
+
459
+ Hum: 50.01 %
460
+
461
+ Press: 1000.01 hPa
462
+
463
+ 1 143 1
464
+
465
+ 1 149 1
466
+
467
+ 1 155 1
468
+
469
+ Writing to /log.csv
470
+
471
+ done.
472
+
473
+ 1 178 29
474
+
475
+ 1 184 30
476
+
477
+ (100回目)
478
+
479
+ 100 110 0
480
+
481
+ 2020/08/09 13:21:49
482
+
483
+ Temp: 25.01 ℃
484
+
485
+ Hum: 50.01 %
486
+
487
+ Press: 1000.01 hPa
488
+
489
+ 100 143 5
490
+
491
+ 100 149 6
492
+
493
+ 100 155 8
494
+
495
+ Writing to /log.csv
496
+
497
+ done.
498
+
499
+ 100 178 16
500
+
501
+ 100 184 17
502
+
503
+ (1000回目)
504
+
505
+ 1000 110 0
506
+
507
+ 2020/08/09 13:22:02
508
+
509
+ Temp: 25.01 ℃
510
+
511
+ Hum: 50.01 %
512
+
513
+ Press: 1000.01 hPa
514
+
515
+ 1000 143 5
516
+
517
+ 1000 149 6
518
+
519
+ 1000 155 9
520
+
521
+ Writing to /log.csv
522
+
523
+ done.
524
+
525
+ 1000 178 17
526
+
527
+ 1000 184 18
528
+
529
+ (10000回目)
530
+
531
+ 10000 110 0
532
+
533
+ 2020/08/09 13:24:21
534
+
535
+ Temp: 25.01 ℃
536
+
537
+ Hum: 50.01 %
538
+
539
+ Press: 1000.01 hPa
540
+
541
+ 10000 143 5
542
+
543
+ 10000 149 6
544
+
545
+ 10000 155 9
546
+
547
+ Writing to /log.csv
548
+
549
+ done.
550
+
551
+ 10000 178 15
552
+
553
+ 10000 184 16
554
+
555
+ (20363回目)
556
+
557
+ 20363 110 0
558
+
559
+ 2020/08/09 13:27:07
560
+
561
+ Temp: 25.01 ℃
562
+
563
+ Hum: 50.01 %
564
+
565
+ Press: 1000.01 hPa
566
+
567
+ 20363 143 5
568
+
569
+ 20363 149 6
570
+
571
+ 20363 155 9
572
+
573
+ Writing to /log.csv
574
+
575
+ done.
576
+
577
+ 20363 178 15
578
+
579
+ 20363 184 16
580
+
581
+ (20364回目)
582
+
583
+ 20364 110 0
584
+
585
+ 2020/08/09 13:27:08
586
+
587
+ Temp: 25.01 ℃
588
+
589
+ Hum: 50.01 %
590
+
591
+ Press: 1000.01 hPa
592
+
593
+ 20364 143 5
594
+
595
+ 20364 149 6
596
+
597
+ 20364 155 9
598
+
599
+ Writing to /log.csv
600
+
601
+ done.
602
+
603
+ 20364 178 15
604
+
605
+ 20364 184 15
606
+
607
+ ```
608
+
609
+ となり、実行時間には大きな変化はありません。この方法であれば、安定して測定が続けられるものと考えられます。
610
+
611
+
612
+
613
+ このとき、SDカードに生成したCSVファイルについて
614
+
615
+ ```CSV
616
+
617
+ (20364行目)2020/08/09 13:27:07,25.01,50.01,1000.01
618
+
619
+ (20365行目)2020/08/09 13:27:08,25.01,50.01,1000.01
620
+
621
+ ```
622
+
623
+ となっており、少なくともこの範囲ではファイルの書き込みが正常に行えていることを確認しました。
624
+
625
+
626
+
627
+ なお、正常動作としても一回の測定値の処理に10~30msかかるわけで、単純にdelayを1000ms入れて「1秒」としていると、100回も測定すれば1回分データの個数がずれてくることになります。それで構わないのならそのままでもよいですが、きっちり1秒を期待するなら、せっかくntpでとっている時刻を使って、「秒」の数字が変化したら測定/記録する、という作りにした方がよろしいかと思います。

1

情報の追加をうけて追記

2020/08/09 05:04

投稿

thkana
thkana

スコア7703

test CHANGED
@@ -23,3 +23,99 @@
23
23
 
24
24
 
25
25
  アマチュア的には、原因を絞り込む前にとりあえずやってみてそれで動いたならOK、という解決も駄目とは言い切れないですかね。プロなら駄目ですけど。
26
+
27
+
28
+
29
+ ---
30
+
31
+ 質問に情報が追加されたので...
32
+
33
+
34
+
35
+ ファイル書き込みと同時にシリアルにも出力しているのですね? では何故シリアルがどうなっているか見ていないのでしょう。見なかったら何のために出力したのですか?
36
+
37
+
38
+
39
+ さて。毎秒以下の情報がファイルに追加されるわけですね。
40
+
41
+ ```C++
42
+
43
+ myFile.print(s);//sは日付情報19文字
44
+
45
+ myFile.print(",");
46
+
47
+ myFile.print(Temp);//5文字ぐらい
48
+
49
+ myFile.print(",");
50
+
51
+ myFile.print(Hum);//4文字ぐらい
52
+
53
+ myFile.print(",");
54
+
55
+ myFile.print(hPa);//6文字ぐらい
56
+
57
+ myFile.println();//CR/LFで2文字
58
+
59
+ ```
60
+
61
+ でおおよそ39文字、ですか。
62
+
63
+ データの追加の処理を全て自分でメモリに抱え込んでやっていますから、メモリサイズ以上のファイルは作れません。ESP32のSRAMサイズは520KB、これをフルに使えたとして520x1024/39=13653.xx秒なので、どんなに頑張っても4時間弱でロギングは不可能になり、
64
+
65
+ > ・起動中は常にデータを保存したい
66
+
67
+
68
+
69
+ を満たさないことが明白です。
70
+
71
+ 「データの追加の処理を全て自分でメモリに抱え込んでやって」いるのが非常識なので、ファイルはアペンド(追記)モードで開いてそのまま追加データをprintしてやればいいのでは。データの「追加」はライブラリに任せましょう。
72
+
73
+ ```C++
74
+
75
+ //SD_writting
76
+
77
+ //String backLog = SD_read(); //削除
78
+
79
+ myFile = SD.open(FILE_NAME, FILE_APPEND); //追記モードで開く
80
+
81
+ if (myFile) {
82
+
83
+ Serial.print("Writing to ");
84
+
85
+ Serial.println(FILE_NAME);
86
+
87
+ //myFile.print(backLog); //削除
88
+
89
+ myFile.print(s);
90
+
91
+ myFile.print(",");
92
+
93
+ myFile.print(Temp);
94
+
95
+ myFile.print(",");
96
+
97
+ myFile.print(Hum);
98
+
99
+ myFile.print(",");
100
+
101
+ myFile.print(hPa);
102
+
103
+ myFile.println();
104
+
105
+ myFile.close();
106
+
107
+ Serial.println("done.");
108
+
109
+ }
110
+
111
+ ```
112
+
113
+ さて。
114
+
115
+ そもそも14:56の時点で55サンプルしか取れていないというのも看過できない情報です。
116
+
117
+ SD_read()が結構重い処理なので、これを削っただけでも相当軽くはなると思いますが、2kB程度のデータを処理しただけでそんなに重くなるかなぁ...
118
+
119
+ 場合によっては、データの書き込み毎にファイルをopen/closeするのをやめた方がいいかも知れません。そうすると、測定終了時にはボタンを押すなどしてファイルをクローズしてやるという操作方法になるかも知れませんが。
120
+
121
+ この辺は後で(明日か)ちょっと実験してみようかしら。