2020-04-30技术入坑,js中的二进制存储及读取,work

2020-04-29  本文已影响0人  KFQ_0a90

前言

想学cesium源码,感觉自己基础太薄弱于,于是想把基础打牢,感觉自己动力不足,就像试试每天写点博客,写博客的好处还有就是自己温习使用,很多事时候当时学会的东西很快就忘掉了,如果能看到自己的思路,很快就能重新掌握起来。这也是自己想写博客的一个原因,name就由H5 先开始,慢慢进入webGL,Cesium源码的学习吧。

本文学习参考https://www.cnblogs.com/fuckgiser/p/5045234.html,更详细的学习还要读者自己摸索。

js 操作二进制

二进制数据的创建与读取

创建、 如下代码,自己写了个小例子进行二进制数据的创建与读取,只用了int32类型,其他类型类似。

js中开辟一块内存空间采用ArrayBuffer对象,实例中开辟了一个16字节的内存空间,然后用32位整形来绑定,我们知道8位是一字节,所以绑定后是一个长度为4的整形数组(目前我这么理解的)

读取、js读取二进制数据有两种方式,一是TypeArray的方式;还有DataView的方式,有的笔者说着两者一个是小家碧玉,一个是大家闺秀,我理解后发现形容的非常到位。

TypeArray,它的类型有:Int8, Uint8, Int16, Uint16, Int32, Uint32, Float32, Float64

TypeArray的构建方式如代码中TypeArray(buffer,begin,length),其中buffer就是我们的内存块,begin是读取内存的起始位置,length是创建该类型数组的长度,代码中长度设置了4,就是从buffer内存块的0位置读取int32类型的数据,读取4份,赋值给h变量,

DataVeiw

通过代码可以看到,DataView的读取方式,是传入读取位置,和类型一个一个读取数据
最后代码中的例子是两者结合使用的方式,感觉实际开发中应该是两个结合使用公有效率

    // 创建16个字节的内存
    var buffer = new ArrayBuffer(16); 
    // 用32位的类型来绑定该内存区域,32位,每个变量是4个字节
    var int32View = new Int32Array(buffer); 
    // 此时长度为4:4个int32类型,则4*4 = 16字节
    for (var i=1; i<int32View.length; i++) { 
        int32View[i-1] = i; // 对每一个int32的变量赋值
    }

    //使用TypeArray解析二进制,它的类型有:Int8, Uint8, Int16, Uint16, Int32, Uint32, Float32, Float64
    debugger
    var h = new Int32Array(buffer,0,4)[1];
    alert(h)

    //使用dataview解析二进制
    var pos = 0;
    var view = new DataView(buffer);
    var res= view.getInt32(pos,true)
    alert(res)
    pos+=Int32Array.BYTES_PER_ELEMENT;
    var res2= view.getInt32(pos,true)
    alert(res2)
    debugger
    var h2 = new Int32Array(buffer,pos,2)[0];
    alert(h2)

上面代码依次alert的值应该是:2,1,2,2

js 执行worker

worker算是js中的多线程技术,它的用法也很简单,只需向 Worker 构造函数传递需要在worker中运行的文件路径作为参数,就可以使得对应的文件运行在worker线程。Worker线程中没有 window 对象,没有 document 对象。不能操作和创建 DOM。 worker 线程和主线程只能通过消息机制来通信。下面直接给实例代码

主线程

    var worker = new Worker('doWork.js');
    worker.onmessage= function (event) { 
        console.log(event.data)
    }; 


    var worker2 = new Worker('doWork2.js');
    worker2.addEventListener('message', function(e) { //worker onmessage 事件  
        console.log('Worker said: ', e.data);
    }, false);

    worker2.postMessage('Hello World'); // 把数据传给工作者线程.

    console.log('主线程')

doWork.js

var i = 0;

function timedCount() {
    for (var j = 0, sum = 0; j < 100; j++) {
        for (var i = 0; i < 10; i++) {
            sum += i;
        }
    }
    postMessage(sum);
}

postMessage("Before computing," + new Date());
timedCount();
postMessage("After computing," + new Date());

doWork2.js

self.addEventListener('message', function (e) {
    debugger
    self.postMessage(e.data);
}, false);

主线程中创建了2个work线程,主线程与work线程通过message事件进行通信,注册好message事件,通过postMessage方法即可互相传递信息。

程序运行的输出结果如下图,可以看出主线程线执行完毕了,并不会发生堵塞: 无标题.jpg

worker也可以导入外部脚本,如下

importScripts('script.js', 'script2.js'); 

关闭worker ,在主线程中用 terminate,在 worker 线程中用 close,使用完就应该即使关闭

 worker.terminate(); // 在主线程中关闭当前 worker
self.close(); // 在 worker 中关闭自己
上一篇 下一篇

猜你喜欢

热点阅读