Re: Lahman, how ya doing?
- From: glhansen@xxxxxxxxxxxxxxxxxxxxx (Gregory L. Hansen)
- Date: Sat, 14 May 2005 01:45:23 +0000 (UTC)
In article <tDCee.18502$yd1.17138@trndny01>,
H. S. Lahman <hsl@xxxxxxxxxxxxxxxxx> wrote:
>Responding to Hansen...
Backing up a little, I want to return to some technical details.
>>>>>class EventElement
>>>>>{
>>>>>private:
>>>>> Object* recipient;
>>>>> int event_id;
>>>>> int tick_count;
>>>>>public:
>>>>> EventElement (Object* r, int e, int t)
>>>>> {recipient = r; event_id = e; tick_count = t;};
>>>>> int getTickCount() {return tick_count;};
>>>>>}
>>>>>
>>>>>class Timer
>>>>>{
>>>>>private:
>>>>> EventQueue* queueManager;
>>>>> EventElement eventList[MAX_EVENT_COUNT];
>>>>> int tick_count;
>>>>> int next_event;
>>>>>public:
>>>>> Timer (EvetnQueue* e)
>>>>> {queueManager = e; next_event = 0; tick_count = 0;};
>>>>> void add_event (Object* o, int e, int t);
>>>>> void tick()
>>>>> void reset() {tick_count = 0;};
>>>>>}
>>>>>
>>>>>void Timer::add_event (Object* o, int e, int t)
>>>>>{
>>>>> EventElement event = new [] (o, e, t);
>>>>> eventList[next_event] = event;
>>>>> next_event++;
>>>>> if (next_event == MAX_EVENT_COUNT)
>>>>> // signal exception.
>>>>>};
>>>>>
>>>>>void Timer::tick()
>>>>>{
>>>>> tick_count++;
>>>>> for (int i = 0; i < next_event; i++)
>>>>> {
>>>>> int eventTickCount = eventList[i].getTickCount();
>>>>> if ((tick_count MOD eventTickCount) == 0)
>>>>> queueManager->push(&eventList[i]);
>>>>> }
>>>>>}
Here in Timer::tick() you're pushing pointers on to the queue from a pool
of events held by Timer. Not relevant to my simulation, but generalizing
to a case where any amount of time can pass between when an event is
pushed on to the queue and when it is popped off and processed, it seems
you can have two identical events going to the same object. I guess that
still doesn't matter the way you've set it up, but if I'm passing data
with an event (and you've opined on that practice!) I can imagine the
content of the first being modified by preparing the second. So I'd want
to make a copy for the queue, and destroy the copy at the end. Fire and
forget, but somewhat different queue behavior, and all events must be
processed that way if any of them are.
And if I don't pass data in the event, but data still needs to be passed,
I don't know how to pass it. Using Timer as a specific example of the
more generic question, it *could* be given an accessor function
get_time(), a receiving object *could* get the time directly through that.
But if it's to process event1 using time1 and then event2 using time2, and
Timer has time3 by the time event1 hits the object and time4 by the time
event2 hits it, I can't think of an easy alternative other than to stuff
the data you need into the event so that it's all there.
>>>>MODing it is an interesting approach that I hadn't thought of. And that
>>>>makes more sense of some of the other things you'd said-- I imagined
>>>>filling the event queue with 2 million events before the simulation even
>>>>began!
>>>
>>>Presumably Timer.tick() is invoked when all the processing for the
>>>current simulation tick is completed. (The easy way to do that is for
>>>the event queue manager to invoke tick() when it is empty since tick()
>>>will fill it up with the events for the current tick and those all have
>>>to be processed.)
>>
>>
>> In my non-multitasking system, where would control pass to a queue manager
>> that would pop events and distribute them?
>
>Once the application is initialized (presumably in main() or equivalent
>for the language) a "seed" event is put on the queue and the Queue is
>started. It pops events until the queue is empty, in which case the
>application is done. Note that the state machine actions put events on
>the queue and the pop is not complete until the action completes, so the
>queue will not empty out until all the processing is completed.
So what happens if the queue empties before...
>
>Things are more complicated in a truly asynchronous system where the
>queue may have to wait for an external event. (Or for events generated
>by a real- or scaled-time timer.) But then the push just needs to
>restart the queue operation if the event count is exactly 1 after the
>push. Since you are using simulation ticks rather than scaling, this
Oh, okay. I suppose somewhere in the bowels of the queue it will be
looping until it finds a quit event directed to queue?
>doesn't matter because you just just need an event to Timer to trigger
>tick() when all the tick's processing is completed. In your case there
>are a couple of easy options: (1) have Timer put a self-directed event
>on the queue as the last event or (2) have the event queue manager call
>tick() when it is empty. (Tick() can generate an event for a graceful
>exit if, say, the maximum simulation ticks have executed to provide an
>exit.)
Hey, I just told you about (1)! Some of what you've been telling me is
starting to make more sense in retrospect.
--
"Very well, he replied, I allow you cow's dung in place of human
excrement; bake your bread on that." -- Ezekiel 4:15
.
- Follow-Ups:
- Re: Lahman, how ya doing?
- From: H. S. Lahman
- Re: Lahman, how ya doing?
- References:
- Re: Lahman, how ya doing?
- From: H. S. Lahman
- Re: Lahman, how ya doing?
- From: Gregory L. Hansen
- Re: Lahman, how ya doing?
- From: H. S. Lahman
- Re: Lahman, how ya doing?
- Prev by Date: Interdependencies
- Next by Date: Re: Lahman, how ya doing?
- Previous by thread: Re: Lahman, how ya doing?
- Next by thread: Re: Lahman, how ya doing?
- Index(es):
Relevant Pages
|