这是今天做的一个测试。
        private static void updateCust(Customers c)
        {
            NorthwindEntities n = new NorthwindEntities();
            c.CompanyName = "lulalua";
            n.SaveChanges();
        }        然后我执行下面的代码:
        Customers customer = (from c in ne.Customers where c.CustomerID == "DFEGI" select c).FirstOrDefault();        updateCust(customer);
        没有报错,跟踪updateCust里面,CompanyName也修改了。但是问题是,数据库并没有被更新。
        当然,我觉得这是因为,和Hibernate一样,虽然俩Customer表面看起来一样,但其实他俩并不是一个东西。现在的问题是怎么解决他?有没有类似的Merge的方法?我对EF的对象状态还不是非常了解,那位可以详细的讲讲。我并不想只传ID当参数,
去Find或者重新查询。那位大大科普一下嗖?!

解决方案 »

  1.   

    因为你updateCust()方法与你的那段LINQ查询,分属于两个Context。
      

  2.   

    Customers customer = (from c in ne.Customers where c.CustomerID == "DFEGI" select c).FirstOrDefault();   updateCust(customer);
    ne.SubmitChanges();//再提交一次看看
      

  3.   

    Customer cust =
        db.Customers.First(c => c.CustomerID == "ALFKI");
    cust.ContactTitle = "Vice President";
    db.SubmitChanges();
      

  4.   

      private static void updateCust(Customers c)
      {
      NorthwindEntities n = new NorthwindEntities();
      //此处c 和n有关系么?  这代码写的很有问题
      c.CompanyName = "lulalua";
      n.SaveChanges();
      }
      

  5.   


    此处的C和N当然没有关系。但是,如果你用过HIBERNATE的话,你就知道这是可行的。你只需要merge一下两个Customer,他们可以在任意的connection里成功执行。
    我是想做到这种效果。
    当然按.net的风格来办事的话,应该穿ID进来,code first的时候可用find来加载对象,之后再操作。我想说的就是这个问题。有没有方法做到和Hibernate一样的效果。因为这样非常方便。
      

  6.   


            private static void updateCust(Customers c)
            {
                NorthwindEntities n = new NorthwindEntities();
                var cust = (from c1 in n.Customers where c1.CustomerID == c.CustomerID select c1).FirstOrDefault();//这样就是可以的,但这样好繁琐
                cust.CompanyName = "uodate1";
                n.SaveChanges();
            }
      

  7.   


    没办法,理论上就是这样,只能在上下文中进行操作,出了上下文就不行。不然不能保证上下文的同步。
    你可以查找“ EntityFramework ” 三层架构/分层架构/多层架构 相关资料了解更多。当然也可学得一些技巧。
      

  8.   

    Basically, you were trying to update a detached entity. Here's what happened: you first extracted a customer entity from a context, but later you attempted to change that customer and open another context that customer.The problem is: the second context had no idea of your customer entity extracted from the first context. If this is the way you want, you need to attach that customer back to the second context, by using: context.Attach(customer), and then, you must modify the customer's state to Modified, by using state manager.
      

  9.   

    but later you attempted to change that customer and open another context that customer.
    --> but later you attempted to change that customer and open another context to update that customer in database.
      

  10.   


    我不清楚你说的状态混乱是什么意思,如果有混乱,只能说明你的代码没有写好。其实MSDN解释的很详细了,你可以去查一下。这完全取决于你:你是想打开并维持一个持久context还是打开一个context,做一点事情,然后立即关闭。如果是前者,你可以直接update,因为所有的entity都在当前context里,如果是后者,所有的entity已经detached掉了,你需要attache回去;而且,如果你是做远程服务,那所有客户端的entity必然是detached的。请你相信我,这里不存在好使不好使。没有任何一个ORM工具可以做到你说的既关闭了连接,又能识别已经脱离context的实体。任何问题,请仔细研究透以后后再下结论。
      

  11.   

    如果是后者,所有的entity已经detached掉了,你需要attache回去; 对,就是这里,我认为容易造成混乱。你需要随时清楚你detached了谁,用完了之后,你需要在把他合并回来。这样做的目的出于“东西交给你来办,我不管,你干完了,我接着办自己事儿”的目的,因为现在我的情况是数据和硬件要在同一个事务里。我明白不同的context里本身就对游离状态的没有认识能力。但我讲的并不是关闭连接,而是不在同一个链接里。事实上,如果用HIBERNATE来做的话,下面的逻辑是没有任何问题的(代码并不等同,但逻辑相同):
    private static void updateCust(Customers c)
      {
       NorthwindEntities n = new NorthwindEntities();//视为一个链接
       var cust = n.Merge(c); //将C合并到这个链接,在这个链接里操作 ,ef出现的问题就是,我要合并进来可以,但!前提是我在上一个链接里,得明确的把他分离出去,之后,才能合并到这个链接n里。这里就容易造成混乱,就好像以前写程序你会忘记Dispose().
       //并且,EF目前对对象参数还没有查询能力,可能问题本质与上个问题是相同的。例如:hibernate可以    select * from customers as ccc where  ccc == c,但我用EF做了实验,结果是EF只能以标量作为参数。实际上这样做只是为了书写方便。也为了研究下技术,以备不时只需。
       cust.CompanyName = "uodate1";
       n.SaveChanges();//提交
      }