On the Arduino Mega, the ADC is clocked at F_CPU
/128 =
125 kHz (period = 8 µs). Except for the very first one,
each ADC conversion takes 13 ADC clock cycles, i.e. 104 µs. If
you run analogRead()
in a tight loop, like
for (;;)
analogRead(A0);
the CPU has to do some work in between the conversions, and since the
ADC always starts by waiting for a rising edge of the ADC clock, you
loose at least one full ADC cycle in between the conversions. You then
get one conversion every 14 ADC cycles, which results in a sampling
period of 112 µs, and the corresponding sampling frequency of about
8.93 kHz.
The code you showed does a little bit more than an analogRead()
per
iteration: two digitalRead()
, a test, and a Serial.println()
that
involves a binary to decimal conversion. I am not sure the CPU will be
able to handle all that in a mere 8 µs. You might end up using
15 ADC clock cycles per iteration (13 for the conversion,
2 for the computation), which would result in 120 µs
(8.33 kHz) sampling period. Maybe even more. You will have to test
if you want to know for sure. The sampling period is not even guaranteed
to be constant: the code will take longer to run whenever it's
interrupted by the timer interrupt, which the Arduino core uses for
timekeeping purposes...
All this applies as long as the serial output buffer is not full. Once
you have 64 bytes waiting to be sent, the buffer will be full, and
Serial.println()
will start delaying the output, effectively
throttling down your loop to the speed of the serial connection. C.f.
the busybee's answer for the details. Note that the sampling period is
still not constant, as sending a 1-to-4-digit number through the serial
port can take anywhere between 3.125 and 6.25 ms.
If you want a constant sampling period, you have to take control over
the timing yourself. A straightforward example would be:
const uint32_t SAMPLING_PERIOD = 6500; // 6.5 ms
void loop() {
static uint32_t last_sample;
if (micros() - last_sample >= SAMPLING_PERIOD) {
last_sample += SAMPLING_PERIOD;
Serial.println(analogRead(A0));
}
}
You could go faster with a higher baud rate, but you have to always keep
SAMPLING_PERIOD
consistent with your chosen baud rate. The code above
will still produce some jitter in the sampling, mostly due to the timer
interrupt. If this is not acceptable for your application, you will have
to read the datasheet of the microcontroller and learn how to set the
ADC to be “auto-triggered” from a timer.