2011-02-27 9 views
3

5 프레임 워크, 데이터베이스에서 관계형 외래 키를 사용하지 않고, 어떻게 여러 개의 테이블을 여러 번 조인 한 후에 여러 객체를 다시 전달해야하는지에 대해 4.0에서이 정크 코드가 어떻게 향상되는지 궁금합니다.3.5 VS 4.0 .NET Framework

public IList<User> GetTutorByCourseId(int courseId) 
    { 
     IList<User> output = new List<User>(); 
     using (leDataContext db = new leDataContext()) 
     { 
      try 
      { 
       var m = from c in db.Courses 
         join ct in db.CourseByTutors on c.Id equals ct.CourseId 
         join u in db.Users on ct.TutorId equals u.Id 
         where c.Id == courseId 
         select new 
         { 
          c, ct, u 
         }; 

       foreach (var result in m) 
       { 
        User user = new User(); 
        user.Id = result.u.Id; 
        user.Name = result.u.Name; 
        user.CourseTutor.Id = result.ct.Id; 
        user.Course.Name = result.c.Name;  
        output.Add(user); 
       } 
       return output; 
      } 
      catch (Exception ex) 
      { 
       Logger.Error(typeof(User), ex.ToString()); 
       throw; 
      } 
     } 
    } 

GUI에서 호출자에게 반환되는 개체가 3 개 있습니다. 그러나이 작업을 수행하려면 public 클래스 CourseByTutors {get; set} 및 공용 클래스 (get; set;)의 속성을 User 클래스에 추가해야합니다.이 클래스는 코드를 엉망으로 만듭니다. 이 경우 어떻게 4.0을 해결할 수 있습니까? 내가 선택한 투플 ..에 대해 뭔가 읽었 어 ??

+0

3.5, AFAIK에서 튜플 또는 적어도 동적 유형을 선택할 수 있습니다. –

+0

위의 코드를 변환하여 예제를 보여 주시겠습니까? 나는 실제로 4.0으로 변환할지 여부를 결정하고 있습니다. – VeecoTech

답변

2

데이터베이스에 외래 키가 없더라도 관계를 EF 모델에 추가 할 수 없습니다. 이렇게하면 하위 값을 저장하기 위해 추가 속성을 생성 할 필요가 없으므로 문제를 단순화하는 데 도움이됩니다. CourseTutor, CourseName 등.

내 경험상 3.5와 4.0 모두 도움이 될 수 있지만, 4.0에서 훨씬 더 쉽습니다. 이 도움이

var results = (from u in db.Users 
     where u.Course.Id == courseId 
     select u).ToList(); 
return results; 

희망 : 위의 코드가 같은 것을 보일 수 있습니다되면

.

+0

나는 모델에서 관계를 유지하는 것이 옳은 일이라고 생각하지만, 이것은 실제로 문제를 해결하지는 못할 것입니다. 이렇게하면 코스의 모든 사용자를 얻게되지만 각 사용자마다 자신이 가르치는 모든 코스와 모든 코스를 제공합니다. 직접적인 강좌 관계가 아니라는 사실을 무시하면 (강사, 강사 또는 학생 중 한 명을 통해 이루어짐), 각 사용자별로 문제가되는 강좌뿐만 아니라 강좌를 수강하게됩니다. 이 과정에서 흥미로운 과정을 파악하는 것은 불가능할 수 있습니다. 보기에 특정 모델을 사용하는 것이 더 좋습니다 (IMO). – tvanfosson

+0

단순히 데이터를 읽기 전용보기로 반환하는 경우 저장 프로 시저를 사용하여 쿼리를 병합하고 모든 데이터를 단일 쿼리로 반환하는 것을 고려해보십시오. 그것은 모두 당신의 경험이 어디에 있으며 당신이 행복하게 일하는 기술에 달려 있습니다. 저장 프로 시저를 사용하기로 결정했다면 몇 가지 옵션이 있습니다. 엔티티 프레임 워크 (4.0은 훨씬 더 쉽습니다)를 사용하면 http://msdn.microsoft.com/en-us/library/bb896279.aspx를 확인하거나 데이터 세트를 만들어 저장 프로 시저를 추가 할 수 있습니다. 후자는해야 할 일이지만 어쩌면 유지할 다른 것을 소개 할 것입니다. – dubs

3

(3.5)

select new User 
{ 
    Id = u.Id, 
    Name = u.Name, 
    CourseTutor = new CourseTutor {Id = ct.Id}, 
    Course = new Course {Name = c.Name} 
}; 
return m.ToList(); 

편집 : 불법 CourseTutor.NameCourse.Id 초기화를 대체되었습니다. User의 생성자가 CourseTutorCourse의 고급 초기화를 수행하지 않았다고 가정하면 수정 된 코드가 작동합니다.

+1

+1. 덧붙여 ReSharper는 유사한 솔루션에 대한 리팩토링 힌트를 제공 할 것입니다. – TrueWill

+0

답장을 보내 주셔서 감사합니다. 그러나 나는 IList를 다시 건네주기 때문에 U가 그런 식으로 전달할 수 있다고 생각하지 않는다 ? CourseTutor.Id = ct.Id에서 'Invalid initializer member declarator'오류가 발생했습니다. – VeecoTech

+0

@TrueWill : +1 ReSharper를 홍보했습니다. ;-) 그러나 나는 이것이 OP가 정말로 요구하고 있던 것인지 아닌지에 대해 갑자기 불확실 해졌다. 그는'User'에 추가 속성을 제거하는 것에 더 관심이있는 것처럼 보입니다 ... –

0

보통 내가 처리 할 방법은 GUI에 필요한 정보 만 포함 된 GUI 용 데이터 엔터티와는 별도의 모델을 만드는 것입니다. 원하는 경우 3.5에서이 작업을 수행 할 수 있습니다.

public class TutorViewModel 
{ 
    public IEnumerable<User> Tutors { get; set; } 
    // the pair CourseId, UserId is the relation in CourseTutors so we only 
    // need to keep it once, not once per user. 
    public int CourseId { get; set; } 
    public string CourseName { get; set; } 
} 



public TutorViewModel GetTutorByCourseId(int courseId) 
{ 
    var model = new TutorViewModel { CourseId = courseId }; 

    using (leDataContext db = new leDataContext()) 
    { 
     try 
     { 
      model.CourseName = db.Courses 
           .First(c => c.CourseId == courseId) 
           .Name; 
      model.Users = db.CourseByTutors 
          .Where(c => c.Id == courseId) 
          .Join(db.Users, 
            c => c.TutorId, 
            u => u.Id, 
            (c,u) => u); 

      return model; 
     } 
     catch (Exception ex) 
     { 
      Logger.Error(typeof(User), ex.ToString()); 
      throw; 
     } 
    } 
} 
관련 문제