我对以下代码的行为有几件事情(但有一件主要事情)不了解。
有人可以帮忙解释一下吗?
它实际上是非常简单的代码-只是一个常规方法调用异步方法。在异步方法中,我使用using块尝试临时更改SynchronizationContext。
在代码的不同点,我探查了当前的SynchronizationContext。
这是我的问题:
码:
public class Test
{
public void StartHere()
{
SynchronizationContext.SetSynchronizationContext(new SynchronizationContext());
this.logCurrentSyncContext("1.1"); // Context #1
Task t = f();
this.logCurrentSyncContext("1.2"); // Context #1, why not Context #2?
t.Wait();
this.logCurrentSyncContext("1.3"); // Context #1
}
private async Task f()
{
using (new ThreadPoolSynchronizationContextBlock())
{
this.logCurrentSyncContext("2.1"); // Context #2
await Task.Delay(7000);
this.logCurrentSyncContext("2.2"); // Context is NULL, why not Context #2?
}
this.logCurrentSyncContext("2.3"); // Context #1
}
// Just show the current …Run Code Online (Sandbox Code Playgroud) 我注意到当我通过不同的"成员路径"导航到同一个实体对象时,我得到了一个不同的对象.(我正在使用更改跟踪代理,因此我获得了一个不同的更改跟踪代理对象.)
这是一个显示我的意思的例子.
var joesInfo1 = context.People.Single(p => p.Name == "Joe").Info;
var joesInfo2 = context.People.Single(p => p.Name == "Joe's Dad").Children.Single(p => p.Name == "Joe").Info;
Run Code Online (Sandbox Code Playgroud)
即使joesInfo1和joesInfo2引用DB(同一实体)中的相同记录,它们也是不同的对象.我认为实体框架确保在这些情况下使用相同的对象.
问题1:这真的是这样吗?或者我的观察错了?
通过Include进行急切加载时,这是一个问题.例如,
IQueryable<Person> allPeople = null;
using(context)
{
allPeople = context.People
//.AsNoTracking()
.Include(p => p.Info)
.Include(p => p.Children)
.Include(p => p.Parent)
.ToList();
}
var joesInfo1 = allPeople.Single(p => p.Name == "Joe").Info; // OK, Info is already there because it was eagerly loaded
var joesInfo2 = allPeople.Single(p => p.Name == "Joe's Dad").Children.Single(p => p.Name == "Joe").Info;
// …Run Code Online (Sandbox Code Playgroud)