Arduino UNO R3,Leonardo / IDE 1.0.1
前回、LM35DZの動作確認をしたのでArduinoのアナログポートに複数個接続してみた所、測定値が時々跳ね上がる現象が発生。
LM35DZはA0〜A5に約50cmのケーブルで接続。パソコン筐体内の複数箇所の温度を測定するつもりで作った。
温度センサを同じ所にまとめて動作確認をした時に以下の現象が発生。
現象:時々、A0ポートに接続したLM35DZが6℃、A5ポートに接続したのが330℃を表示。測定間隔は約1分。
最初、Arduino Leonardo(ATmega 32U4)で確認したがArduino UNO R3(ATmega328)でも再現。こちらで調査開始。
アナログポートに接続したLM35DZを入れ替えても現象同じ。センサ個別についてまわる問題ではない。
以前見かけたこの記事が詳しい。これに当たったようだ。これがなければわからなかっただろう。
// LM35DN x6 Thermal Logger
// http://arduino.cc/en/Reference/AnalogReference
unsigned int t,c;
float sc;
unsigned long time;
#define NUM_LM35 6
int LM35[NUM_LM35];
int Shuffle[NUM_LM35] ; // shuffle LM35 port 0-5
// initialize the library with the numbers of the interface pins
///LiquidCrystal lcd(12, 11, 5, 4, 3, 2);
float temp5v(int ain) { // analog 0-1023 10mV/Celsius ,5V*100/1024
return ain*5.0*100/1024;
}
float temp3v3(int ain) { // analog 0-1023 10mV/Celsius,3.3V*100/1024
return ain*3.3*100/1024;
}
float temp2v56(int ain) { // analog 0-1023 10mV/Celsius,2.56V*100/1024
return ain*2.56*100/1024;
}
float temp1v1(int ain) { // analog 0-1023 10mV/Celsius,1.1V*100/1024
return ain*1.1*100/1024;
}
void setup() {
// set up the LCD's number of columns and rows:
// lcd.begin(16, 2);
Serial.begin(9600);
// External Aref(3.3V)
// analogReference(EXTERNAL);//3.3V
// Internal Aref(1.1V) ATmega328 ???
analogReference(INTERNAL);
/*
Shuffle[0]=A0;
Shuffle[1]=A1;
Shuffle[2]=A2;
Shuffle[3]=A3;
Shuffle[4]=A4;
Shuffle[5]=A5;
*/
/*
Shuffle[0]=A4;
Shuffle[1]=A2;
Shuffle[2]=A5;
Shuffle[3]=A0;
Shuffle[4]=A3;
Shuffle[5]=A1;
*/
// for (int i=0; i<=NUM_LM35;i++) LM35[i]=Shuffle[i] ;
/*
LM35[0]=A0;
LM35[1]=A1;
LM35[2]=A2;
LM35[3]=A3;
LM35[4]=A4;
LM35[5]=A5;
*/
LM35[0]=A4;
LM35[1]=A2;
LM35[2]=A5;
LM35[3]=A0;
LM35[4]=A3;
LM35[5]=A1;
}
void loop() {
time=millis();Serial.print(time);Serial.print(" ");
for(int i=0;i<=NUM_LM35;i++) {
t=analogRead(LM35[i]); // (0...1023)
sc=temp3v3(t); // Selcius
// Serial.print(sc);
// Serial.print(":");
Serial.print(t);
if (i<NUM_LM35) Serial.print(" ");
delay(100);
}
Serial.println("");
delay(60000); // 1000
}
(1)A/Dコンバータ(ADC)のリファレンス電圧による違い→ 3.3Vより1.1Vの方が発生頻度が上がる
analogReference(EXTERNAL); // 3.3VをAREF端子に接続
analogReference(INTERNAL); // 1.1V内部リファレンス
(2)測定間隔による違い→1分間隔よりも1秒間隔の方が頻度が下がる(が発生)
(3)チャネルによる違い
A0,A1,A2,A3,A4,A5の順にリード→ A0で少し下がり、A5で大きく跳ね上がる
A4,A2,A5,A0,A3,A1の順にリード→ A4で少し下がり、A1で大きく跳ね上がる
つまり、ポートに関係なく読み出し順の最初と最後で異常。
(4)チャネルによる違いその2
Shuffle[0]=A4;
Shuffle[1]=A2;
Shuffle[2]=A5;
Shuffle[3]=A0;
Shuffle[4]=A3;
Shuffle[5]=A1;
for (int i=0; i<=NUM_LM35;i++) LM35[i]=Shuffle[i] ;
として analogRead(LM35[i]);とやってみたら再現しなくなった。Shuffle[i]に代入するポート番号をA0〜A5に整列させても発生しない。
ATmega32U4のデータシートを見てみると、ADCの実体は1つで入力ポートを切り替えている。
きょうはここまで。