前端:QuickJS到底能干什么

640?wx_fmt=png


QuickJS 是一个轻量且可嵌入的 JavaScript 引擎,它支持 ES2019 规范,包括 ES module、异步生成器以及 proxies。除此之外,还支持可选的数学扩展,例如大整数(BigInt)、大浮点数(BigFloat)和运算符重载。


主要特点:

  • 轻量而且易于嵌入:只需几个C文件,没有外部依赖,一个x86下的简单的“hello world”程序只要180 KiB。

  • 具有极低启动时间的快速解释器:在一台单核的台式PC上,大约在100秒内运行ECMAScript 测试套件1 56000次。运行时实例的完整生命周期在不到300微秒的时间内完成。

  • 几乎完整实现ES2019支持,包括:模块,异步生成器和和完整Annex B支持 (传统的Web兼容性)。

  • 通过100%的ECMAScript Test Suite测试。

  • 可以将Javascript源编译为没有外部依赖的可执行文件。

  • 使用引用计数(以减少内存使用并具有确定性行为)的垃圾收集与循环删除。

  • 数学扩展:BigInt, BigFloat, 运算符重载, bigint模式, math模式.

  • 在Javascript中实现的具有上下文着色和完成的命令行解释器。

  • 采用C包装库构建的内置标准库。

用途:后端服务、嵌入式应用、命令工具等等。

示例:

QuickJS/bjson.c:一个可读取可写入JSON文件的插件

#include "quickjs-libc.h"
#include "cutils.h"

static JSValue js_bjson_read(JSContext *ctx, JSValueConst this_val,
int argc, JSValueConst *argv)
{
uint8_t *buf;
uint64_t pos, len;
JSValue obj;
size_t size;

if (JS_ToIndex(ctx, &pos, argv[1]))
return JS_EXCEPTION;
if (JS_ToIndex(ctx, &len, argv[2]))
return JS_EXCEPTION;
buf = JS_GetArrayBuffer(ctx, &size, argv[0]);
if (!buf)
return JS_EXCEPTION;
if (pos + len > size)
return JS_ThrowRangeError(ctx, "array buffer overflow");
obj = JS_ReadObject(ctx, buf + pos, len, 0);
return obj;
}

static JSValue js_bjson_write(JSContext *ctx, JSValueConst this_val,
int argc, JSValueConst *argv)
{
size_t len;
uint8_t *buf;
JSValue array;

buf = JS_WriteObject(ctx, &len, argv[0], 0);
if (!buf)
return JS_EXCEPTION;
array = JS_NewArrayBufferCopy(ctx, buf, len);
js_free(ctx, buf);
return array;
}

static const JSCFunctionListEntry js_bjson_funcs[] = {
JS_CFUNC_DEF("read", 3, js_bjson_read ),
JS_CFUNC_DEF("write", 1, js_bjson_write ),
};

static int js_bjson_init(JSContext *ctx, JSModuleDef *m)
{
return JS_SetModuleExportList(ctx, m, js_bjson_funcs,
countof(js_bjson_funcs));
}

#ifdef JS_SHARED_LIBRARY
#define JS_INIT_MODULE js_init_module
#else
#define JS_INIT_MODULE js_init_module_bjson
#endif

JSModuleDef *JS_INIT_MODULE(JSContext *ctx, const char *module_name)
{
JSModuleDef *m;
m = JS_NewCModule(ctx, module_name, js_bjson_init);
if (!m)
return NULL;
JS_AddModuleExportList(ctx, m, js_bjson_funcs, countof(js_bjson_funcs));
return m;
}


QuickJS/tests/test_bjson.js:测试代码

import * as bjson from "../bjson.so";

function assert(b, str)
{
if (b) {
return;
} else {
throw Error("assertion failed: " + str);
}
}

function toHex(a)
{
var i, s = "", tab, v;
tab = new Uint8Array(a);
for(i = 0; i < tab.length; i++) {
v = tab[i].toString(16);
if (v.length < 2)
v = "0" + v;
if (i !== 0)
s += " ";
s += v;
}
return s;
}

function toStr(a)
{
var s, i, props, prop;

switch(typeof(a)) {
case "object":
if (a === null)
return "null";
if (Array.isArray(a)) {
s = "[";
for(i = 0; i < a.length; i++) {
if (i != 0)
s += ",";
s += toStr(a[i]);
}
s += "]";
} else {
props = Object.keys(a);
s = "{";
for(i = 0; i < props.length; i++) {
if (i != 0)
s += ",";
prop = props[i];
s += prop + ":" + toStr(a[prop]);
}
s += "}";
}
return s;
case "undefined":
return "undefined";
case "string":
return a.__quote();
case "number":
case "bigfloat":
if (a == 0 && 1 / a < 0)
return "-0";
else
return a.toString();
break;
default:
return a.toString();
}
}

