一、为什么要在EF中执行SQL语句

使用EF操作数据库,可以避免写SQL语句,完成使用Linq实现,但为什么还要在EF中执行SQL语句呢。如果要写SQL语句,完全可以使用ADO.NET来操作数据库。这样说虽然没错,可是有些时候使用EF操作数据库还是有一些不方便的地方,例如:如果要修改某一条记录,按照EF的正常流程走,需要先把要修改的数据查询出来,然后在去修改,这样不仅麻烦而且性能也低,这时直接使用EF执行SQL语句性能会提高很多。

而使用EF执行SQL又比ADO.NET方便,特别是在执行查询语句的时候,EF会把查询到的数据自动保存到数据实体中,省去了使用DataReader的麻烦。同时查询出来的数据还会进行跟踪,如果你修改了查询出的值,之后就可以很方便的使用.SaveChanges()直接更新到数据库了。

在数据上下文DbContext中有一个Database的属性,Database属性中有两组方法:ExecuteSqlCommand()和SqlQuery()。这两个方法都可以用来执行SQL语句,但这两个方法也有不同点:ExecuteSqlCommand()是不返回结果的,只返回受影响的行数,所以ExecuteSqlCommand()更适合用来执行创建、插入、更新、删除操作(即执行给定的DDL/DML命令)。SqlQuery()则会返回查询到的结果,并将结果保存在数据实体中,所以SqlQuery()更适合执行查询操作。

二、使用ExecuteSqlCommand()执行创建、插入、更新、删除语句

ExecuteSqlCommand()的使用方法很简单,直接传入SQL语句就可以了,执行完成后会返回受影响的行数。

在下面的例子中,entity是一个继承自DbContext的对象。

1、执行创建语句

// 执行创建语句

string strCreateSQL = @"CREATE table test( id int primary key not null,name varchar(16),password varchar(20))";

// 注意:执行create语句受影响的行数是-1

int result = entity.Database.ExecuteSqlCommand(strCreateSQL);

if (result.Equals(-1))

{

Console.WriteLine("创建成功!");

}

2、执行Insert语句

// 执行Insert语句

string strInsertSQL = @"INSERT INTO test

SELECT 1,'小明','1234' UNION

SELECT 2,'小王','1234' UNION

SELECT 3,'小红','1234' ";

int result = entity.Database.ExecuteSqlCommand(strInsertSQL);

if (result > 0)

{

Console.WriteLine("插入成功");

}

3、执行Update语句

// 执行Update语句

string strUpdateSQL = @"UPDATE test SET password=@pwd1 WHERE id=@id1;

UPDATE test SET password=@pwd2 WHERE id=@id2;";

SqlParameter[] para = {

new SqlParameter("@pwd1","ceshi12we"),

new SqlParameter("@id1",1),

new SqlParameter("@pwd2","ceshi127890"),

new SqlParameter("@id2",2),

};

int result = entity.Database.ExecuteSqlCommand(strUpdateSQL, para);

if (result > 0)

{

Console.WriteLine("更新成功");

}

4、执行Delete语句

// 执行删除语句

string strDelSQL = "delete from test";

int result = entity.Database.ExecuteSqlCommand(strDelSQL);

if (result > 0)

{

Console.WriteLine("删除成功");

}

5、执行Drop语句

string strDropSQL = "drop table test";

int result = entity.Database.ExecuteSqlCommand(strDropSQL);

if (result.Equals(-1))

{

Console.WriteLine("删除成功");

}

注意:执行DDL语句(create、alter、drop等)返回值是-1,DML(insert、update、delete)返回的是受影响的行数。

三、使用SqlQuery()查询数据

SqlQuery()是用来执行查询的。SqlQuery()使用前需要指定返回值的类型。返回值类型可以是定义的实体类型,或者基元类型。例如:查询一个用户的完整信息,返回类型就是用户实体类型;如果是统计有多少个用户,返回值就是int类型。

注意:返回值的个数和名称必须和传入的类型中属性个数、名称相同,不如会报错。

在下面的例子中User是根据数据库表生成的实体类型。

string strSQL = "SELECT * FROM Users WHERE ID>=10 ORDER BY ID DESC";

