2011-09-02 18 views
145

이것은 아주 간단하지만 난 손실에있어 : ​​ 데이터 세트의이 유형을 감안할 때 :GROUPBY와 LINQ와 계산

UserInfo(name, metric, day, other_metric) 

이 샘플 데이터 세트 : 나는 '

joe 1 01/01/2011 5 
jane 0 01/02/2011 9 
john 2 01/03/2011 0 
jim 3 01/04/2011 1 
jean 1 01/05/2011 3 
jill 2 01/06/2011 5 
jeb 0 01/07/2011 3 
jenn 0 01/08/2011 7 

카운트가 발생하는 총 횟수와 함께 순서 (0,1,2,3 ..)의 메트릭을 나열하는 테이블을 검색하려고합니다. 그래서이 세트에서 당신이로 끝날 것 : 나는 LINQ 구문 고심하고 있습니다 만 GROUPBY를 넣어 계산하는 위치에 부착하고

0 3  
1 2  
2 2  
3 1 

.... 어떤 도움?

POST 편집 : 게시 된 답변은 항상 다른 수의 숫자가있는 레코드 하나를 반환하므로 절대로 작동하지 않았습니다. 이 결과는 '매트릭스'와 각각 연결된 사용자의 수에 나에게 기록의 순서 세트를 준

 var pl = from r in info 
       orderby r.metric  
       group r by r.metric into grp 
       select new { key = grp.Key, cnt = grp.Count()}; 

: 그러나 내가 함께 일을했던 LINQ SQL에 대한 예를 넣을 수 있었다. 저는 LINQ에 대해 명확하게 처음입니다. 아직 익숙하지 않은 눈에는이 접근법이 순수한 LINQ 접근법과 매우 유사하지만 나에게 다른 대답을주었습니다.

+0

예,하지만 지미의 설명은 나를 더 많이 도왔습니다. 그러나 나는 결코 그의 모범을 얻을 수 없었지만 그것은 새로운 방향으로 나를 인도했다. – Gio

답변

254

GroupBy를 호출 한 후, 각 자체 그룹화 그룹을 만드는 데 사용되는 Key를 노출 그룹 IEnumerable<Grouping>의 시리즈를 얻을 수 있으며 항목이 원래 데이터 세트에있는 어떤의 IEnumerable<T>입니다. 소계를 얻으려면 해당 그룹화에 Count()으로 전화하면됩니다.


foreach(var line in data.GroupBy(info => info.metric) 
         .Select(group => new { 
          Metric = group.Key, 
          Count = group.Count() 
         }) 
         .OrderBy(x => x.Metric) 
{ 
    Console.WriteLine("{0} {1}", line.Metric, line.Count); 
} 
이것은 훌륭하게 빠른 응답했지만 내가 첫 번째 줄에 문제의 비트를 보내고있어, 특히 "data.groupby (정보 => info.metric)"

class UserInfo { 
    string name; 
    int metric; 
    ..etc.. 
} 
... 
List<UserInfo> data = ..... ; 
과 같은 몇 가지 class

난 당신이 이미 목록을 가지고 있으리라 믿고있어/배열 당신이 data.GroupBy(x => x.metric)을 수행 할 때 17,451,515,

, 그것은 data에 의해 정의는 IEnumerable의 각 요소 x를 들어, 다음, 그것은 .metricGrouping에 동일한 메트릭 그룹 모든 요소를 ​​계산하고 모든 결과 그룹의 IEnumerable를 돌려 "를 의미한다.

 var groups = userInfoList 
      .GroupBy(n => n.metric) 
      .Select(n => new 
      { 
       MetricName = n.Key, 
       MetricCount = n.Count() 
      } 
      ) 
      .OrderBy(n => n.MetricName); 

람다 기능 :

<DATA>   | Grouping Key (x=>x.metric) | 
joe 1 01/01/2011 5 | 1 
jane 0 01/02/2011 9 | 0 
john 2 01/03/2011 0 | 2 
jim 3 01/04/2011 1 | 3 
jean 1 01/05/2011 3 | 1 
jill 2 01/06/2011 5 | 2 
jeb 0 01/07/2011 3 | 0 
jenn 0 01/08/2011 7 | 0 

당신의 예를 들어 데이터 집합을 감안할는 GROUPBY 후 다음과 같은 결과가 초래하십시오 List<UserInfo>

(Group 1): [joe 1 01/01/2011 5, jean 1 01/05/2011 3] 
(Group 0): [jane 0 01/02/2011 9, jeb 0 01/07/2011 3, jenn 0 01/08/2011 7] 
(Group 2): [john 2 01/03/2011 0, jill 2 01/06/2011 5] 
(Group 3): [jim 3 01/04/2011 1] 
+0

이것은 훌륭하게 빠른 답장 이었지만 첫 번째 줄, 특히 "data.groupby (info => info.metric)"과 관련하여 약간의 문제가 있습니다. 보통 '데이터'는 현재 데이터 세트이지만 'info.metric'represet은 무엇입니까? 클래스 정의? – Gio

+0

"info.metric"은 질문에서 언급 한 UserInfo 클래스의 메트릭 속성/필드입니다. –

+1

감사합니다. 그러나 실제로 이것은 하나의 값, 즉 다른 메트릭 수의 총 수를 나타냅니다. 이 예제에서 나는 얼마나 많은 다른 카운트를 가지고 있는지를 나타내는 "메트릭 4"를 얻습니다. – Gio

13
userInfos.GroupBy(userInfo => userInfo.metric) 
     .OrderBy(group => group.Key) 
     .Select(group => Tuple.Create(group.key, group.Count())); 
26

userInfoList 가정입니다 예 : GroupBy(), n => n.metric mea ns는 UserInfo 개체마다 필드 metric을 가져옵니다.n의 유형은 문맥에 따라 다르며, 첫 번째 발생 유형은 UserInfo입니다. 목록에 UserInfo 개체가 포함되어 있기 때문입니다. 두 번째 발생시 nGrouping 개체의 목록이기 때문에 Grouping 유형입니다.

Grouping에는 .Count(), .Key() 등의 확장 방법이 있으며 예상 할 수있는 것 외에도 많은 기능이 있습니다. 을 string에서 확인하는 것처럼 그룹에서 .Count()을 확인할 수 있습니다.

관련 문제