|
|

Available Now

Search

Contact
Feedback:
Send an e-mail with your
comments about this program (or anything else).

Help support DFF
If you benefit from the website, in terms of
knowledge, entertainment value, or something otherwise useful,
consider making a donation via PayPal to help defray the
costs. (No PayPal account necessary to donate via credit
card.) Transaction is secure.


|
| |
Here is a program exploring Delphi's TThreads class as the mechanism
to run independent processes. In this case, I've implemented the rudiments
of an elevator simulator. TElevator is a TThreads descendant which visually
moves from floor to to floor, opening its doors at each stop.
This is the basis for an Elevator Simulation program currently being
developed. Several days trying to implement elevator controls using
queues and lists convinced me that perhaps I have finally found an application
suitable for thread processing.
Here are the tricks I've learned so far about using threads.
- Anything outside of it's own instance variables which is updated must be
synchronized. There is a Synchronize method to which schedules
such routines to run serially from the main VCL unit's
thread. In this case, there are three methods (MoveIt,
OpenDoorStep, CloseDoorStep) that change the elevator
display and therefore must run synchronized.
- The Execute method where all processing is performed is only called
one time. It is up to the programmer to not exit until
termination time. In this case, I nested a "While moving"
loop inside of a "While not terminated" loop.
When the elevator is stopped at a floor, moving flag is set to
false, the elevator is suspended and I sleep 1/10th of a second for
each iteration to minimized CPU usage while we're not doing
anything. When it's time to move again, the outside force
(button click) just sets Moving to true and calls the Resume
method for the elevator to start it up again.
- Calls to the Suspend method are counted and Resume calls
must match Suspend calls before the thread is actually resumed , so
it is important not to call Suspend redundantly.
- Whenever the number of floors or elevators changes, I free and recreate
all of the elevators. Gracefully terminating the elevator's thread
before destroying it was a little tricky. There is a
"Waitfor" method that waits for the thread to
actually terminate before continuing. So the logical
sequence of method calls to free an elevators seems like it should be "Terminate;
Waitfor; Free;" If the elevator happens to
be stopped (Suspended) when that sequence is executed, the call to Waitfor
never returns. The version that seem to work is : Terminate;
If not suspended then waitfor; free;
The rest of the code is not trivial, but not too complex either. I made
an array of buttons to move the elevators one floor per push. Only
the buttons corresponding to the current number of elevators are made
visible. The TImage, Image1, is used only to provide a
convenient way to define the field for floors and elevators. It
remains invisible in order to speed up the drawing the other
elements. A timer is used to periodically check how long each
elevators doors have been open to close them when the specified "Door
open" time has passed.
I've learned quite a bit in the process of coding this. Perhaps
you will too!
Download source
Download executable
| Created: November 07, 2008 |
Modified: November 07, 2008
|
|