马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。
您需要 登录 才可以下载或查看,没有账号?立即注册
×
本篇文章从性能、功能、应用场景等方面对比.NET几款JavaScript脚本引擎。
一 简介
1.1 AScript
AScript是一个开源的C#动态脚本解析实行引擎,支持自定义语法,支持扩展多种脚本语言(目前已支持C#/Python3/SQL/JavaScript/Lua五种语言),支持解释实行和编译实行两种实行模式,而且支持编译缓存,以适配不同应用场景下对性能的要求。
AScript的JavaScript语言包:AScript.Lang.JavaScript。
目前官方最新版本:
- AScript:1.7.0
- AScript.Lang.JavaScript:0.2.0
开源地址:
- gitee.com/rockey627/AScript
- github.com/rockey627/AScript
干系文章:
- 基于AScript的JavaScript脚本语言发布啦
- C#脚本引擎之AScript与DynamicExpresso对比
- C#脚本引擎之AScript与Flee对比
1.2 Jurassic
Jurassic是一个开源的托管JavaScript实行引擎,支持ECMAScript 3和ECMAScript 5的功能,将JavaScript编译为.NET字节码(CIL),而非解释实行。
目前官方最新版本:3.2.9
开源地址:github.com/paulbartrum/jurassic
1.3 Jint
Jint是一款专为.NET平台设计的JavaScript解释器,支持.NET Standard 2.0和.NET 4.6.2及以上版本。它能够在任何当代.NET平台上运行,为开发者提供了一个安全沙箱情况,以便在.NET应用程序中运行JavaScript代码。Jint不但支持将原生.NET对象和函数暴露给JavaScript代码,还支持脚本化,允许用户使用JavaScript自定义应用程序。
目前官方最新版本:4.16.1
开源地址:github.com/sebastienros/jint
二 功能
由于AScript默认脚本语言为C#,需要安装JavaScript语言包,并注册JavaScript语言:- Script.Langs.Set("js", AScript.Lang.JavaScript.JavaScriptLang.Instance);
复制代码 方式一:在ScriptContext上下文中指定js语言- 1 var script = new AScript.Script();
- 2 script.Context.Langs = new[] { "js" };
- 3 var result = script.Eval(xxx);
复制代码 方式二:在脚本中指定js语言- 1 string code = @"
- 2 @lang js
- 3 function sum(a, b) {
- 4 return a+b;
- 5 }
- 6 ";
- 7 var script = new AScript.Script();
- 8 var result = script.Eval(code);
复制代码 方式三:全局设置js为默认语言- Script.Langs.SetDefault("js");
复制代码 建议使用 方式一 或者 方式二 来实行js脚本。
2.1 解释实行
1)AScript
默认为解释实行模式:- 1 var script = new AScript.Script();
- 2 script.Context.Langs = new[] { "js" };
- 3 var result = script.Eval("5 + 6");
复制代码 2)Jurassic
不支持。
3)Jint- 1 var engine = new Jint.Engine();
- 2 var result = engine.Evaluate("5 + 6");
复制代码 2.2 编译实行
将脚本编译天生委托,再实行;编译天生委托的本钱较大,但是编译后实行快,因此如果能缓存编译天生的委托,整体性能就比较高。
1)AScript
- 1 var script = new AScript.Script();
- 2 // 可以统一设置为编译执行模式
- 3 // script.Options.CompileMode = AScript.ECompileMode.All;
- 4 script.Context.Langs = new[] { "js" };
- 5 // 或者Eval方法指定为编译执行模式
- 6 var result = script.Eval("5 + 6", AScript.ECompileMode.All);
复制代码- 1 var script = new AScript.Script();
- 2 script.Context.Langs = new[] { "js" };
- 3 var result = script.Eval("5 + 6", -1);
复制代码 Eval方法定义如下:- 1 /// <summary>
- 2 /// 计算表达式,返回结果
- 3 /// </summary>
- 4 /// <param name="expression">脚本</param>
- 5 /// <param name="cacheTime">
- 6 /// <para>缓存时长</para>
- 7 /// <para>为0表示不使用缓存(默认);</para>
- 8 /// <para>-1表示永久缓存;</para>
- 9 /// <para>大于0表示缓存时长(单位:毫秒)</para>
- 10 /// </param>
- 11 /// <param name="cacheKey">
- 12 /// 缓存key(如果为空则取表达式字符串)
- 13 /// </param>
- 14 /// <param name="cacheVersion">
- 15 /// 缓存版本号,如果版本号有变化,则重新编译并缓存
- 16 /// </param>
- 17 /// <returns></returns>
- 18 public object Eval(string expression, int cacheTime = 0, string cacheKey = null, string cacheVersion = null);
复制代码- 1 var script = new AScript.Script();
- 2 script.Context.Langs = new[] { "js" };
- 3 Expression<Func<int, bool>> lambda = script.Lambda<int, bool>("a>0 && a<10", "a");
复制代码 2)Jurassic
不支持
3)Jint- .Lambda #Lambda1<System.Func`2[System.Int32,System.Boolean]>(System.Int32 $a) {
- $a > 0 && $a < 10
- }
复制代码 2.5 扩展函数
AScript支持,Jurassic/Jint不支持。
扩展脚本语言通常会使用扩展函数、属性、构造函数等方式来支持该脚本语言的语法特性。
正常添加函数,第1个参数类型为当前要扩展的对象类型
示例:扩展字符串实例函数,toDate转时间。- 1 var script = new AScript.Script();
- 2 script.Context.Langs = new[] { "js" };
- 3 Func<int> func = script.Compile<int>("5 + 6");
- 4 var result = func();
复制代码 方法名规则:{ClassName}_{扩展方法名}
示例:扩展字符串静态函数,String.toDate转时间- 1 var engine = new Jurassic.ScriptEngine();
- 2 var result = engine.Evaluate("5 + 6");
复制代码 方法名规则:new_{ClassName}
示例:添加字符串构造函数String(Date)- 1 var total = 1;
- 2
- 3 export function sum(a, b) {
- 4 total += 1;
- 5 return a + b;
- 6 }
- 7
- 8 export function fib(a) {
- 9 if (a <= 1) return a;
- 10 return fib(a - 1) + fib(a - 2);
- 11 }
- 12
- 13 export function getTotal() {
- 14 return total;
- 15 }
- 16
- 17 /*
- 18 AScript兼容CommonJS写法,import/require互相兼容
- 19 module.exports = { sum, fib }
- 20 */
- 21 export default { sum, fib }
复制代码 2.6 自定义语法
AScript支持,Jurassic/Jint不支持。
需要实现ITokenHandler接口,稍微复杂一些,扩展脚本语言也是通过该接口来实现语法特性的,可参考干系文章:
- AScript如何实现LINQ语法
- AScript如何实现中文脚本引擎
- AScript扩展多种脚本语言
2.7 嵌入其他语言脚本
AScript支持脚本中使用@lang/@end嵌入其他语言的脚本。
示例:使用C#语言的LINQ语法过滤js数组- 1 // 全局添加模块目录
- 2 JavaScriptLang.Instance.Modules.AddDir("./modules");
- 3 // 或者当前上下文添加模块目录,只在当前范围有效,不影响全局
- 4 var script = new AScript.Script();
- 5 script.Context.Langs = new[] { "js" };
- 6 script.Context.Modules.AddDir("./modules");
复制代码 测试结果:
性能:Jint > AScript
四 总结
功能AScriptJurassicJint.NET框架net45
netstandard2.0
netstandard2.1
net6.0
net8.0netstandard2.0net46
netstandard2.0
netstandard2.1
net8.0
net10.0性能高中高ES5语法支持支持支持ES6语法部分部分支持ES2016~2021新特性部分少量支持ES2022~2025新特性不支持不支持支持解释实行支持不支持支持编译实行支持支持不支持编译缓存支持不支持不支持解构语法支持不支持支持模块功能支持不支持?异步支持不支持支持自定义语法支持不支持不支持扩展函数支持不支持不支持1)Jint语法支持最全面,性能高;
2)AScript应用场景支持最全面,JavaScript语法支持也较多,性能高(解释实行大循环语句性能低,可开启编译循环语句或者改用编译实行模式来提高性能);
3)Jurassic性能中等,许多新语法不支持,比如:()=>{}、var [name,age]=['tom',25]、'5'.padStart(4, '0')等。
项目中如何选择?
1)需要全面的js语法支持,可以选择Jint
2)考虑各种应用场景,以及功能扩展,可以选择AScript
免责声明:如果侵犯了您的权益,请联系站长及时删除侵权内容,谢谢合作!qidao123.com:ToB企服之家,中国第一个企服评测及软件市场,开放入驻,技术点评得现金. |