Cho phép các chương trình chính sách thực sự chạy song song, thêm hỗ trợ nhiều luồng dưới hệ thống cho chính sách JavaScript

Tác giả:Giấc mơ nhỏ, Tạo: 2023-03-02 14:19:15, Cập nhật: 2024-03-20 15:06:41

img

Cho phép các chương trình chính sách thực sự chạy song song, thêm hỗ trợ nhiều luồng dưới hệ thống cho chính sách JavaScript

Khi phát triển chính sách trên FMZ sử dụng ngôn ngữ JavaScript, vì kiến trúc chính sách được đặt ra. Nếu có kịch bản được thiết kế song song, nó được thông quaexchange.GoTuy nhiên, việc thực hiện một loạt các hoạt động nếu muốn thực sự tạo ra một chuỗi chủ đề riêng biệt là không thể thực hiện được, ví dụ như sử dụng ngôn ngữ Python.threadingTôi đã có một số người làm việc cùng với tôi.

FMZ đã nâng cấp nền tảng hệ thống dựa trên nhu cầu này. Nó cũng bổ sung hỗ trợ nhiều luồng thực sự cho ngôn ngữ JavaScript. Các tính năng chi tiết bao gồm:

  • Tạo các chủ đề đồng thời thực hiện các chức năng tùy chỉnh.
  • Các công nghệ này được sử dụng trong nhiều lĩnh vực khác nhau.
  • Các biến được lưu trữ giữa các chuỗi chia sẻ.
  • Chờ cho việc thực hiện của thread kết thúc tài nguyên thu hồi và trả về kết quả thực hiện.
  • Các nhà nghiên cứu cho biết: "Điều này có nghĩa là các nhà nghiên cứu đã tìm thấy một số nguyên nhân cho việc này.
  • Nhận ID chuỗi hiện tại trong hàm thực thi chuỗi đồng thời.

Sau đây là những đoạn văn nhỏ để giúp bạn hiểu từng chức năng một cách chi tiết.

Tạo các hàm tùy chỉnh để thực hiện cùng một lúc

__ThreadCác hàm có thể tạo ra một chuỗi và thực hiện một hàm đồng thời. Ví dụ: cần tạo một hàm đồng thời.func1func1Chúng ta có thể làm cho nó tăng từ 0 lên 9, để xem quá trình tăng dần này, trong hàm func1 sử dụng vòng lặp for để tạm dừng mỗi lần (chức năng ngủ được sử dụng để ngủ một số millisecond).

function func1(sleepMilliseconds) {
    var sum = 0 
    for (var i = 0 ; i < 10 ; i++) {
        sum += i 
        Sleep(sleepMilliseconds)
        Log("sum:", sum)
    }
    
    return sum
}

function main() {
    // 使用__Thread函数并发创建一个线程,参数200即为func1函数的参数,
    // 如果func1函数有多个参数,这里就具体传对应的参数
    var thread1Id = __Thread(func1, 200)
    
    // 这里需要等待线程Id为thread1Id的线程执行结果,否则main函数执行完就直接释放所有线程
    var ret = __threadJoin(thread1Id)
    Log("ret:", ret)
}

Trong trường hợp thực tế, chúng ta có thể thực hiện các yêu cầu HTTP cùng một lúc như sau:

function main() {
    let threads = [
        "https://www.baidu.com",
        "https://www.163.com"
    ].map(function(url) {
        return __Thread(function(url) {
            Log("GET", url)
            return HttpQuery(url)
        }, url)
    })
    threads.forEach(function(tid) {
        Log(__threadJoin(tid))
    })
}

Chờ cho việc thực hiện của chủ đề kết thúc tài nguyên thu hồi và trả về kết quả thực thi

Trong ví dụ trên, chúng ta đã sử dụng cuối cùng trong hàm main.__threadJoinChức năng chờ đợi các chuỗi đồng thời được thực hiện, biếnretNhận__threadJoinGiá trị trả về của hàm, chúng ta in giá trị trả lại này để quan sát kết quả cụ thể của việc thực hiện chuỗi đồng thời này.

