Как сделать массив истории из диспетчерского таймера? С#

По сути, мне нужно создать таймер Dispatcher, сохранить переменную в массиве по мере ее подсчета, а затем отобразить массив истории в текстовом поле, когда я нажимаю кнопку rawDataButton. По какой-то причине мой массив показывает только самые последние и никогда не сохраняется в массиве, вот мой код

DispatcherTimer timer = new DispatcherTimer();
MeasureLengthDevice dg = new MeasureLengthDevice();
int mostRecnet = 0;
int[] arr = new int[10];

private void StartCollectingDataButton_Click(object sender, RoutedEventArgs e)
{
    timer.Interval = new TimeSpan(0, 0, 1);
    timer.Start();
    timer.Tick += timer_Tick;
}
private void timer_Tick(object sender, object e)
{
    mostRecnet = dg.GetMeasurement();
    recentDataTextBlock.Text = mostRecnet.ToString();
    for(int i = 0; i < arr.Length; i++)
    {
        arr[i] = mostRecnet;
    }
}
private void stopCollectingDataButton_Click(object sender, RoutedEventArgs e)
{
    timer.Stop();
}

private void rawDataButton_Click(object sender, RoutedEventArgs e)
{
    for (int i = 0; i < arr.Length; i++)
    {
        mostRecnet = arr[i];
        rawDataTextBox.Text += arr[i].ToString() + "\n";
    }
}

person CapitalistNick    schedule 26.10.2019    source источник
comment
Похоже, вы используете одно измерение для заполнения всех элементов массива.   -  person ChiefTwoPencils    schedule 26.10.2019
comment
Вероятно, вы хотели иметь List<int>, а не массив. Нет необходимости вручную организовывать массив.   -  person Christopher    schedule 27.10.2019
comment
Конечно, с таймером Dispatcher Concurrency может быть проблемой. И параллельного списка не существует. Конечно, поскольку вам нужно будет только прочитать список после этого, это может не быть большой проблемой.   -  person Christopher    schedule 27.10.2019
comment
@ChiefTwoPencils да, я тоже заметил это после отладки, но я пытаюсь сохранить наиболее недавние внутри массива по мере его поступления.   -  person CapitalistNick    schedule 27.10.2019
comment
Как сказал другой, список был бы лучше.   -  person ChiefTwoPencils    schedule 27.10.2019
comment
Да, List работает намного лучше, спасибо, но если бы я хотел сделать то же самое с массивом, как бы вы могли это сделать, теперь мне любопытно, и я хочу научиться. Спасибо всем еще раз   -  person CapitalistNick    schedule 27.10.2019
comment
Обратите внимание: вы прикрепляете обработчик Tick каждый раз, когда нажимаете кнопку запуска, но никогда не удаляете его позже. Таким образом, с каждым щелчком вы увеличиваете количество вызовов обработчика. Переместите timer.Tick += timer_Tick; из обработчика Click в конструктор или метод инициализации. И конечно же, параллелизм с DispatcherTimer вообще не проблема, потому что весь ваш код выполняется в потоке пользовательского интерфейса. Вы можете смело игнорировать этот комментарий и ответ.   -  person Clemens    schedule 27.10.2019


Ответы (1)


Вы можете заменить

int mostRecnet = 0;
int[] arr = new int[10];

И необходимость вручную считать со списком и некоторым базовым кодом мьютекса:

//Always use a dedicated object to lock onto
private object mutex = new object();
var History = new List<int>();

В галочке делаешь так:

lock(mutex){
  History.Add(mostRecent);
}

И когда вы его читаете, вы делаете это:

lock(mutex){
  //do whatever you need to output the list contents
}

Имейте в виду, что блокировка вывода предотвратит обработку события тика. И особенно массовая запись в пользовательский интерфейс может занять значительное время, легко в пределах от 10 до 100 миллисекунд.

person Christopher    schedule 26.10.2019
comment
Использование lock с DispatcherTimer — ужасная чепуха. Обработчик Tick уже работает в потоке пользовательского интерфейса, и проблемы параллелизма вообще нет. - person Clemens; 30.10.2019