private Channel ParseSeries(ANLG_CHNL_NEW analogChannel) { Series series = new Series(); series.Channel = new Channel(); series.SeriesType = new SeriesType() { Name = "Instantaneous" }; series.SourceIndexes = analogChannel.chanlnum; Channel channel = series.Channel; channel.Series = new List <Series>() { series }; channel.MeasurementType = new MeasurementType() { Name = "Unknown" }; channel.MeasurementCharacteristic = new MeasurementCharacteristic() { Name = "Unknown" }; channel.Phase = new Phase() { Name = "Unknown" }; channel.Name = analogChannel.title; channel.HarmonicGroup = 0; return(channel); }
private void ExportToCOMTRADE(string filePath, ControlFile controlFile, string identityString, List <ANLG_CHNL_NEW> analogChannels, List <EVNT_CHNL_NEW> digitalChannels) { string assetKey = GetMeterKey(filePath, m_filePattern) ?? ThreadContext.Properties["Meter"].ToString(); string rootFileName = FilePath.GetFileNameWithoutExtension(filePath); string directoryPath = Path.Combine(m_emaxSettings.COMTRADEExportDirectory, assetKey); string schemaFilePath = Path.Combine(directoryPath, $"{rootFileName}.cfg"); string dataFilePath = Path.Combine(directoryPath, $"{rootFileName}.dat"); Schema comtradeSchema = new Schema(); if (File.Exists(dataFilePath)) { return; } comtradeSchema.StationName = Regex.Replace(identityString, @"[\r\n]", ""); comtradeSchema.Version = 2013; comtradeSchema.AnalogChannels = new AnalogChannel[controlFile.AnalogChannelCount]; comtradeSchema.DigitalChannels = new DigitalChannel[controlFile.EventChannelSettings.Count]; comtradeSchema.SampleRates = new SampleRate[1]; comtradeSchema.SampleRates[0].Rate = controlFile.SystemParameters.samples_per_second; comtradeSchema.SampleRates[0].EndSample = controlFile.SystemParameters.rcd_sample_count - 1; comtradeSchema.StartTime = new Timestamp() { Value = m_meterDataSet.DataSeries[1][0].Time }; int triggerIndex = controlFile.SystemParameters.start_offset_samples + controlFile.SystemParameters.prefault_samples; comtradeSchema.TriggerTime = new Timestamp() { Value = m_meterDataSet.DataSeries[1][triggerIndex].Time }; for (int i = 0; i < analogChannels.Count; i++) { ANLG_CHNL_NEW analogChannel = analogChannels[i]; AnalogChannel comtradeAnalog = new AnalogChannel(); DataSeries channelData = m_meterDataSet.DataSeries[i + 1]; double unitMultiplier = 1.0D; double max = channelData.Maximum; double min = channelData.Minimum; double num; comtradeAnalog.Index = i + 1; comtradeAnalog.Name = analogChannel.title; comtradeAnalog.Units = new Func <string, string>(type => { switch (type) { case "V": return("kVAC"); case "A": return("kAAC"); case "v": return(" VDC"); default: return(type); } })(analogChannel.type); if (analogChannel.type.All(char.IsUpper)) { unitMultiplier = 0.001D; max *= unitMultiplier; min *= unitMultiplier; } comtradeAnalog.Multiplier = (max - min) / (2 * short.MaxValue); comtradeAnalog.Adder = (max + min) / 2.0D; comtradeAnalog.PrimaryRatio = double.TryParse(analogChannel.primary, out num) ? num * unitMultiplier : 0.0D; comtradeAnalog.SecondaryRatio = double.TryParse(analogChannel.secondary, out num) ? num * unitMultiplier : 0.0D; comtradeSchema.AnalogChannels[i] = comtradeAnalog; } for (int i = 0; i < digitalChannels.Count; i++) { EVNT_CHNL_NEW digitalChannel = digitalChannels[i]; DigitalChannel comtradeDigital = new DigitalChannel(); comtradeDigital.Index = i + 1; comtradeDigital.ChannelName = digitalChannel.e_title; comtradeSchema.DigitalChannels[i] = comtradeDigital; } Directory.CreateDirectory(directoryPath); File.WriteAllText(schemaFilePath, comtradeSchema.FileImage, Encoding.ASCII); using (FileStream stream = File.OpenWrite(dataFilePath)) { const int DigitalSize = sizeof(ushort) * 8; IEnumerable <DataSeries> digitalWords = m_meterDataSet.Digitals.Skip(1) .Select((dataSeries, index) => dataSeries.Multiply(Math.Pow(2.0D, DigitalSize - (index % DigitalSize) - 1))) .Select((DataSeries, Index) => new { DataSeries, Index }) .GroupBy(obj => obj.Index / DigitalSize) .Select(grouping => grouping.Select(obj => obj.DataSeries)) .Select(grouping => grouping.Aggregate((sum, series) => sum.Add(series))); List <DataSeries> allChannels = m_meterDataSet.DataSeries.Skip(1) .Select((dataSeries, index) => analogChannels[index].type.All(char.IsUpper) ? dataSeries.Multiply(0.001D) : dataSeries) .Concat(digitalWords) .ToList(); for (int i = 0; i < m_meterDataSet.DataSeries[1].DataPoints.Count; i++) { DateTime timestamp = m_meterDataSet.DataSeries[1][i].Time; double[] values = allChannels .Select(dataSeries => dataSeries[i].Value) .ToArray(); Writer.WriteNextRecordBinary(stream, comtradeSchema, timestamp, values, (uint)i, false); } } }