当前位置:首页 > JavaScript

watch js实现

2026-03-14 03:01:11JavaScript

watch 在 JavaScript 中的实现方法

在 JavaScript 中,可以通过多种方式实现类似 watch 的功能,用于监听对象属性的变化。以下是几种常见的实现方法:

使用 Object.defineProperty

Object.defineProperty 是原生 JavaScript 提供的 API,可以用于定义对象的属性及其特性(如可枚举性、可配置性、getter 和 setter 等)。通过定义 setter,可以在属性值变化时触发回调函数。

function watch(obj, prop, callback) {
  let value = obj[prop];
  Object.defineProperty(obj, prop, {
    get() {
      return value;
    },
    set(newValue) {
      if (newValue !== value) {
        const oldValue = value;
        value = newValue;
        callback(newValue, oldValue);
      }
    },
    enumerable: true,
    configurable: true
  });
}

// 示例用法
const obj = { count: 0 };
watch(obj, 'count', (newVal, oldVal) => {
  console.log(`count changed from ${oldVal} to ${newVal}`);
});

obj.count = 1; // 输出: count changed from 0 to 1

使用 Proxy

Proxy 是 ES6 引入的功能,可以拦截对象的操作(如属性访问、赋值等)。通过 Proxy,可以更灵活地监听对象的变化。

function watch(obj, callback) {
  return new Proxy(obj, {
    set(target, prop, value, receiver) {
      const oldValue = target[prop];
      if (oldValue !== value) {
        target[prop] = value;
        callback(prop, value, oldValue);
      }
      return true;
    }
  });
}

// 示例用法
const obj = { count: 0 };
const watchedObj = watch(obj, (prop, newVal, oldVal) => {
  console.log(`${prop} changed from ${oldVal} to ${newVal}`);
});

watchedObj.count = 1; // 输出: count changed from 0 to 1

使用 MutationObserver

MutationObserver 主要用于监听 DOM 树的变化,但也可以用于监听特定元素属性的变化。适用于需要监听 DOM 属性的场景。

const targetNode = document.getElementById('target');
const config = { attributes: true, childList: true, subtree: true };

const observer = new MutationObserver((mutations) => {
  mutations.forEach((mutation) => {
    if (mutation.type === 'attributes') {
      console.log(`Attribute ${mutation.attributeName} changed`);
    }
  });
});

observer.observe(targetNode, config);

使用第三方库

许多第三方库提供了更强大的 watch 功能,例如 Vue.js 的响应式系统、MobX 等。以下是使用 Vue 的 watch 示例:

watch js实现

const vm = new Vue({
  data: { count: 0 },
  watch: {
    count(newVal, oldVal) {
      console.log(`count changed from ${oldVal} to ${newVal}`);
    }
  }
});

vm.count = 1; // 输出: count changed from 0 to 1

注意事项

  1. 性能影响:使用 Object.definePropertyProxy 可能会对性能产生轻微影响,尤其是在频繁修改属性的场景中。
  2. 兼容性Proxy 是 ES6 特性,不支持旧版浏览器(如 IE11)。Object.defineProperty 的兼容性较好,但无法监听新增属性。
  3. 深层监听:如果需要监听嵌套对象的属性变化,需要递归地为每个属性设置监听。

以上方法可以根据具体需求选择使用。

标签: watchjs
分享给朋友:

相关文章

js实现

js实现

实现 JavaScript 功能的方法 在 JavaScript 中实现特定功能通常涉及多个步骤。以下是常见的实现方法: 基础语法和变量声明 使用 let 或 const 声明变量: let co…

js实现乘

js实现乘

JavaScript 实现乘法运算 在 JavaScript 中实现乘法运算可以通过多种方式完成,包括基本运算符、函数封装以及高级算法(如大数乘法)。以下是几种常见方法: 使用基本乘法运算符 Jav…

js实现求导

js实现求导

实现数值求导的方法 在JavaScript中实现求导通常采用数值方法,因为JavaScript不是符号计算语言。以下是常见的数值微分方法: 中心差分法 中心差分法提供较高精度的导数近似:…

js实现自举

js实现自举

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

js实现吸色

js实现吸色

使用Canvas实现吸色功能 通过Canvas的getImageData方法获取像素颜色数据。创建一个Canvas元素,将目标图像绘制到Canvas上,通过鼠标事件获取坐标对应的颜色值。 c…

js 实现跳转

js 实现跳转

使用 window.location.href 进行跳转 通过修改 window.location.href 可以跳转到指定 URL,浏览器会加载新页面: window.location.hre…