2015-01-28 2 views
4

에이 내 입력 테이블입니다 :가입하고 그룹 LINQ

Persons Table: 
================ 
ID Code 
------------------------ 
1 Person1  # Person1: John Smith, 25, 50Kg 
2 Person2  # Person2: William Brown, 30, 80Kg 
3 Person3  # Person3: James Miller, 32, 73Kg 

StringProperties Table: 
========================= 
ID PersonID Name  Value 
---------------------------------------------- 
1 1   FirstName John  # Person1: John Smith, 25, 50Kg 
2 1   LastName Smith  # Person1: John Smith, 25, 50Kg 
3 2   FirstName William  # Person2: William Brown, 30, 80Kg 
4 2   LastName Brown  # Person2: William Brown, 30, 80Kg 
5 3   FirstName James  # Person3: James Miller, 32, 73Kg 
6 3   LastName Miller  # Person3: James Miller, 32, 73Kg 

NumericProperties Table: 
========================= 
ID PersonID Name Value 
----------------------------------------- 
1 1   Age  25   # Person1: John Smith, 25, 50Kg 
2 1   Weight 50   # Person1: John Smith, 25, 50Kg 
3 2   Age  30   # Person2: William Brown, 30, 80Kg 
4 2   Weight 80   # Person2: William Brown, 30, 80Kg 
5 3   Age  32   # Person3: James Miller, 32, 73Kg 
6 3   Weight 73   # Person3: James Miller, 32, 73Kg 

나는 다음과 같은 결과를 생성하는 LINQ 쿼리를 작성하려는 : 이것은 내 코드입니다

Result: 
========== 
Code  FirstName LastName Age  Weight 
----------------------------------------------------------------- 
Person1  John  Smith  25  50 
Person2  William  Brown  30  80 
Person3  James  Miller  32  73 

을하지만 일을하지 않습니다 올바르게 :

var q = from p in db.Persons 
     join s in db.StringProperties on p.ID equals s.PersonID 
     join n in db.NumericProperties on p.ID equals n.PersonID 
     group p by p.Code into g 
     select new 
     { 
      g.Key, 
      g 
     }; 

답변

2

우리는 다음과 같이 보일 실체를 가정 :

이 같은 691,363,210
public class Person 
{ 
    public int ID { get; set; } 
    public string Code { get; set; } 
} 

public class StringProperty 
{ 
    public int ID { get; set; } 
    public int PersonID { get; set; } 
    public string Name { get; set; } 
    public string Value { get; set; } 
} 

public class NumericProperty 
{ 
    public int ID { get; set; } 
    public int PersonID { get; set; } 
    public string Name { get; set; } 
    public int Value { get; set; } 
} 

그리고 데이터 :

var persons = new List<Person> 
{ 
    new Person { ID = 1, Code = "Person1" }, 
    new Person { ID = 2, Code = "Person2" }, 
    new Person { ID = 3, Code = "Person3" } 
}; 

var stringProperties = new List<StringProperty> 
{ 
    new StringProperty { ID = 1, PersonID = 1, Name = "FirstName", Value = "John" }, 
    new StringProperty { ID = 2, PersonID = 1, Name = "LastName", Value = "Smith" }, 
    new StringProperty { ID = 3, PersonID = 2, Name = "FirstName", Value = "William" }, 
    new StringProperty { ID = 4, PersonID = 2, Name = "LastName", Value = "Brown" }, 
    new StringProperty { ID = 5, PersonID = 3, Name = "FirstName", Value = "James" }, 
    new StringProperty { ID = 6, PersonID = 3, Name = "LastName", Value = "Miller" } 
}; 

var numericProperties = new List<NumericProperty> 
{ 
    new NumericProperty { ID = 1, PersonID = 1, Name = "Age", Value = 25 }, 
    new NumericProperty { ID = 2, PersonID = 1, Name = "Weight", Value = 50 }, 
    new NumericProperty { ID = 3, PersonID = 2, Name = "Age", Value = 30 }, 
    new NumericProperty { ID = 4, PersonID = 2, Name = "Weight", Value = 80 }, 
    new NumericProperty { ID = 5, PersonID = 3, Name = "Age", Value = 32 }, 
    new NumericProperty { ID = 6, PersonID = 3, Name = "Weight", Value = 73 } 
}; 

우리는 다음과 같은 문자열 값 테이블에 사람을 가입하고 동시에 그것을 피벗 할 수 있습니다

var stringValues = from p in persons 
        join s in stringProperties on p.ID equals s.PersonID 
        group s by p.Code into g 
        select new 
        { 
         Code = g.Key, 
         FirstName = g.Where(s => s.Name == "FirstName").First().Value, 
         LastName = g.Where(s => s.Name == "LastName").First().Value, 
        }; 

가에 대한 동일한 작업을 수행 숫자 값 :

var numericValues = from p in persons 
        join n in numericProperties on p.ID equals n.PersonID 
        group n by p.Code into g 
        select new 
        { 
         Code = g.Key, 
         Age = g.Where(n => n.Name == "Age").First().Value, 
         Weight = g.Where(n => n.Name == "Weight").First().Value, 
        }; 

var q = from s in stringValues 
     join n in numericValues on s.Code equals n.Code 
     select new 
     { 
      Code = s.Code, 
      FirstName = s.FirstName, 
      LastName = s.LastName, 
      Age = n.Age, 
      Weight = n.Weight 
     }; 

단일 명령문에서이 작업을 수행 할 수 있지만 이렇게 분할하면 더 간단합니다.

실제로 더 빠른 저장 프로 시저에서이 작업을 수행 할 가능성이 더 높습니다.

3

여러 가지 방법으로 해결할 수 있습니다. 여기 부부가 있습니다.

먼저 클래스 및 입력 데이터를 제공 한 DavidG에게 감사드립니다.

가 여기에 옵션 2의
var query = 
    from p in persons 
    join s in stringProperties on p.ID equals s.PersonID into gss 
    join n in numericProperties on p.ID equals n.PersonID into gns 
    from fn in gss.Where(x => x.Name == "FirstName") 
    from ln in gss.Where(x => x.Name == "LastName") 
    from a in gns.Where(x => x.Name == "Age") 
    from w in gns.Where(x => x.Name == "Weight") 
    select new 
    { 
     p.Code, 
     FirstName = fn.Value, 
     LastName = ln.Value, 
     Age = a.Value, 
     Weight = w.Value, 
    }; 

:

여기에 옵션 1의

이 모두 나에게이 결과 제공
var query = 
    from p in persons 
    join s in stringProperties on p.ID equals s.PersonID into gss 
    join n in numericProperties on p.ID equals n.PersonID into gns 
    let sl = gss.ToLookup(x => x.Name, x => x.Value) 
    let nl = gns.ToLookup(x => x.Name, x => x.Value) 
    from FirstName in sl["FirstName"] 
    from LastName in sl["LastName"] 
    from Age in nl["Age"] 
    from Weight in nl["Weight"] 
    select new 
    { 
     p.Code, 
     FirstName, 
     LastName, 
     Age, 
     Weight, 
    }; 

:

result

+0

그럼 당신은 도둑질에 대한 upvote에 얻을 내 입력 : – DavidG

+0

@DavidG - 감사합니다. :-) 나는 당신에게 그것을 창조하기 위해 +1을 주었다. LOL – Enigmativity