var info = entity.Database.SqlQuery(strSQL);

foreach (var item in info)

{

Console.WriteLine("ID:" + item.ID + " " + "登录名:" + item.LoginName + " " + "密码:" + item.Password);

}

运行结果:

前面说过返回值的个数和名称必须和传入的类型中属性个数、名称相同,不如会报错。如果将SQL语句修改为只查询ID、登录名、密码会出现下面的错误:

如果只想查询ID、登录名、密码该怎么办呢?那就需要单独定义一个类(只包含ID、登录名、密码三个属性)来保存数据.

新定义的类,只包含ID、登录名、密码三个属性:

public class newUser

{

public int ID { get; set; }

public string LoginName { get; set; }

public string Password { get; set; }

}

// 方法四:SqlQuery

try

{

string strSQL = "SELECT ID,LoginName,Password FROM Users WHERE ID>=10 ORDER BY ID DESC";

var info = entity.Database.SqlQuery(strSQL);

foreach (var item in info)

{

Console.WriteLine("ID:" + item.ID + " " + "登录名:" + item.LoginName + " " + "密码:" + item.Password);

}

}

catch (Exception ex)

{

Console.WriteLine(ex.Message);

}

运行结果:

返回值是基元类型:

查询用户数量,返回int类型

// 查询用户数量

string strSQL = "SELECT COUNT(*) FROM test";

var result = entity.Database.SqlQuery(strSQL);

// 注意:必须使用循环才会真正的去数据库执行SQL语句,否则不会再数据库执行SQL语句(EF的延迟加载)

foreach(var item in result)

{

Console.WriteLine("用户数量:" + item.ToString());

}

运行结果:

四、使用DbSet下的SqlQuery()

在每个数据实体集合DbSet下也有一个SqlQuery(),功能与上面介绍的一样,只不过DbSet下的SqlQuery()只能返回DbSet中包含的类型,DbSet下的SqlQuery()在返回数据的同时还会让数据库上下文(DBContext)跟踪返回数据的状态,如果返回的数据发生了修改,就可以使用SaveChanges()将结果直接保存回数据库。而Database.SqlQuery()查出的结果则不能跟踪返回数据的状态。

1、使用实体集合下面的SqlQuery()方法

string strSQL = "SELECT * FROM Users WHERE UserID='002068'";

User user = entity.Users.SqlQuery(strSQL).FirstOrDefault();

user.Password = "测试实体下面的SqlQuery方法";

// 调用SaveChanges()方法可以更新Password字段

entity.SaveChanges();

2、使用Database下的SqlQuery()方法

string strSQL = "SELECT * FROM Users WHERE UserID='002068'";

User user = entity.Database.SqlQuery(strSQL).FirstOrDefault();

user.Password = "测试Database下面的SqlQuery方法";

// 调用SaveChanges()方法不可以更新Password字段

entity.SaveChanges();

如果希望使用Database下的SqlQuery()查询出的数据在修改后也能保存到数据库,可以使用下面的代码:

string strSQL = "SELECT * FROM Users WHERE UserID='002068'";

User user = entity.Database.SqlQuery(strSQL).FirstOrDefault();

user.Password = "测试Database下面的SqlQuery方法";

// 设置这条数据的状态是:Modified,这样可以通知数据上下文,这条记录也被修改了

entity.Entry(user).State = System.Data.Entity.EntityState.Modified;

// 调用SaveChanges()方法不可以更新Password字段

entity.SaveChanges();