// id:线程ID,terminated:是否被强制停止,elapsed:耗时(纳秒),ret:线程执行函数的返回值
ret: {"id":1,"terminated":false,"elapsed":2004884301,"ret":45}

Việc buộc phải kết thúc các đường dây và tái chế tài nguyên

function func1(sleepMilliseconds) {
    var sum = 0 
    for (var i = 0 ; i < 10 ; i++) {
        sum += i 
        Sleep(sleepMilliseconds)
        Log("sum:", sum)
    }
    
    return sum
}

function main() {
    var thread1Id = __Thread(func1, 200)
    Sleep(1000)
    retThreadTerminate = __threadTerminate(thread1Id)
    Log(retThreadTerminate)   // true
}

Hoặc ví dụ như ở đây, sau khi tạo một thread, bạn có thể ép kết thúc việc thực hiện nó sau khi chờ 1 giây.

Truyền thông giữa các dây

Thông tin liên lạc giữa các dây chủ yếu được sử dụng__threadPostMessageChức năng và__threadPeekMessageCác hàm. Chúng ta hãy xem một ví dụ đơn giản:

function func1() {
    var id = __threadId()
    while (true) {
        var postMsg = "来自id:" + id + "的线程函数func1的消息"
        __threadPostMessage(0, postMsg)              // 发送消息到主线程
        var peekMsg = __threadPeekMessage()         // 接收来自其它线程的消息
        Log(peekMsg)
        Sleep(5000)
    }
}

function main() {
    var threadId = __Thread(func1)
    
    while (true) {
        var postMsg = "来自主线程的main函数的消息"
        __threadPostMessage(threadId, postMsg)
        var peekMsg = __threadPeekMessage()
        Log(peekMsg, "#FF0000")                     // #FF0000 , 设置日志为红色用于区分
        Sleep(5000)
    }
}

__threadPostMessageChức năng được sử dụng để gửi tin nhắn đến một chuỗi, tham số đầu tiên là ID cụ thể của chuỗi được gửi đến, tham số thứ hai là tin nhắn được gửi, có thể là chuỗi, giá trị số, mảng, đối tượng JSON, v.v.

__threadPeekMessageChức năng này được sử dụng để nghe lén các thông điệp được gửi bởi một chuỗi, có thể đặt thời gian trễ (milliseconds) hoặc được thiết lập là 0 để chặn, tiếp tục nghe lén cho đến khi có tin nhắn được trả về.

Tất nhiên, ngoài việc liên lạc giữa các đường dây song song và đường dây chính, các đường dây song song cũng có thể liên lạc trực tiếp với nhau.

Nhận ID chủ đề hiện tại trong hàm thực thi chuỗi đồng thời

Trong ví dụ trên, chúng ta sử dụngvar id = __threadId()__threadId()Chức năng có thể lấy ID của thread hiện tại.

Các biến được lưu trữ giữa các chuỗi được chia sẻ

Ngoài việc giao tiếp giữa các chuỗi, bạn có thể tương tác với các biến được chia sẻ.

function testFunc() {
    __threadSetData(0, "testFunc", 100)   // 储存在当前线程环境,键值对 testFunc : 100 
    Log("testFunc执行完毕")
}

function main() {
    // threadId为1 ,创建的threadId为1的线程会先执行完,只要线程资源没有被回收,线程本地储存的变量就有效
    var testThread = __Thread(testFunc)
    
    Sleep(1000)

    // 输出 in main, get testFunc: 100
    Log("in main, get testFunc:", __threadGetData(testThread, "testFunc"))   // 取出键名为testFunc的值
}

Đây là một bản trình bày ngắn gọn về tất cả các chức năng.


Có liên quan

Thêm nữa

Dao xươngNhập mã này để chạy mẹo: Error ReferenceError: '__Thread' is not defined at main (__FILE__:5)

Dao xươngThu thập và học hỏi

Nhà phát minh định lượngTrình quản lý nâng cấp