function bjson_test(a)
{
var buf, r, a_str, r_str;
a_str = toStr(a);
buf = bjson.write(a);
if (0) {
print(a_str, "->", toHex(buf));
}
r = bjson.read(buf, 0, buf.byteLength);
r_str = toStr(r);
if (a_str != r_str) {
print(a_str);
print(r_str);
assert(false);
}
}

function bjson_test_all()
{
var obj;

bjson_test({x:1, y:2, if:3});
bjson_test([1, 2, 3]);
bjson_test([1.0, "aa", true, false, undefined, null, NaN, -Infinity, -0.0]);
if (typeof BigInt !== "undefined") {
bjson_test([BigInt("1"), -BigInt("0x123456789"),
BigInt("0x123456789abcdef123456789abcdef")]);
}
if (typeof BigFloat !== "undefined") {
BigFloatEnv.setPrec(function () {
bjson_test([BigFloat("0.1"), BigFloat("-1e30"), BigFloat("0"),
BigFloat("-0"), BigFloat("Infinity"), BigFloat("-Infinity"),
0.0 / BigFloat("0"), BigFloat.MAX_VALUE,
BigFloat.MIN_VALUE]);
}, 113, 15);
}

/* tested with a circular reference */
obj = {};
obj.x = obj;
try {
bjson.write(obj);
assert(false);
} catch(e) {
assert(e instanceof TypeError);
}
}

bjson_test_all();


本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/271959.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

随机存取是什么意思_手机小白必看!12GB+256GB,同样是GB,它们到底有什么不同?...

导语本文适合对电子产品有深度兴趣的小白&#xff0c;详细介绍了信息世界的数据计量单位&#xff0c;以及RAM与ROM的&#xff0c;文末给出了购机建议&#xff0c;建议不了解手机或者说半懂的同学观看。看完如果您觉得还可以的话&#xff0c;点赞关注&#xff0c;给小编一个鼓励…

ES6 解构赋值的用法笔记

1、概念&#xff1a;解构赋值可以理解为对赋值运算符的一种扩展。它主要针对数组或者对象进行模式匹配&#xff0c;然后对模式中的变量进行赋值。2、特性&#xff1a;采用ES6解构赋值的方式可以代码的可读性更高、代码书写更加简洁、清晰。3、解构模型&#xff1a;分为解构源、…

收集12个经典的程序员段子

1bug 跟蚊子的相似之处&#xff1a;1、不知道藏在哪里。2、不知道有多少。3、总是在你即将睡觉休息的时候出现。2A&#xff1a;最近在看《一拳超人》&#xff0c;觉得咱们程序猿跟埼玉老师有点像啊&#xff01;B&#xff1a;哪里像了&#xff1f;A&#xff1a;越秃越强&#xf…

2020mysql安装教程_2020MySQL安装图文教程

MySQL安装图文教程(Windows10)1、MySQL下载可以去MySQL官网下载&#xff0c;或者在我提供的百度云链接下载。官网下载网速较慢&#xff0c;我从官网下载了将近四个小时&#xff0c;然后把下载好的放在了百度网盘&#xff0c;需要的而已自取。MySQL官网地址&#xff1a;MySQL官网…

说一下 runnable 和 callable 有什么区别?

主要区别 Runnable 接口 run 方法无返回值&#xff1b;Callable 接口 call 方法有返回值&#xff0c;支持泛型Runnable 接口 run 方法只能抛出运行时异常&#xff0c;且无法捕获处理&#xff1b;Callable 接口 call 方法允许抛出异常&#xff0c;可以获取异常信息 Runnable Ca…

几种常见的光纤接头(ST,SC,LC,FC)以及PC、APC和UPC的区别

一、几种常见的光纤接头(ST,SC,LC,FC)FC型光纤连接器&#xff1a;外部加强方式是采用金属套&#xff0c;紧固方式为螺丝扣。 一般在ODF侧采用(配线架上用的最多)SC型光纤连接器&#xff1a;连接GBIC光模块或普通光纤收发器的连接器&#xff0c;它的外壳呈矩形&#xff0c;紧固方…

python开发客户端_python用700行代码实现http客户端

本文用python在TCP的基础上实现一个HTTP客户端, 该客户端能够复用TCP连接, 使用HTTP1.1协议.一. 创建HTTP请求HTTP是基于TCP连接的, 它的请求报文格式如下:因此, 我们只需要创建一个到服务器的TCP连接, 然后按照上面的格式写好报文并发给服务器, 就实现了一个HTTP请求.1. HTTPC…

家里网线的接法和顺序

对于网线&#xff0c;大伙都熟悉吧&#xff0c;它是电脑连接时必不可少的一种设备。但是许多网友却和小编一样&#xff0c;不知道如何连接网线&#xff0c;导致电脑无法上网&#xff0c;下面我们就来详细介绍一下&#xff1a;如何接网线以及家里网线的接法和顺序&#xff1f;希…

