首页 > 作文

C#表达式树Expression基础讲解

更新时间:2023-04-04 07:10:56 阅读: 评论:0

什么是表达式树

表达式树以树形数据结构表示代码,其中每一个节点都是一种表达式,比如方法调用和 x < y 这样的二元运算等。可以对表达式树中的代码进行编辑和运算。 这样能够动态修改可执行代码、在不同数据库中执行 linq 查询以及创建动态查询。 表达式树还能用于动态语言运行时 (dlr) 以提供动态语言和 .net 之间的互操作性,同时保证编译器编儿童谜语大全3到6岁写员能够发射表达式树而非 microsoft 中间语言 (msil)。 这段话是来自官网( [表达式树 (c#) | microsoft docs](表达式树 (c#) | microsoft docs) )的定义。

在 c# 中,我们可以通过 expression 的方式来手动创建表达式树,比如:

[httpget]public iactionresult expression(){    // 查询 年龄age 大于 18 的元素    expression<func<ur,bool>> expression1 = x => x.age > 18;     return ok();}

那么,x.age > 18 这一表达式,它的树状结构是这样的:

通过 visual studio 自带的查看变量或添加监视的方式,我们可以发现其中 树的根节点(nodetype)是 greaterthan,左节点(left)是 x.age,右节点(right)是 18。所以由此就可以大概画出树状结构。

最后,通过这种树状结构,c# 就可以帮我们将表达式编译成具体的 sql 执行语句。

如果想更清晰的查看表达式树的结构,可以 nuget 一个包( expressiontreetostring ),将表达式结构转换成字符串

pm> install-package zspitz.util -version 0.1.116
expression<func<ur, bool>> expression = u => u.age >= 18;var treestr = expression.tostring("object notation", "c#");// 输出为下面字符串var u = new parameterexpression {    type = typeof(ur),    isbyref = fal,    name = "u"};new expression<func<ur, bool>> {    nodetype = expressiontype.lambda,    type = typeof(func<ur, bool>),    parameters = new readonlycollection<parameterexpression> {        u    },    body = new binaryexpression {        nodetype = expressiontype.greaterthanorequal,        type = typeof(bool),        left = new memberexpression {            type = typeof(int),            expression = u,            member = typeof(ur).getproperty("age")        },        right = new constantexpression {            type = typeof(int),            value = 18        }    },    returntype = typeof(bool)}

expression 和 func 的区别

expression 存储了运算逻辑,可以将其保存成抽象语法树(ast),可以在运行时动态获取运算逻辑。func 只是存储了结果,无法保存成语法树,也无法动态获取运算逻辑。

所以,在 efcore 中,使用表达式对数据库数据进行查询中,我们应该选择 expression 而不是 func,因为使用了 func ,实际上并无法将 func 中的表达式转换成 sql,而是在将所有数据加载到内存后,在内存中在过滤 func 中的条件。

简单来说就是,此时要筛选 ur 表中年龄大于18的数据,可以有这两种写法

// 这种写法,实际生成的 sql 语句, 大概是这样的 lect * from ur as t where t.age > 18expre命运共同体作文ssion<func<ur,bool>> expression1 = x => x.age > 18;dbcontext.ur.where(expression1).tolist();// 而这种, 生成的语句是这样的 lect * from u中国一共多少个市r, 然后将 ur 表中所有数据加载到内存中后, 在进行 age > 18 的过滤func<ur, bool> func1 = x => x.age > 18;dbc健康状况填什么ontext.ur.where(func1).tolist();

通过代码创建表达式树

parameterexpressionbinaryexpressionmethodcallexpressionconstantexpression

这些类几乎都没有提供构造方法,而且所有的属性都几乎只是只读。因此我们一般不会直接创建这些类的实例,而是调用 expression 类的 parameter、makebinary、call、constant等静态方法来生成,这些静态方法我们一般称作创建表达式树的工厂方法,而属性则通过方法参数类设置。

动态将表达式:u => u.age >= 18; 通过代码构建出来

一般构建步骤:

先创建 parameterexpression接着由里到外逐步构建先左节点(left)后右节点(right)接着body节点将其拼接成 expression
public iactionr依依墟里烟esult geturbymanualexpression(){    parameterexpression parameterexpression = expression.parameter(type:typeof(ur), name: "u");    constantexpression right = expression.constant(18);    memberexpression left = expression.makememberaccess(parameterexpression, member: typeof(ur).getproperty("age"));    binaryexpression body = expression.greaterthanorequal(left, right);    expression<func<ur, bool>> expression = expression.lambda<func<ur, bool>>(body, parameters: parameterexpression);    var data = _urrvice.geturs(expression);    return ok(new    {        code = 200,        msg = "ok",        data    });}

到此这篇关于c#表达式树expression基础讲解的文章就介绍到这了。希望对大家的学习有所帮助,也希望大家多多支持www.887551.com。

本文发布于:2023-04-04 07:10:54,感谢您对本站的认可!

本文链接:https://www.wtabcd.cn/fanwen/zuowen/e2000f98ff5bc55b771e4b8411632ceb.html

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。

本文word下载地址:C#表达式树Expression基础讲解.doc

本文 PDF 下载地址:C#表达式树Expression基础讲解.pdf

标签:表达式   节点   动态   是这样
相关文章
留言与评论(共有 0 条评论)
   
验证码:
Copyright ©2019-2022 Comsenz Inc.Powered by © 专利检索| 网站地图