在反应式流上发布时出现IndexOutOfRangeException

时间:2018-12-10 14:59:09

标签: c# multithreading concurrency reactive-programming system.reactive

我正在开发一个使用可连接的可观察对象发布结果的应用程序。 这些结果由两个观察者在两个不同的线程上使用;一个可观察的运行在UI线程上,并将结果显示在表和图表中,而另一个可观察的运行在默认线程池上将结果发送到REST端点。

但是,在某些情况下,可变时间后会抛出IndexOutOfRangeException。 我怀疑这是因为我的线程将结果发送到REST Web服务的并发问题。 如果我不启动该线程,则结果显示就很好。 此外,发生的不规则性是并发问题的典型特征。 我附加了异常的堆栈跟踪。

at System.Collections.Generic.List`1.Add(T item)
at System.Reactive.Linq.ObservableImpl.Buffer`1.CountExact.ExactSink.OnNext(TSource value)
at System.Reactive.Subjects.Subject`1.OnNext(T value)
at System.Reactive.Sink`1.ForwardOnNext(TTarget value)
at System.Reactive.IdentitySink`1.OnNext(T value)
at System.Reactive.AutoDetachObserver`1.OnNextCore(T value)
at System.Reactive.ObserverBase`1.OnNext(T value)
at Wetr.Simulator.viewModel.SimulationViewModel.OnSimulationResultPublished(SimulationResult measurement) in E:\programming\csharp\Weatr\Wetr.Simulator\Wetr.Simulator\viewModel\SimulationViewModel.cs:Line 96.

发布结果的代码如下所示。

private void OnSimulationResultPublished(SimulationResult measurement)
{
    this.aggregatedSimulationResultObserver?.OnNext(measurement);
}

度量编写器使用以下代码来订阅事件。

this.measurementStreamSubscription = measurementStream
    .Buffer(BUFFER_SIZE)
    .Subscribe(
        results => this.writer.AddMeasurementsAsync(
            results
                .Where(container => container != null)
                .Select(container => container.Result)
        )
    );

UI更新由以下所示的订阅处理。

this.uiUpdateSubscription =
    this.AggregatedSimulationResults
        //.Select(result => new SimulationResult(
        //    result.Station, result.MeasurementSequenceID,
        //    new Measurement(
        //        result.Result.Station,
        //        result.Result.MeasurementType,
        //        new DateTime(result.Result.Timestamp.Ticks),
        //        result.Result.MeasuredValue
        //    )
        //))
        .ObserveOn(DispatcherScheduler.Current)
        .Subscribe(this.DisplayNewSimulationResults);

我已经阅读了Intro to RX,但是我对Reactive Extensions还是很陌生。 我还尝试过在缓冲之前创建测量的新副本,但这并不能解决问题。 因此,感谢您的帮助。

0 个答案:

没有答案