Delaying events for fixed amounts of time.



I'm not sure if this is an appropriate topic, but it does possibly
involve multithreading. I have some requirements and I'm not sure what
the best solution is:

I have an application and part of it is receiving "events" in real
time, and must take a delayed action on those events by waiting a
fixed amount of time (say, 5 seconds) before processing the events.
Events may be arriving much closer together than the delay time, so I
need to asynchronously delay for each event.

Additionally, each event has a "key", and events with the same keys
must be grouped together. The delayed action must happen a fixed
amount of time after the *FIRST* event with a given key arrives. This
means I have to be able to keep track of what events I'm in the
progress of waiting on, I can't lose that information.

So basically the logic is:

onEvent (key, event) {
if no event with this key is pending:
begin new asynchronous delay for this event
else
add this event to the set of other events with same key
}

Then after the time period expires, the events with that key are all
processed. Event with key 42 arrives, delay time is 5 seconds, every
other event with that key arriving in the next 5 seconds is grouped
together, and after 5 seconds passes all of those events are
processed.

Timing accuracy is not critical, but I must respond to new events
within 250 ms of their arrival (so I can't impose a limit on the
number of pending unique keys). There are going to be a lot of events,
maybe on the order of 50-100 every second, with 15-30 unique keys per
second. It's part of a server application that's going to be doing a
decent amount of other work, so minimal system resource usage will be
critical, as well as scalability in the future.

I'm not sure what the best way to implement this is. I'm on Windows so
I have anything Windows has to offer. The options considered so far
are:

1) Create a new thread and a list of events each time a new key
arrives. If a key that already has a thread+list arrives, just add the
key to the list. The thread just sleeps for 5 seconds and then
processes all the events in the associated list. Appropriate
synchronization is done to avoid race conditions keeping track of key-
thread+list mappings. Disadvantage: Requires creation of a lot of
threads (is this bad?).

2) Store the current system time and create a list of events each time
a new key arrives. Start one thread that is continuously running in a
loop, checking the current system time against all of the stored
system times. Process events as timers expire. Use a manual reset
event to prevent thread from running in tight loops needlessly if no
events are pending. Pause for, say, 250ms each time through the loop
to reduce CPU load when running (250ms is good enough accuracy).
Disadvantage: Seems ugly, and complexity is linear with respect to
number of pending unique keys, although the number is small right now
(on the order of 10's or 100's).

3) Use Windows SetTimer, create a new timer + list of events when a
new key arrives. Same deal as #1, except process list when timer is
triggered. Disadvantage: SetTimer makes no guarantees about the max
number of timers that can be created, also requires a Windows message
processing loop, which is a big issue.

4) Use some other Windows timing service that I'm not aware of.
Disadvantage: I'm not aware of it.

5) Maybe there's some other Windows feature that helps, like APC or...
thread pools or something? Disadvantage: I've never used any of that
stuff before, and don't know much about it.

The major advantage of #1 is simplicity. #3, #4 and #5 can potentially
be even simpler to implement. The major advantage of #2 is it doesn't
require new threads per unique event. So I guess the question kind of
boils down to, is it better to create a ton of threads, or to take a
single threaded approach with a loop checking all of the times (or
some combination of the two and have multiple threads responsible for
subsets of all of the unique keys)? And the second question, then, is,
does Windows provide something well-suited to this task, or is there
some other technique that works well?


Thanks,
Jason
.



Relevant Pages

  • Re: Delaying events for fixed amounts of time.
    ... amount of time after the *FIRST* event with a given key arrives. ... I have anything Windows has to offer. ... Pause for, say, 250ms each time through the loop ... Have a queue of keys, each time a new key arrives, add it to the end ...
    (comp.programming.threads)
  • Re: Splash Screens , how could something so basic still be hard?
    ... You say that there "is no message pump to allow for further GUI ... Note that by "there is no message pump", I mean that because of the way the code is written, no message pump is working while the "splash screen" is displayed. ... In a normal Forms app, there would be a message pump loop, and there's no reason to believe that in those examples, one doesn't exist. ... The same technique is possible in Windows, ...
    (microsoft.public.dotnet.languages.csharp)
  • Re: Bug in win xp: Auto-detaching modeless dialog.
    ... Destroying the dialog is important whether there is a bug or not. ... >I don't think that windows API cares about design flaws. ... >> The whole loop with a sleep in it is a colossal blunder. ... My program does some time consuming calculations and from ...
    (microsoft.public.vc.mfc)
  • Re: threading question
    ... say I have a worker process processing in a loop ... Note that console apps very rarely show "Not Responding" because the Win32/64 console subsystem puts a layer between the application's input queue and the underlying windows message queue. ... A dotNet Console application become "native" console applications. ...
    (microsoft.public.dotnet.languages.csharp)
  • Re: How to block system copy commands at driver level
    ... about GUI level windows internals, but there are a number of tricks you ... Open Source&Dest/Read Source/Write Dest loop, and you're not going to be ... thats the reason our task is limited to restrict standerd copy/paste ... #3 + preventing someone opening the file in notepad, ...
    (microsoft.public.development.device.drivers)