2016-07-26 14 views
1

最初のタイムインと最後のタイムアウトの取得次の日を過ぎると、バイオメトリック読み取りで構造化された最初のエントリと最後のエントリが取得できません。でる。私はこの
新しい生体認証をペアリングするlinqを使用するコレクション

 IEnumerable<biometric> dtrs = new List<biometric>() 
     { 
      new biometric{Id = 1, InOut = 0, DateTime = new DateTime(2013,5,5,8,0,0)}, 
      new biometric{Id = 2, InOut = 0, DateTime = new DateTime(2013,5,5,8,0,5)}, 
      new biometric{Id = 3, InOut = 0, DateTime = new DateTime(2013,5,5,8,1,0)}, 
      new biometric{Id = 4, InOut = 0, DateTime = new DateTime(2013,5,5,8,2,0)}, 

      //here is my problem getting this paired to 
      new biometric{Id = 5, InOut = 0, DateTime = new DateTime(2013,5,5,18,0,0)}, 

      new biometric{Id = 1, InOut = 1, DateTime = new DateTime(2013,5,5,18,0,0)}, 
      new biometric{Id = 2, InOut = 1, DateTime = new DateTime(2013,5,5,17,5,5)}, 
      new biometric{Id = 3, InOut = 1, DateTime = new DateTime(2013,5,5,17,5,10)}, 
      new biometric{Id = 4, InOut = 1, DateTime = new DateTime(2013,5,5,17,10,0)}, 

      //this Entry here 
      new biometric{Id = 5, InOut = 1, DateTime = new DateTime(2013,5,6,3,0,0)}, 
     }; 

     var asd = dtrs.GroupBy(x => new { x.Id, x.DateTime.Date }, (key, group) => new 
     { 
      Key1 = key.Date, 
      Key2 = key.Id, 
      Result = group.OrderBy(a => a.DateTime).ToList() 
     }) 
     //checks if the grouping result has one timein and 1 timeout or more 
     .Where(a => a.Result.Where(z => z.InOut == 1).Count() >= 1 && a.Result.Where(z => z.InOut == 0).Count() >= 1) 
     .Select(a => new dtr() { employeeId = a.Key2, TimeIn = a.Result.FirstOrDefault(b => b.InOut == 1).DateTime, TimeOut = a.Result.LastOrDefault(c => c.InOut == 0).DateTime }); 



    private class biometric 
     { 
     public int Id { get; set; } 
     public DateTime DateTime { get; set; } 
     public int InOut { get; set; } 
     } 

     private class dtr 
     { 
     public int employeeId { get; set; } 
     public DateTime TimeIn { get; set; } 
     public DateTime TimeOut { get; set; } 
     } 

:で、タイムアウト時間が同じ日にある場合でも、私はここ

は私のコード..ですそれは私が望むようにフォーマットされ得ることができます{ID = 5、InOutの= 0、日時が新しい=日時(2013,5,5,18,0,0)}、この
新しい生体{ID = 5から

、InOutの= 1、日時=新しいDateTime(2013,5,6,3,0,0)}、

回避策や提案はありますか?

+0

ことができません 'Id'と' InOut'によって順序によって、あなただけのグループ? –

+0

いいえ..毎日それを取得していました。 –

答えて

1
var asd3 = from d1 in dtrs 
       join d2 in dtrs on d1.Id equals d2.Id 
       where d1.InOut ==0 
        && d2.InOut == 1 
        && d2.DateTime > d1.DateTime 
        && d2.DateTime.AddHours(-18) < d1.DateTime 
       orderby d1.DateTime.Date, d1.Id 
       select new dtr {employeeId = d1.Id, 
           TimeIn=d1.DateTime, 
           TimeOut= d2.DateTime}; 

フィルタリングが適切であることを確認するために、2日分のデータを追加しました。これは誰も1日に18時間以上働かないと仮定します。ほとんどの人が標準で8時間働いていると仮定すると、それは31時間に設定することができます。

employeeId TimeIn       TimeOut 
1   05/05/2013 08:00:00.000   05/05/2013 18:00:00.000 
2   05/05/2013 08:00:05.000   05/05/2013 17:05:05.000 
3   05/05/2013 08:01:00.000   05/05/2013 17:05:10.000 
4   05/05/2013 08:02:00.000   05/05/2013 17:10:00.000 
5   05/05/2013 18:00:00.000   05/06/2013 03:00:00.000 
1   05/06/2013 08:00:00.000   05/06/2013 18:00:00.000 
2   05/06/2013 08:00:05.000   05/06/2013 17:05:05.000 
3   05/06/2013 08:01:00.000   05/06/2013 17:05:10.000 
4   05/06/2013 08:02:00.000   05/06/2013 17:10:00.000 
5   05/06/2013 18:00:00.000   05/07/2013 03:00:00.000 

また、補足として、元のコードにはa.Result.Where(z => z.InOut == 1).Count() >= 1が含まれています。それはa.Result.Any(z => z.InOut == 1)に減らすことができます。簡略化すると、&が読みやすくなり、おそらくより高速に実行されます。

はUPDATE: は、これら2件のレコードを追加する(従業員1は、ランチに行く)

 new biometric{Id = 1, InOut = 1, DateTime = new DateTime(2013,5,5,12,0,0)}, 
     new biometric{Id = 1, InOut = 0, DateTime = new DateTime(2013,5,5,13,0,1)}, 


var sorted = dtrs.OrderBy (d =>d.Id).ThenBy (d =>d.DateTime).ToList(); 

var zipped = sorted.Where (d =>d.InOut==0).Zip(sorted.Where (s =>s.InOut==1), 
       (i,o)=>{ 
         Debug.Assert(i.Id == o.Id); 
         return new dtr 
        { 
         employeeId = i.Id, 
         TimeIn=i.DateTime, 
         TimeOut= o.DateTime 
        }; 
       }).OrderBy (d =>d.TimeIn); 
zipped.Dump(); 
+0

mu upvoteについては考えていません。 –

+0

この行を追加しています。 新しいバイオメトリック{Id = 1、InOut = 0、DateTime = new DateTime 2013,5,5,8,0,1)}、 それは時間が同じであるが、ちょうど1分後に6ペアを作成しますので、回答は –

+0

とマークすることはできません。離れる。あなたが無効なデータを入力した場合、私は責任を負うことができません。 –

関連する問題