0

我有一个包含如下数据的数组(字符串和时间数据用逗号分隔):

array[0]= 通道 1, 01:05:36

数组[1]= 通道 2, 02:25:36

数组[2]= 第 1 组,22:25:36

数组 [3]= 网络,41:40:09

数组[4]= LossOf,03:21:17

数组[5]= LossOf,01:13:28

数组[6]= 通道 1, 04:25:36

数组[7]= 通道 2, 00:25:36

. . . 数组[xxx]= xxx, xxx

我想计算所有重复项并确定每个重复项的平均时间,如下所示:

Item1,Channel 1,2次出现,每次出现的平均时间约为xx分钟

Item2,Channel 2,2次出现,每次出现的平均时间约为xx分钟

Item3,LossOf,2次出现,每次出现平均时间约xx分钟

时间格式为 hh:mm:ss

这是我到目前为止所做的,它只给了我重复的总次数:

public void CountDuplicates(string[] myStringArray)
{
  //count duplicates
  ArrayList list = new ArrayList();
  int  loopCnt=0;

  foreach (string item in myStringArray)
  {
    if (!String.IsNullOrEmpty(myStringArray[loopCnt]) == true)
      list.Add(item);
    loopCnt++;
  }

  loopCnt = 0;
  Dictionary<string, int> distinctItems = new Dictionary<string, int>();
  foreach (string item in list)
  {
    if (!distinctItems.ContainsKey(item))
    {
      distinctItems.Add(item, 0);
      loopCnt++;
    }
    distinctItems[item] += 1;
  }
  foreach (KeyValuePair<string, int> distinctItem in distinctItems)
  {
    txtDisplayResults.AppendText("Alarm Error: " + distinctItem.Key + ",  How many times: " + distinctItem.Value + "\r\n");
  }
}
4

2 回答 2

1

也许是这样:

一个通道类来保存你的价值观

class Channel
{
    public String Name { get; set; }
    public TimeSpan Duration { get; set; }
}

你的样本数据

var array = new[]{
    "Channel 1, 01:05:36",
    "Channel 2, 02:25:36",
    "Group 1, 22:25:36",
    "Network, 41:40:09",
    "Loss of, 03:21:17",
    "Loss of, 01:13:28",
    "Channel 1, 04:25:36",
    "Channel 2, 00:25:36",
};

查询

var channelGroups = array.Select(s =>
{
    var tokens = s.Split(new[] { ',' }, StringSplitOptions.RemoveEmptyEntries);
    var tsTokens = tokens[1].Split(':');
    return new Channel()
    {
        Name = tokens[0],
        Duration = new TimeSpan(
            int.Parse(tsTokens[0]),  // hours
            int.Parse(tsTokens[1]),  // minutes
            int.Parse(tsTokens[2]))  // seconds
    };
})
.GroupBy(c => c.Name)
.Select(g => new
{
    Channel = g.Key,
    Count = g.Count(),
    Average = g.Average(c => c.Duration.TotalMinutes)
});

输出:

foreach(var group in channelGroups)
{
   Console.WriteLine("Channel:[{0}] Count:[{1}] Average:[{2}]"
                    , group.Channel, group.Count, group.Average);
}

演示:http: //ideone.com/6dF6s

Channel:[Channel 1] Count:[2] Average:[165.6]
Channel:[Channel 2] Count:[2] Average:[85.6]
Channel:[Group 1] Count:[1] Average:[1345.6]
Channel:[Network] Count:[1] Average:[2500.15]
Channel:[Loss of] Count:[2] Average:[137.375]
于 2012-09-17T22:31:33.517 回答
0

喜欢以下帮助?

var regex=new Regex(@"^(?<item>.*), (?<hours>\d{2}):(?<minutes>\d{2}):(?<seconds>\d{2})$");
var result=array.Select(a=> regex.Match(a)).Where(a=>a.Success)
           .Select (a => new { 
                               item=a.Groups["item"].Value,
                               time=decimal.Parse(a.Groups["hours"].Value)*60 + 
                                    decimal.Parse(a.Groups["minutes"].Value) +
                                    decimal.Parse(a.Groups["seconds"].Value)/60
                              })
           .GroupBy (a => a.item)
           .Select (a =>new {item=a.Key, duplicates=a.Count(),time=a.Average (b => b.time)} );

格式化为字符串,然后您可以执行以下操作:

var resultString=result.Aggregate(new StringBuilder(),(sb,a)=>sb.AppendFormat("Item: {0}, # of occurences: {1}, Average Time: {2:0.00}\r\n",a.item,a.duplicates,a.time)).ToString();

resultString现在将是您要查找的字符串。

编辑——请求使用字典后,由于元组不可用,您需要定义一个类来保存临时数据。我使用了公共字段,但您可以轻松扩展以使用私有字段周围的属性

public class Data { 
   public int Occurrences;
   public decimal Time;

   public Data(int occurrences, decimal time) {
     this.Occurrences=occurrences;
     this.Time=time;
   }
}

var regex=new Regex(@"^(?<item>.*), (?<hours>\d{2}):(?<minutes>\d{2}):(?<seconds>\d{2})$");
var dict = new Dictionary<string,Data>();

foreach (var entry in array) {
    if (regex.IsMatch(entry)) {
      var match=regex.Match(entry);
      var item=match.Groups["item"].Value;
      var time=decimal.Parse(match.Groups["hours"].Value)*60 + 
                                        decimal.Parse(match.Groups["minutes"].Value) +
                                        decimal.Parse(match.Groups["seconds"].Value)/60;
      if (dict.ContainsKey(item)) {
        dict[item].Occurrences++;
                dict[item].Time+=time);
      } else {
        dict[item]=new Data(1,time);
      }
    }
}

StringBuilder sb=new StringBuilder();
foreach (var key in dict.Keys) {
    sb.AppendFormat("Item: {0}, # of occurences: {1}, Average Time: {2:0.00}\r\n", key, dict[key].Occurrences, dict[key].Time / dict[key].Occurrences);
}
var resultString=sb.ToString();
于 2012-09-17T22:34:26.793 回答