当前位置:首页 > JavaScript

js 实现同步锁

2026-02-03 03:57:01JavaScript

同步锁的概念

在JavaScript中,由于单线程和事件循环机制,传统的多线程同步锁概念并不直接适用。但通过Promise、Async/Await或共享状态管理,可以模拟类似同步锁的行为,控制异步代码的执行顺序。

使用Promise实现同步锁

通过Promise链和闭包维护锁状态,确保异步操作按顺序执行:

class Lock {
  constructor() {
    this._locked = false;
    this._queue = [];
  }

  acquire() {
    return new Promise(resolve => {
      if (!this._locked) {
        this._locked = true;
        resolve();
      } else {
        this._queue.push(resolve);
      }
    });
  }

  release() {
    if (this._queue.length > 0) {
      const nextResolve = this._queue.shift();
      nextResolve();
    } else {
      this._locked = false;
    }
  }
}

// 使用示例
const lock = new Lock();
async function criticalSection() {
  await lock.acquire();
  try {
    // 临界区代码
  } finally {
    lock.release();
  }
}

使用Async/Await与标志位

通过标志位和循环等待实现简单锁:

js 实现同步锁

let locked = false;

async function withLock(fn) {
  while (locked) {
    await new Promise(resolve => setTimeout(resolve, 10));
  }
  locked = true;
  try {
    return await fn();
  } finally {
    locked = false;
  }
}

// 使用示例
await withLock(async () => {
  // 临界区代码
});

使用Atomics实现低级锁(SharedArrayBuffer环境)

在Web Worker共享内存场景下,可使用Atomics API:

const lockBuffer = new SharedArrayBuffer(4);
const lockView = new Int32Array(lockBuffer);

async function acquireLock() {
  while (Atomics.wait(lockView, 0, 1) !== 'ok') {
    // 等待锁释放
  }
  Atomics.store(lockView, 0, 1); // 获取锁
}

function releaseLock() {
  Atomics.store(lockView, 0, 0);
  Atomics.notify(lockView, 0, 1); // 通知等待线程
}

注意事项

  • 浏览器环境中优先使用Promise或Async/Await方案
  • Node.js可通过async-mutex等库直接实现
  • 避免死锁:确保锁最终被释放,使用try-finally块
  • 考虑锁粒度:过细影响性能,过粗降低并发性

第三方库推荐

  1. async-mutex:支持互斥锁和信号量

    js 实现同步锁

    npm install async-mutex
    const { Mutex } = require('async-mutex');
    const mutex = new Mutex();
    
    async function run() {
      const release = await mutex.acquire();
      try {
        // 临界区
      } finally {
        release();
      }
    }
  2. proper-lockfile:适用于文件操作场景

  3. redis-lock:分布式环境下的Redis锁实现

标签: js
分享给朋友:

相关文章

js实现图片上传

js实现图片上传

图片上传的基本实现 使用HTML的<input type="file">元素配合JavaScript的File API可以实现图片上传功能。HTML部分需要创建一个文件选择输入框和一个用于…

js实现图表

js实现图表

在JavaScript中实现图表通常使用流行的图表库,以下是几种常见的方法和工具: 使用Chart.js Chart.js是一个简单灵活的库,适合快速生成响应式图表。安装方式包括CDN引入或npm安…

js 实现链表

js 实现链表

链表的基本概念 链表是一种线性数据结构,由一系列节点组成,每个节点包含数据和指向下一个节点的指针。与数组不同,链表在内存中是非连续存储的,插入和删除操作效率较高。 链表的实现 在 JavaScrip…

js实现自举

js实现自举

实现 JavaScript 自举的方法 JavaScript 自举(Bootstrap)通常指通过 JavaScript 动态加载自身或依赖的脚本,实现运行时环境的初始化或扩展。以下是几种常见实现方式…

js实现图片

js实现图片

图片加载与显示 在JavaScript中,可以通过Image对象动态加载图片。创建实例后设置src属性触发加载,通过onload回调处理加载完成后的操作: const img = new Ima…

js实现复选框

js实现复选框

实现复选框的基本方法 使用HTML的<input type="checkbox">元素创建复选框,并通过JavaScript监听其状态变化。 <input type="checkb…