Projekt

Obecné

Profil

Stáhnout (9.18 KB) Statistiky
| Větev: | Tag: | Revize:
1 734533a8 A-Konig
using ServerApp.Parser.InputData;
2
using ServerApp.Parser.OutputInfo;
3 0da0ac88 A-Konig
using System;
4 5d9a5bd9 A-Konig
using System.Collections.Generic;
5 0da0ac88 A-Konig
using System.IO;
6 5d9a5bd9 A-Konig
7 734533a8 A-Konig
namespace ServerApp.Parser.Parsers
8 5d9a5bd9 A-Konig
{
9 734533a8 A-Konig
    /// <summary>
10
    /// Class parsing weather files into instances of WeatherInfo divided by given time interval
11
    /// Data parsed from 7am (included) to 18pm (included)
12
    /// </summary>
13 98b568bc A-Konig
    /// <author>Alex Konig</author>
14 5d9a5bd9 A-Konig
    class WeatherParser
15
    {
16 98b568bc A-Konig
17
        /// <summary> Datafile loader  </summary>
18
        DataLoader loader;
19
20
        /// <summary>
21
        /// Constructor
22
        /// </summary>
23
        /// <param name="loader">Datafile loader</param>
24
        public WeatherParser(DataLoader loader)
25
        {
26
            this.loader = loader;
27
        }
28
29 734533a8 A-Konig
        /// <summary>
30
        /// Parses weather data to WeatherInfo instances
31
        /// Data parsed from 7am (included) to 18pm (included)
32
        /// </summary>
33
        /// <param name="folder">Folder with weather data files</param>
34
        /// <param name="wholeDay">Should data be parsed as one instance per day (if true parameter interval will be ignored)</param>
35
        /// <param name="interval">Time interval to divide days by, minimum is 1h</param>
36
        /// <returns></returns>
37 0da0ac88 A-Konig
        public List<WeatherInfo> ParseWeatherData(string folder, bool wholeDay = true, int interval = 1)
38
        {
39
            if (!Directory.Exists(folder))
40
                return null;
41
42 734533a8 A-Konig
            List<WeatherInfo> list = new List<WeatherInfo>();
43
44
            // get all files in folder
45 0da0ac88 A-Konig
            string[] fileEntries = Directory.GetFiles(folder);
46
            foreach (string fileName in fileEntries)
47
            {
48
                List<WeatherInfo> loadedData = null;
49 734533a8 A-Konig
                
50
                // parse as one instance per day
51 0da0ac88 A-Konig
                if (wholeDay)
52
                    loadedData = ProcessOneWeatherFileAsDays(fileName);
53 734533a8 A-Konig
                // parse according to interval
54 0da0ac88 A-Konig
                else
55
                {
56 98b568bc A-Konig
                    loadedData = ProcessOneWeatherFileAsIntervals(fileName, interval);
57 0da0ac88 A-Konig
                }
58
59
                list.AddRange(loadedData);
60
            }
61
62
            return list;
63
        }
64
65 734533a8 A-Konig
        /// <summary>
66
        /// Parses data from one data file as one instance per day
67
        /// </summary>
68
        /// <param name="path">Path ti file</param>
69
        /// <returns>List with WeatherInfo instances</returns>
70 98b568bc A-Konig
        private List<WeatherInfo> ProcessOneWeatherFileAsDays(string path)
71 0da0ac88 A-Konig
        {
72 734533a8 A-Konig
            if (!File.Exists(path))
73
                return null;
74 0da0ac88 A-Konig
75 734533a8 A-Konig
            List<WeatherInfo> weatherInfo = new List<WeatherInfo>();
76 98b568bc A-Konig
            List<WeatherInstance> list = loader.LoadWeatherFile(path);
77 0da0ac88 A-Konig
78 734533a8 A-Konig
            // array with data [temp, rain, wind, lum]
79 0da0ac88 A-Konig
            double[] recordedAmount = new double[4];
80 734533a8 A-Konig
            // min/max hour taken into account
81 0da0ac88 A-Konig
            int[] minmaxHour = new int[] { 7, 18 };
82 734533a8 A-Konig
            // interval length
83 0da0ac88 A-Konig
            int range = minmaxHour[1] - minmaxHour[0];
84
85 734533a8 A-Konig
            // first day
86
            DateTime lastStartDay = new DateTime(list[0].dateTime.Year, list[0].dateTime.Month, list[0].dateTime.Day, minmaxHour[0], 0, 0);
87
            // number of values in day
88 98b568bc A-Konig
            int values = 0, weatherValues = 0;
89 0da0ac88 A-Konig
            for (int i = 0; i < list.Count; i++)
90
            {
91
                int currHour = list[i].dateTime.Hour;
92
                if (currHour < minmaxHour[0] || currHour > minmaxHour[1])
93
                    continue;
94
95 734533a8 A-Konig
                // start of new day -> make a new instance
96
                DateTime date = new DateTime(list[i].dateTime.Year, list[i].dateTime.Month, list[i].dateTime.Day, minmaxHour[0], 0, 0);
97 0da0ac88 A-Konig
                if (!date.Equals(lastStartDay))
98
                {
99 98b568bc A-Konig
                    WeatherInfo dayInfo = new WeatherInfo(lastStartDay, recordedAmount[0] / values, (int)(recordedAmount[1] / values * 100), recordedAmount[2] / values, recordedAmount[3] / weatherValues, range); 
100 0da0ac88 A-Konig
                    weatherInfo.Add(dayInfo);
101
102
                    recordedAmount = new double[4];
103
                    lastStartDay = date;
104
                    values = 0;
105 98b568bc A-Konig
                    weatherValues = 0;
106 0da0ac88 A-Konig
                }
107
108 734533a8 A-Konig
                // aggregate data
109 0da0ac88 A-Konig
                recordedAmount[0] += list[i].temp;
110
                recordedAmount[1] += list[i].rain;
111
                recordedAmount[2] += list[i].wind;
112 98b568bc A-Konig
113
                if (LuxToConditions.TransferLuxToConditions(list[i].lum * 1000) != WeatherConditions.Dark)
114
                    recordedAmount[3] += list[i].lum * 1000; weatherValues++;
115 734533a8 A-Konig
116 0da0ac88 A-Konig
                values++;
117
            }
118
119 734533a8 A-Konig
            // data from last day
120 0da0ac88 A-Konig
            WeatherInfo dayInfo2 = new WeatherInfo(lastStartDay, recordedAmount[0] / values, (int)(recordedAmount[1] / values * 100), recordedAmount[2] / values, recordedAmount[3] / values, range); 
121
            weatherInfo.Add(dayInfo2);
122
123
            return weatherInfo;
124
        }
125
126 98b568bc A-Konig
        /// <summary>
127
        /// Parses data from one data file as one instance per interval length
128
        /// </summary>
129
        /// <param name="path">Path to file</param>
130
        /// <param name="interval">Interval length</param>
131
        /// <returns>List with ActivityInfo instances</returns>
132
        private List<WeatherInfo> ProcessOneWeatherFileAsIntervals(string path, int interval)
133 0da0ac88 A-Konig
        {
134 98b568bc A-Konig
            if (!File.Exists(path))
135
                return null;
136
137
            List<WeatherInfo> loignInfo = new List<WeatherInfo>();
138
            List<WeatherInstance> list = loader.LoadWeatherFile(path);
139
140
            // min/max hour taken into account
141
            int[] minmaxHour = new int[] { 7, 18 };
142
            int range = minmaxHour[1] - minmaxHour[0];
143
144
            if (interval > range)
145
                return null;
146
147
            int indices = (int)Math.Ceiling(range / (double)interval);
148
            int[] to = new int[indices];
149
            double[][] data = new double[indices][];
150
            int[] count = new int[indices];
151
            for (int i = 0; i < to.Length; i++)
152
            {
153
                to[i] = minmaxHour[0] + interval * (i + 1);
154
                data[i] = new double[4];
155
            }
156
157
            // first day
158
            DateTime lastStartTime = new DateTime(list[0].dateTime.Year, list[0].dateTime.Month, list[0].dateTime.Day, minmaxHour[0], 0, 0);
159
            int index;
160
            for (int i = 0; i < list.Count; i++)
161
            {
162
                int currHour = list[i].dateTime.Hour;
163
                if (currHour < minmaxHour[0] || currHour > minmaxHour[1])
164
                    continue;
165
166
                // start of the day -> make an instance
167
                DateTime date = new DateTime(list[i].dateTime.Year, list[i].dateTime.Month, list[i].dateTime.Day, list[i].dateTime.Hour, 0, 0);
168
169
                // end of the day
170
                if (!(date.Year == lastStartTime.Year && date.Month == lastStartTime.Month && date.Day == lastStartTime.Day))
171
                {
172
                    // note down all aggregated data
173
                    for (int k = 0; k < to.Length; k++)
174
                    {
175
                        int raincount = 0;
176
                        double rainval = 0;;
177
                        for (int l = 0; l <= k; l++)
178
                        {
179
                            raincount += count[l];
180
                            rainval += data[l][1];
181
                        }
182
183
                        DateTime stTime = new DateTime(lastStartTime.Year, lastStartTime.Month, lastStartTime.Day, to[k] - interval, 0, 0);
184
185
                        WeatherInfo intervalInfo = new WeatherInfo(stTime, data[k][0] / count[k], (int)((rainval / raincount) * 100), data[k][2] / count[k], data[k][3] / count[k], interval);
186
                        if (count[k] != 0)
187
                            loignInfo.Add(intervalInfo);
188
189
                    }
190
191
                    lastStartTime = date;
192
                    count = new int[indices];
193
                    for (int l = 0; l < data.Length; l++)
194
                        data[l] = new double[4];
195
                }
196
197
                // find index for current instance
198
                index = 0;
199
                for (int k = 1; k < to.Length; k++)
200
                {
201
                    if (to[k] > list[i].dateTime.Hour && to[k - 1] <= list[i].dateTime.Hour)
202
                    {
203
                        index = k;
204
                        break;
205
                    }
206
                }
207
208
                // aggregate data
209
                data[index][0] += list[i].temp;
210
                data[index][1] += list[i].rain;
211
                data[index][2] += list[i].wind;
212
                data[index][3] += list[i].lum * 1000;
213
                count[index]++;
214
215
            }
216
217
            for (int k = 0; k < to.Length; k++)
218
            {
219
                int raincount = 0;
220
                double rainval = 0; ;
221
                for (int l = 0; l <= k; l++)
222
                {
223
                    raincount += count[l];
224
                    rainval += data[l][1];
225
                }
226
227
                DateTime stTime = new DateTime(lastStartTime.Year, lastStartTime.Month, lastStartTime.Day, to[k] - interval, 0, 0);
228
229
                WeatherInfo intervalInfo = new WeatherInfo(stTime, data[k][0] / count[k], (int)((rainval / raincount) * 100), data[k][2] / count[k], data[k][3] / count[k], interval);
230
                if (count[k] != 0)
231
                    loignInfo.Add(intervalInfo);
232
            }
233
234
            return loignInfo;
235 0da0ac88 A-Konig
        }
236 5d9a5bd9 A-Konig
    }
237 98b568bc A-Konig
238 5d9a5bd9 A-Konig
}