Paul is right when he says this is a bad idea. You are logically creating a situation where the queued up actions could blow system resources. You could even find it works on your computer, but fails on a customer's computer. The available memory, 32-/64-bit processor, etc, could all affect the code.
However, it's easy to modify you code to make it do what you want.
First up though, the Timer
method will correctly schedule timer events as long as the observer finishes before the next scheduled event. If the observer hasn't finished then the timer will wait. Remember that observable timers are "cold" observables, so for every subscribed observer there is effectively a new timer observable. It's a one-to-one relationship.
This behaviour prevents the timer from inadvertently blowing your resources.
So, as you code is currently defined, OnNext
is being called every 1000 milliseconds, not every 100.
Now, to allow the code to run at the 100 millisecond schedule, do this:
Observable
.Timer(TimeSpan.Zero, TimeSpan.FromMilliseconds(100))
.Select(x => Scheduler.NewThread.Schedule(() =>
{
count++;
Thread.Sleep(TimeSpan.FromMilliseconds(1000));
}))
.Subscribe(x => { });
Effectively this code is an IObservable<IDisposable>
where each disposable is the scheduled action that takes 1000 milliseconds to complete.
In my tests this ran nicely and incremented the count correctly.
I did try to blow my resources and found that setting the timer to run once every millisecond I quickly got a System.OutOfMemoryException
, but I found that the code ran if I changed the setting to every two milliseconds. This did, however, use up over 500 MB of RAM while the code ran and created around 500 new threads. Not nice at all.
Proceed with caution!