1

我有以下课程:

public class Person {
   public int Id {get; set;}
   ...
   public ICollection<PersonalJobs> Jobs {get; set;}
}

public class PersonalJob {
   public int Id {get; set;}
   public int PersonId {get; set;}
   public int JobId {get; set;}
   public Job Job {get; set;}
   public DateTime StartDate {get; set;}
   ...
}

public class Job {
   public int Id {get; set;}
   public string Description {get; set;}
   ...
}

现在我执行以下操作:

var _personId = 1;
var _jobId = 15;

_context.Set<Jobs>().Load();  //Pre-Load all jobs

var _person = _context.Persons.Include(p => p.Jobs.Select(j => j.Job))
   .SingleOrDefault(p => p.Id == _personId);

var _job = _person.Jobs.SingleOrDefault(p => p.JobId == _jobId);
_job.JobId = 23;  //Change the job that this person is tied to.

// At this point, if I try to access _job.Job.Description, it still references the old job.

因为上下文已经加载了 Jobs,所以我假设 EF 在我更改 ID 时会更新 _job 的导航属性。然而,这种情况并非如此。在这种情况下,_job.Job 仍然引用与原始 ID (15) 关联的作业。

我对 EF 如何处理导航属性的假设是错误的,还是我只是在这个难题中遗漏了一部分?

谢谢。

4

2 回答 2

2

我刚刚在您的评论中读到您希望参考在保存之前与新 id 同步。但这是 EF 不会自动执行的操作。它发生在你打电话SaveChanges没事时,但如果你想在此之前发生,你必须打电话

_context.ChangeTracker.DetectChanges();

(假设您使用DbContextAPI)

DetectChanges触发关系修复,这是一个同步外键中涉及的所有属性的过程。

顺便说一句:您不必为此成功预加载作业。

于 2012-12-12T16:36:21.757 回答
1

您需要调用SaveChanges()以持久保存到数据库:

_job.JobId = 23;

_context.SaveChanges();

// _job.Job now points to Job 23

这只是因为 Job 23 已经加载到你的DbContext.

如果加载了一个对象,EF 将在您调用时连接您的属性SaveChanges()


编辑:

您已经加载了所有作业,因此您可以自己设置属性:

_job.Job = _context.Set<Jobs>().Find( 23 );

这不会导致任何数据库调用 - 它会从您的DbContext

UPDATE当您调用时,它会产生相同的语句SaveChanges()

于 2012-12-12T16:26:52.803 回答