1

I'm trying to demonstrate how using a state machine can clarify the logic of most Raspberry Pi projects. All of the code is available as a gist, but the problem portion is around line 34:

while True:
    onoff.read(GPIO.input(button_no))
    time.sleep(.001)

The state machine is designed to use a button (momentary latch) to toggle an LED on and off in a reasonable fashion (push-release, light turns on; push-release, light turns off). The code works as listed in the gist, but as soon as you comment out the sleep call the behavior changes to (push, light turns on; release, light turns off).

Given the real-time nature of the Pi, I believe this pause impacts it in a way that would not apply to a simulated environment. I'm pretty sure it's a Pi-specific issue.

What could be going on, here?

4
  • Perhaps it has something to do with this quote from the project page of RPi.GPIO: "Note that this module is unsuitable for real-time or timing critical applications. This is because you can not predict when Python will be busy garbage collecting. It also runs under the Linux kernel which is not suitable for real time applications - it is multitasking O/S and another process may be given priority over the CPU, causing jitter in your program." I haven't the expertise to say if this is the source of the issue, but it deserves an explanation Jan 12 '14 at 5:27
  • 1
    Just as a side-note. Why check so often? People can only notice a delay if its more that 100ms. So checking every 100ms or 0.1 seconds is more than adequate. Checking less often will lessen the CPU load.
    – Gerben
    Jan 12 '14 at 13:27
  • Busy looping (i.e., without a delay) is generally an atrocious way to code.
    – goldilocks
    Jan 12 '14 at 18:58
  • 1
    @goldilocks It generally is, but I take (my only) solace in that this meant to be a single-purpose device. @ Gerben, I will be inserting a one second delay in the final code, but I I was still curious about why this problem happened in the first place. Jan 12 '14 at 19:40
6

The reason is contact bounce - any mechanical switch will have contact bounce.

See the link for possible solutions https://raspberrypi.stackexchange.com/a/10338/8697

The code fragment you posted is very poor code. The Pi will devote most of its resources to a tight loop. You should explore interrupts or callbacks.

2
2

Because without the sleep call, you're in a tight loop and there's no chance for other threads to run. If you really need to poll like this (without callbacks) then you must wait a little bit (maybe 0.1 seconds makes more sense) to give the poor Pi chance to do what you're waiting for.

Imagine your boss wants you to finish some work, and he asks you every 0.001 seconds whether you've done it yet or not. Would you be able to get the work done? ;)

1
  • Having been in a similar but not so drastic situation, I can understand that. It's still odd that the behavior changes, but I can jokingly chalk that up to 'the laws of physics begin to break down'. Jan 13 '14 at 17:11

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.