Need help in atmega 2560 sampling rate

Hi every one,

I need to adjust sampling rate in Arduino atmega 2560 to 1000 samples/sec in channel A0.

Thanks for your assist

Best Regards

You need to take a reading, then wait 1/1000 th second before taking the next reading, and then repeat this process in a loop.

1/1000 second = 1 millisecond (1ms) = 1000 microseconds (1000µs)

Use the technique shown in the 'BlinkWithoutDelay' example sketch, but use micros( ) instead of millis( ), so that you are working in microseconds, to give you the required period between samples.

Hi JohnLincoln,

thanks for your replay, i try this method but it doesn't give an accurate result (+/- few samples), i am asking if there more methods for controlling the AtMega ADC registers?

Thanks again

ADC registers are not the problem. Using them at the proper times are the problem.

Honestly! A 10-bit read takes less than 1/9th of a millisecond. Depending on circuit you will need some settle-time between reading different analog pins but that's about it. You have the full millisecond so the ADC should not be making your code wait, more like the code is making the wait.

Do not code so that the process waits 1 second, makes and processes a read then waits a second, etc as the time between reads will be 1 second plus the read.

Also test your Arduino to see how many counts is a real second and use that number instead of 1000 for millis() or 1 million for micros(). Note that Arduino micros() is to the nearest 4, not nearest 1.

So if I read micros() and then as exactly 1 hour later as possible read micros() again and subtract the first read from the second (micros rolls over a bit after 90 minutes, don't try 2 hours!) I will get the micros per second x 3600 that my Arduino is running.
It may turn out that a real second is taking 992000 micros instead of 1000000. Knowing that, I would trigger a millisecond pulse every 992 micros() as possible, and each time add 992 to the previous start interval time rather than set it to micros() which might be a tiny bit late. The algorithm would be self-correcting.

If you have an external 1 millisecond source you could connect an interrupt to handle your read timing. It should work as accurately as your source.

ahmedfaeq:
i try this method but it doesn't give an accurate result (+/- few samples), i am asking if there more methods for controlling the AtMega ADC registers?

There are many possibilities.

What do you want to do with the ADC readings?

Here is a method to take 1000 readings per second and send them over Serial @115200 baud:

void setup() {
  Serial.begin(115200);
}

unsigned long lastADCsample;
void loop() 
{
  long now=micros();
  if (now-lastADCsample>=1000)
  {
    lastADCsample+=1000;
    Serial.println(analogRead(A0));
  }
}

Is that what you want?

If not: What do you want exactly?

Thanks a lot to every one. Dear jurs this method what i need

ahmedfaeq:
Thanks a lot to every one. Dear jurs this method what i need

Thanks for the positive feedback!

If you use a programming logic like that

  • wait 1000 µs
  • do next ADC reading (which lasts about 120µs)
    Then you will have about one reading per 1120µs, wich is much less than 1000 samples per second.

But if you use a programming logic like hat

  • after 1000 µs since last start of ADC reading
  • do the next ADC reading
    Then it doesn't matter if an ADC reading lasts 30, 120 or 400 µs, you will always start the next ADC reading 1000µs later than the ADC reading before.

This is really not rocket science.
But maybe hard to detect for a beginner who doesn't know that ADC readings are relatively slow and need many, many microseconds of execution time.