这是我第一次接触实体框架——作为一个长期使用 Linq2Sql 的人,我从来没有人向我展示过 EF 做得更好的地方。我已经学习了一些 MS 教程,并且我有一个可以轻松创建数据库和存储内容的上下文。我可以用 LINQ 查询它,所以它仍然很熟悉。
什么不工作,虽然是一种关系。我有三个类,分别称为 Product、Place 和 Price。它们都有一个 int Id。Product 和 Place 都有一个虚拟收藏,Price 对 Product 和 Place 都有一个属性。
逻辑模型是我有一个在零个或多个地方销售的产品列表,并且任何产品在每个位置都可能有不同的价格(想想当地的税收调整)。
我的第一个测试不会填充产品的价格列表,因此 myProduct.Prices 为空。我通过自己获取价格清单来解决这个问题
var prices = dB.Prices.Where(...)
我的问题是,当我有多个地点(Id 1 和 2),并且我输入了多个价格的数据时,当 ID 为 2 时,地点为空。
我尝试将数据直接添加到表中(一个 ID 为 2 的地方,一个 Place_Id = 2 的价格)。我试过用代码添加它们。
如果我进入 Price 表并将 Place_Id 都更改为 1,则它们都检索 Place 1。如果我将它们都设置为 2,它们都会给我 null Place。如果我每种方式都设置一个,则带有 1 的一个有效,另一个为空。
所以我的关系有效,但只有当 FK 为 1 时。我做过 WTF 吗?
编辑:代码示例(对不起,我之前在手机上)
{ //declared in my dbcontext
...
public DbSet<Product> Products { get; set; }
public DbSet<Place> Places{ get; set; }
public DbSet<Price> Prices{ get; set; }
...
}
//Just to be clear, below are separate from the dbcontext
public class Product
{
public int Id { get; set; }
public string Name { get; set; }
...
[InverseProperty("Product")]
public ICollection<Price> Prices { get; set; }
}
public class Place
{
public int Id { get; set; }
public string Name { get; set; }
...
[InverseProperty("Place")]
public ICollection<Price> Prices { get; set; }
}
public class Price{
public int Id { get; set; }
public Product Product { get; set; }
public Place Place { get; set; }
...
}
我试过直接插入行,我也试过
//In the Seed(Context) method of my DbContextInitializer, where db is an instance of my dbcontext
var a1 = new Place { Name = "Place 1"};
var a2 = new Place { Name = "Place 2"};
var p = new Product { Name = "Test Product" };
db.Products.Add(p);
db.Associations.Add(a1);
db.Associations.Add(a2);
db.Prices.Add(new Price { Amount = 10.1m, Place= a1, Product = p });
db.Prices.Add(new Price { Amount = 3.45m, Place= a2, Product = p });
db.SaveChanges();
所有这些数据都被插入,我可以查询数据库来查看它。
即将解开的代码是:
foreach (var p in db.Products.ToList()) //NB if I try this without the ToList I get an exception about an open data reader
{
var price = 0m;
foreach (var o in db.Prices)
{
//there are two price records which we created above.
//In the first Price, o = {Id = 1, Place_Id = 1, Product_Id = 1}. This works.
//In the second Price, o = {Id = 2, Place_Id = 2, Product_Id = 1}. o.Place is null
// Yes, there is absolutely a Place {Name = "Place 2", Id = 2} in the database
if (o.Place.Id == ...)price += o.Amount;
}
...
}
我注意到了一些有趣的事情。如果我加入更多产品,它适用于任何产品 ID。另外(我怀疑这是根本问题),我注意到 o.Product 是 Product 类型,但是 o.Place 是 DynamicProxies.Place_Guid 类型 - 但我不明白为什么这些不同我已经在与您在上面看到的相同的时尚。