Таким образом, у меня есть параллель для цикла for, который отлично работает сам по себе, в основном он перебирает коллекцию элементов 32000 и выполняет некоторый анализ и математические операции, а что нет, и выводит ожидаемый результат.
Требуется достаточно много времени, чтобы деформировать строку загрузки, поэтому я создал новую форму и инициализировал ее перед вызовом этого метода, а затем просто добавляю 1 к индикатору выполнения после завершения каждого цикла, который прекрасно работает, обновляется и все. Затем, после завершения цикла, его означает загрузить следующую форму для отображения данных, и все в порядке.
Теперь странная проблема заключается в том, что этот метод всегда будет работать идеально, когда я удаляю одну строку для обновления индикатора выполнения (ближе к концу кода), но когда я оставляю его, иногда он будет работать так, как я хочу и иногда он выполняет всю обработку и обновляет индикатор выполнения как обычно, а затем доходит до конца и просто останавливается, он фактически не выходит из цикла и не продолжает код (я могу сказать, потому что Debug.WriteLine просто ниже это не вызвано, когда это застревает). И я знаю, что программа ничего не делает, потому что процессор работает на холостом ходу (где он равен 100%, когда работает цикл), и я не могу понять, что не так.
Вот код, который у меня есть:
public void ProcessData()
{
try
{
Globals.frmref.pgbProgress.Value = 0;
string TimeZone = cmbTimeZone.Text;
Globals.frmref.pgbProgress.Maximum = Globals.FileLength - 8;
Parallel.For(0, Globals.FileLength - 9, i =>
{
Globals.data[i].TimeTemp = "{0}/{1}/20{2} {3}:{4}:{5}";
//Process the time and date (received in utc as ddmmyy and HHmmss.fff) to dd/mm/yy HH:mm:ss.fff
Globals.data[i].TimeTemp = String.Format(Globals.data[i].TimeTemp, Globals.data[i].DateRAW.Substring(0, 2), Globals.data[i].DateRAW.Substring(2, 2), Globals.data[i].DateRAW.Substring(4, 2), Globals.data[i].Hours, Globals.data[i].Minutes, Globals.data[i].Seconds);
Globals.data[i].Time = DateTime.Parse(Globals.data[i].TimeTemp.Split('.')[0], CultureInfo.CreateSpecificCulture("en-AU"));
Globals.data[i].Time = Globals.data[i].Time.AddMilliseconds(Double.Parse(Globals.data[i].TimeTemp.Split('.')[1]));
if (TimeZone.Contains("-"))
{
Globals.data[i].Time = Globals.data[i].Time - TimeSpan.Parse(TimeZone.Substring(1, TimeZone.Length - 1));
}
else
{
Globals.data[i].Time = Globals.data[i].Time + TimeSpan.Parse(TimeZone.Substring(1, TimeZone.Length - 1));
}
//Process the lat and lon input to Decimal Degrees
Globals.data[i].DDLat = Globals.data[i].LatDegrees + (Globals.data[i].LatMinutes / 60) + (Globals.data[i].LatSeconds / 3600);
Globals.data[i].DDLon = Globals.data[i].LonDegrees + (Globals.data[i].LonMinutes / 60) + (Globals.data[i].LonSeconds / 3600);
if (Globals.data[i].NS == 'S') //North/South designator
{
//Make the dd coord negative if its southern
Globals.data[i].DDLat = Globals.data[i].DDLat * -1;
}
if (Globals.data[i].EW == 'W') //East/West Designator
{
//ditto
Globals.data[i].DDLon = Globals.data[i].DDLon * -1;
}
//***This is the line breaks it sometimes***
Globals.frmref.pgbProgress.Invoke(new Action(() => Globals.frmref.pgbProgress.Value++));
});
Debug.WriteLine("Made it");
Globals.frmref.Close();
}
catch (Exception ex)
{
MessageBox.Show("An unexpected error has occurred, email wmatt1672@gmail.com with details of the error.", "Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
MessageBox.Show(ex.ToString(), "Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
Application.Exit();
}
}
Я пытался заблокировать элемент управления ProgressBar перед его обновлением, используя int для сохранения значения, а затем обновляя индикатор выполнения с помощью другого метода, и используя Task.Factory (который странно выполняет код). У меня нет идей.
tldr: Параллельный цикл for иногда не завершается после его завершения, только когда я добавляю одну строку кода для добавления 1 в индикатор выполнения.