String str=Hello 与 String str=new String(“Hello”)一样吗?

为什么会输出上边的结果呢&#xff0c;String x "Hello" 的方式&#xff0c;Java 虚拟机会将其分配到常量池中&#xff0c;而常量池中没有重复的元素&#xff0c;比如当执行“Hello”时&#xff0c;java虚拟机会先在常量池中检索是否已经有“Hello”,如果有那么就将…

盘点程序员最喜欢的15个网站

程序员作为一个经常和互联网打交道的人群&#xff0c;他们喜欢浏览哪些网站呢&#xff1f;不爱敲代码的程序猿整理了以下网站供大家参考&#xff0c;排名不分先后&#xff1a; 0. Google https://google.com 这个不用多说了吧。 1.GitHub 开发者最最最重要的网站&#xff1a;h…

python序列化和反序列化_Python 中 json 数据序列化和反序列化

1.Json 定义定义&#xff1a;JSON(JavaScript Object Notation, JS 对象简谱) 是一种轻量级的数据交换格式。JSON 的数据格式其实就是 python 里面的字典格式&#xff0c;里面可以包含方括号括起来的数组&#xff0c;也就是python里面的列表。特点&#xff1a;简洁和清晰的层次…

硬件:RS232基础知识笔记

个人计算机上的通讯接口之一&#xff0c;由电子工业协会&#xff08;ElectronicIndustriesAssociation&#xff0c;EIA&#xff09;所制定的异步传输标准接口。通常RS-232接口以9个引脚&#xff08;DB-9&#xff09;或是25个引脚&#xff08;DB-25&#xff09;的型态出现&#…

硬件:RS422基础知识笔记

❤️作者主页&#xff1a;IT技术分享社区 ❤️作者简介&#xff1a;大家好,我是IT技术分享社区的博主&#xff0c;从事C#、Java开发九年&#xff0c;对数据库、C#、Java、前端、运维、电脑技巧等经验丰富。 ❤️个人荣誉&#xff1a; 数据库领域优质创作者&#x1f3c6;&#x…

硬件:串口握手基础知识笔记

RS-232通行方式允许简单连接三线&#xff1a;Tx、Rx和地线。但是对于数据传输&#xff0c;双方必须对数据定时采用使用相同的波特率。尽管这种方法对于大多数应用已经足够&#xff0c;但是对于接收方过载的情况这种使用受到限制。这时需要串口的握手功能。在这一部分&#xff0…

python高斯求和_二、算法分析

一、什么是算法分析程序和算法的区别&#xff1a;算法是对问题解决的分步描述程序是采用某种编程语言实现的算法&#xff0c;同一个算法通过不同的程序员采用不同的编程语言&#xff0c;能产生很多程序算法分析的概念&#xff1a;算法分析主要就是从计算资源消耗的角度来评判和…

硬件:交换机基础知识

1、交换机的概念交换机&#xff08;Switch&#xff09;意为“开关”&#xff0c;是一种用于电&#xff08;光&#xff09;信号转发的网络设备。它可以为接入交换机的任意两个网络节点提供独享的电信号通路。最常见的交换机是以太网交换机。其他常见的还有电话语音交换机、光纤交…

硬件:宽带猫(光猫)的基础知识

❤️作者主页&#xff1a;IT技术分享社区 ❤️作者简介&#xff1a;大家好,我是IT技术分享社区的博主&#xff0c;从事C#、Java开发九年&#xff0c;对数据库、C#、Java、前端、运维、电脑技巧等经验丰富。 ❤️个人荣誉&#xff1a; 数据库领域优质创作者&#x1f3c6;&#x…

Sentinel介绍和Windows下安装Sentinel-dashboard

Sentinel 是什么&#xff1f; 随着微服务的流行&#xff0c;服务和服务之间的稳定性变得越来越重要。Sentinel 以流量为切入点&#xff0c;从流量控制、熔断降级、系统负载保护等多个维度保护服务的稳定性。 Sentinel 具有以下特征: 丰富的应用场景&#xff1a;Sentinel 承接…

盘点物联网常用的八种通信协议

目录 1、蓝牙 2、Zigbee 3、6LoWPAN 4、Wi-Fi 6、ModBus 7、PROFINET 8、EtherCAT 1、蓝牙 兼容的蓝牙IoT传感器非常适合需要短距离连接和低功率通信的应用。蓝牙协议的有效范围为50到100米&#xff0c;支持高达1 Mbps的数据传输速率。 最近&#xff0c;物联网开发人员已经表现…

docker安装Sentinel

1:拉取镜像&#xff1a;docker pull bladex/sentinel-dashboard 2:启动 docker run --name sentinel -d -p 8858:8858 -d bladex/sentinel-dashboard 3&#xff1a;访问 http://公网ip:8858 4&#xff1a;登录,用户名和密码都是sentinel