ef 执行mysql语句_在EF中执行SQL语句相关推荐

  1. mysql字段重命名_MySQL中使用SQL语句对字段进行重命名

    MySQL中,如何使用SQL语句来对表中某一个字段进行重命名呢?我们将使用alter table 这一SQL语句. 重命名字段的语法为:alter table change . 现在我们来尝试把tes ...

  2. mysql 构造 linq语句_[转]查看LINQ生成SQL语句的几种方法

    记录LINQ生成的SQL语句是常用的调试方式,而且能根据需要来优化LINQ生成的SQL语句,更能了深入的了解LINQ. DataContext的Log属性来将LINQ to SQL生成的SQL语句格式 ...

  3. mybatisplus执行sql语句_一条更新的SQL语句是如何执行的?

    提出问题 UPDATE student SET score = score + 1 WHERE uid = 666; 以上就是一条最简单的SQL更新语句,想要知道上面这句SQL语句是怎么执行的先要了解 ...

  4. upupw mysql崩溃_安装UPUPW后出现SQL语句运行错误解决办法

    如果执行SQL出现错误,如: #1366 - Incorrect integer value: '' for column 'xxx' at row 1 在执行插入语句时,xxx的值不应该像以前那样写 ...

  5. mysql字段排序语句_数据库字段排序的SQL语句

    简明现代魔法 -> 数据库技术 -> 数据库字段排序的SQL语句 数据库字段排序的SQL语句 2009-09-17 将字段依次写在order by 后面即可 , 中间用逗号隔开. sele ...

  6. python执行oracle的sql语句_在oracledb中执行SQL脚本一次执行一条语句

    假设我有一个sql脚本,如下所示:--split statement 1 ALTER TABLE abs ADD (make VARCHAR2(2 byte), model varCHAR2(12 B ...

  7. mysql 数据库连表查询语句_数据库连表查询sql语句

    {"moduleinfo":{"card_count":[{"count_phone":1,"count":1}],&q ...

  8. mysql 存储过程 转义_mysql存储过程中的 sql语句符号问题

    展开全部 不要用斜杠 我看看我这个.没问题PROCEDURE Pro_SelectBidUnit_NOWTIME_ALL(IN P_ID      VARCHAR(64), IN P_IFID     ...

  9. sql转java对象_关于hibernate中使用sql语句时,类对象的转换问题。

    该楼层疑似违规已被系统折叠 隐藏此楼查看此楼 @SuppressWarnings("unchecked") public List getAllStorytell(Long use ...

  10. oracle表中增加字段 sql语句,ORACLE中通过SQL语句(alter table)来增加、删除、修改字段...

    1.添加字段: alter table  表名  add (字段  字段类型)  [ default  '输入默认值']  [null/not null]  ; 2.添加备注: comment on ...

最新文章

  1. 主流WAF架构分析与探索
  2. java word openoffice_java 使用openoffice 转换文档,成.pdf,实现在线预览效果
  3. leetcode算法题--二维区域和检索 - 矩阵不可变
  4. 【知识图谱系列】人工智能经典图谱有哪些?
  5. 新建网站与新建Asp.Net+Web+应用程序的区别
  6. 基于SSD的Kafka应用层缓存架构设计与实现
  7. Linux下自动化测试环境的搭建
  8. 热插拔服务器电源维修,无需关停系统即可热插拔,TE Connectivity推出滑轨电源连接器...
  9. 【Java】java代理 静态代理 动态代理 proxy
  10. 电脑黑屏的原因有哪些
  11. 机器阅读理解(MRC)和问答(QA)在信息抽取中的应用
  12. 2020 cr节目源_2020/8月最新IPTV M3U8直播源分享
  13. 【云原生】DevOps 新纪元 | 史前的惨淡现实
  14. excel怎么输入度分秒,并转换为可编辑文本格式
  15. 洛谷 P4578 [FJOI2018] Upc6605 福建OI2018 所罗门王的宝藏
  16. C语言程序设计第五次作业
  17. 重装系统后需要做什么?
  18. win10 机械硬盘 开机速度缓慢的原因排查与优化
  19. 南航计算机科学与技术学院院徽,南京航空航天大学计算机科学与技术学院简介...
  20. FALL_20_NOTE EDAV「Exploratory Data Analysis and Visualization」图像可视化

热门文章

  1. mysql注入内置函数_PHP面试之mysql内置函数,xss漏洞,sql注入
  2. MFC通过窗口名字(caption的内容)查找窗口,并将其隐藏或者置顶显示
  3. Summed-Area Variance Soft Shadow Mapping(SAVSM):二
  4. requests模块爬取糗事百科用xpath解析
  5. unity3d 使用GL 方式画线
  6. 7.Appium 安卓自动化(Package与Activity)
  7. 文件描述符file descriptor与inode的相关知识
  8. final/finalize/finally的区别
  9. 十大垃圾食品中八种可致脂肪肝
  10. dos批处理命令详解(转)