Skip to content
shuxin edited this page Apr 20, 2023 · 4 revisions

更新数据

Chloe 支持两种数据更新方式。

1.实体更新:

Person person = new Person();
person.Id = 1;
person.Name = "Chloe";
person.Age = 28;
person.Gender = Gender.Male;
person.EditTime = DateTime.Now;

/* 更新所有映射的字段 */
dbContext.Update(person);
/*
 * String @P_0 = 'Chloe';
   Int32 @P_1 = 1;
   Int32 @P_2 = 28;
   Int32 @P_3 = NULL;
   DateTime @P_4 = '2021/2/19 16:12:40';
   UPDATE [Person] SET [Name]=@P_0,[Gender]=@P_1,[Age]=@P_2,[CityId]=@P_3,[EditTime]=@P_4 
   WHERE [Person].[Id] = @P_1
 */

由于 person 对象未被上下文跟踪,这会使所有的映射列都会被更新。Chloe 也支持类似 EF 一样只更新被修改过的属性。

/*
 * 支持只更新属性值已变的属性
 */

/* 在修改实体属性前让上下文跟踪实体 */
dbContext.TrackEntity(person);

/* 然后再修改实体属性 */
person.Name = person.Name + "1";

/* 然后调用 Update 方法,这时只会更新被修改过的属性 */
dbContext.Update(person);
/*
 * String @P_0 = 'Chloe1';
   Int32 @P_1 = 1;
   UPDATE [Person] SET [Name]=@P_0 WHERE [Person].[Id] = @P_1
 */

2.lambda 方式更新:

该方式解决的问题是:1.指定列更新;2.批量更新;3.支持类似 Age=Age + 1 这样更新字段。用法如下:

/* tip:必须在 lambda 里写 new Person() */
dbContext.Update<Person>(a => a.Id == 1, a => new Person()
{
    Name = a.Name,
    Age = a.Age + 1,
    Gender = Gender.Male,
    EditTime = DateTime.Now
});
/*
 * UPDATE [Person] SET [Name]=[Person].[Name],[Age]=([Person].[Age] + 1),[Gender]=1,[EditTime]=GETDATE() 
   WHERE [Person].[Id] = 1
 */

//复杂条件以及复杂 set 更新
dbContext.Update<Person>(a => a.Id == dbContext.Query<City>().Where(city => city.Id == a.Id).First().Id, a => new Person()
{
    Name = dbContext.Query<City>().Where(city => city.Id == a.Id).First().Name
});
/*
 * UPDATE [Person] 
   SET [Name]=(SELECT [City].[Name] AS [C] FROM [City] AS [City] WHERE [City].[Id] = [Person].[Id] LIMIT 1 OFFSET 0) 
   WHERE ([Person].[Id] = (SELECT [City].[Id] AS [C] FROM [City] AS [City] WHERE [City].[Id] = [Person].[Id] LIMIT 1 OFFSET 0))
 */