private async Task AnalyzeData(double Temperature, double Cph, double Cdo, double Cbod5, double Ccod, double Cnh4n, double Cno2n, double Cno3n, double Css, double Ccl, double Ccb)
        {
            Console.WriteLine("----------------------------------------------------------");
            var Is = AnalysisEngine.CalculateSimpleIndices(Temperature, Cph, Cdo, Cbod5, Ccod, Cnh4n, Cno2n, Cno3n, Css, Ccl, Ccb);

            Console.WriteLine(Is.ToJSONString());
            var Ws = AnalysisEngine.GetWeightCoefficients(Temperature, Is);

            Console.WriteLine(Ws.ToJSONString());
            OverallIndex = AnalysisEngine.CalculateOverallIndex(Is, Ws);
            Console.WriteLine("Overall Index: " + OverallIndex.ToString("F5"));
            Level = AnalysisEngine.GetLevel(Temperature, OverallIndex);
            Console.WriteLine("Level: " + Level.ToString("D"));
        }
        private async Task TestEngine()
        {
            // January
            Console.WriteLine("----------------------January----------------------");
            double Temperature = 10.0, PH = 7.1, DO = 13.86, BOD5 = 3.42, COD = 2.68, NH4N = 0.27, NO2N = 0.03, NO3N = 6.7, SS = 24.67, CL = 15.33, CB = 235;
            var    Is = AnalysisEngine.CalculateSimpleIndices(Temperature, PH, DO, BOD5, COD, NH4N, NO2N, NO3N, SS, CL, CB);

            Console.WriteLine(Is.ToJSONString());
            var Ws = AnalysisEngine.GetWeightCoefficients(Temperature, Is);

            Console.WriteLine(Ws.ToJSONString());
            var OverallIndex = AnalysisEngine.CalculateOverallIndex(Is, Ws);

            Console.WriteLine("Overall Index: " + OverallIndex.ToString("F5"));
            var Level = AnalysisEngine.GetLevel(Temperature, OverallIndex);

            Console.WriteLine("Level: " + Level.ToString("D"));

            // May
            Console.WriteLine("----------------------May----------------------");
            Temperature = 20.0; PH = 7.27; DO = 9.95; BOD5 = 2.41; COD = 2.18; NH4N = 0.35; NO2N = 0.02; NO3N = 07.9; SS = 21.33; CL = 24.67; CB = 796.67;
            Is          = AnalysisEngine.CalculateSimpleIndices(Temperature, PH, DO, BOD5, COD, NH4N, NO2N, NO3N, SS, CL, CB);
            Console.WriteLine(Is.ToJSONString());
            Ws = AnalysisEngine.GetWeightCoefficients(Temperature, Is);
            Console.WriteLine(Ws.ToJSONString());
            OverallIndex = AnalysisEngine.CalculateOverallIndex(Is, Ws);
            Console.WriteLine("Overall Index: " + OverallIndex.ToString("F5"));
            Level = AnalysisEngine.GetLevel(Temperature, OverallIndex);
            Console.WriteLine("Level: " + Level.ToString("D"));

            // July
            Console.WriteLine("----------------------July----------------------");
            Temperature = 30.0; PH = 7.23; DO = 8.69; BOD5 = 2.37; COD = 2.4; NH4N = 0.28; NO2N = 0.04; NO3N = 9; SS = 27.33; CL = 23.33; CB = 773.33;
            Is          = AnalysisEngine.CalculateSimpleIndices(Temperature, PH, DO, BOD5, COD, NH4N, NO2N, NO3N, SS, CL, CB);
            Console.WriteLine(Is.ToJSONString());
            Ws = AnalysisEngine.GetWeightCoefficients(Temperature, Is);
            Console.WriteLine(Ws.ToJSONString());
            OverallIndex = AnalysisEngine.CalculateOverallIndex(Is, Ws);
            Console.WriteLine("Overall Index: " + OverallIndex.ToString("F5"));
            Level = AnalysisEngine.GetLevel(Temperature, OverallIndex);
            Console.WriteLine("Level: " + Level.ToString("D"));
        }
        private void ViewMethodComboBox_SelectionChanged(object sender, SelectionChangedEventArgs e)
        {
            var SelectedItem = ViewMethodComboBox.SelectedItem as ViewMethodViewModel;

            if (SelectedItem == null)
            {
                return;
            }

            if (SelectedItem.Id == 0)
            {
                // Daily view, switched from Monthly view
                // Use backup records
                var viewModel = (RecordManagerViewModel)DataContext;

                var records = viewModel.BackupRecords;
                viewModel.Records = new ObservableCollection <RecordViewModel>(records);

                DeleteButton.Visibility = Visibility.Visible;
            }
            else
            {
                // Monthly view
                // Hide the analysis panel
                AnalyzerPanel.Visibility = Visibility.Collapsed;

                // Process current data to switch view
                var viewModel = (RecordManagerViewModel)DataContext;
                var records   = viewModel.BackupRecords;

                // Group records, based on months
                var groupedData = new Dictionary <string, System.Collections.Generic.List <RecordViewModel> >();
                foreach (var record in records)
                {
                    var dateTime  = DateTime.Parse(record.DateTime);
                    var monthTime = dateTime.ToString("yyyy-MM");
                    var newKey    = record.ReservoirId.ToString() + "/" + monthTime;
                    if (groupedData.ContainsKey(newKey))
                    {
                        // Existing
                        // Add the record
                        var data = groupedData[newKey];
                        data.Add(record);
                        groupedData[newKey] = data;
                    }
                    else
                    {
                        // New
                        var data = new List <RecordViewModel>();
                        data.Add(record);
                        groupedData[newKey] = data;
                    }
                }

                // Process grouped data
                var processedData = new ObservableCollection <RecordViewModel>();
                var keys          = groupedData.Keys;
                foreach (var key in keys)
                {
                    var monthData = groupedData[key];
                    if (monthData.Count == 1)
                    {
                        // Only single record for a month
                        // Add it directly. Just change DateTime.
                        // No need to do the analysis again
                        var keyParts    = key.Split('/');
                        var monthRecord = new RecordViewModel
                        {
                            DateTime         = keyParts[1],
                            Id               = -1,
                            ReservoirId      = monthData[0].ReservoirId,
                            ReservoirName    = monthData[0].ReservoirName,
                            Temperature      = monthData[0].Temperature,
                            TemperatureRange = monthData[0].TemperatureRange,
                            PH               = monthData[0].PH,
                            DO               = monthData[0].DO,
                            BOD5             = monthData[0].BOD5,
                            COD              = monthData[0].COD,
                            NH4N             = monthData[0].NH4N,
                            NO2N             = monthData[0].NO2N,
                            NO3N             = monthData[0].NO3N,
                            SS               = monthData[0].SS,
                            CL               = monthData[0].CL,
                            CB               = monthData[0].CB,
                            Overall          = monthData[0].Overall,
                            Level            = monthData[0].Level,
                        };
                        processedData.Add(monthRecord);
                    }
                    else
                    {
                        var    keyParts      = key.Split('/');
                        string DateTime      = keyParts[1];
                        int    ReservoirId   = monthData[0].ReservoirId;
                        string ReservoirName = monthData[0].ReservoirName;
                        double Temperature   = monthData[0].Temperature;
                        double PH            = double.Parse(monthData[0].PH);
                        double DO            = double.Parse(monthData[0].DO);
                        double BOD5          = double.Parse(monthData[0].BOD5);
                        double COD           = double.Parse(monthData[0].COD);
                        double NH4N          = double.Parse(monthData[0].NH4N);
                        double NO2N          = double.Parse(monthData[0].NO2N);
                        double NO3N          = double.Parse(monthData[0].NO3N);
                        double SS            = double.Parse(monthData[0].SS);
                        double CL            = double.Parse(monthData[0].CL);
                        double CB            = double.Parse(monthData[0].CB);

                        for (int i = 1; i < monthData.Count; i++)
                        {
                            if (monthData[i].Temperature == Temperature)
                            {
                                // Records in the same month should have the same temperature range.
                                PH   += double.Parse(monthData[i].PH);
                                DO   += double.Parse(monthData[i].DO);
                                BOD5 += double.Parse(monthData[i].BOD5);
                                COD  += double.Parse(monthData[i].COD);
                                NH4N += double.Parse(monthData[i].NH4N);
                                NO2N += double.Parse(monthData[i].NO2N);
                                NO3N += double.Parse(monthData[i].NO3N);
                                SS   += double.Parse(monthData[i].SS);
                                CL   += double.Parse(monthData[i].CL);
                                CB   += double.Parse(monthData[i].CB);
                            }
                            else
                            {
                                // Temperature range is different.
                                // Can't analyze the data.
                                viewModel.ShowMessageCommand.Execute("There must be some error in the data. Please inspect it and try again.");
                                return;
                            }
                        }

                        PH   = PH / monthData.Count;
                        DO   = DO / monthData.Count;
                        BOD5 = BOD5 / monthData.Count;
                        COD  = COD / monthData.Count;
                        NH4N = NH4N / monthData.Count;
                        NO2N = NO2N / monthData.Count;
                        NO3N = NO3N / monthData.Count;
                        SS   = SS / monthData.Count;
                        CL   = CL / monthData.Count;
                        CB   = CB / monthData.Count;

                        var    Is           = AnalysisEngine.CalculateSimpleIndices(Temperature, PH, DO, BOD5, COD, NH4N, NO2N, NO3N, SS, CL, CB);
                        var    Ws           = AnalysisEngine.GetWeightCoefficients(Temperature, Is);
                        double OverallIndex = AnalysisEngine.CalculateOverallIndex(Is, Ws);
                        int    Level        = AnalysisEngine.GetLevel(Temperature, OverallIndex);

                        var monthRecord = new RecordExtended
                        {
                            Id            = -1,
                            Temperature   = Temperature,
                            PH            = PH,
                            DO            = DO,
                            BOD5          = BOD5,
                            COD           = COD,
                            NH4N          = NH4N,
                            NO2N          = NO2N,
                            NO3N          = NO3N,
                            SS            = SS,
                            CL            = CL,
                            CB            = CB,
                            Overall       = OverallIndex,
                            Level         = Level,
                            ReservoirId   = ReservoirId,
                            ReservoirName = ReservoirName,
                            DateTime      = DateTime
                        };
                        processedData.Add(new RecordViewModel(monthRecord));
                    }
                }

                viewModel.Records = processedData;

                DeleteButton.Visibility = Visibility.Collapsed;
            }
        }