nodejs以对象作对象的key致使value一直被覆盖

 

 

问题描述

在开发中,实现技能状态的事件监听功能时,将状态对象做为key,存入事件管理器的监听列表,以下图:函数

 

image.png

实现后,运行程序,并无报错,可是当某个事件发生时,只有一个状态被触发监听,而大多数状态在建立时,就监听了该事件,正确的表现应当是全部监听该事件的状态对象都被触发。ui

 

缘由分析

首先判断是状态实现问题,可是每一个状态都是继承AbstractState这个父类,并无从新实现父类的事件监听函数,检查父类监听代码实现,未发现问题。spa

代码检查没有发现问题,看着是正常的,但实际效果确实有问题,因而添加打印,在addEventListener以前打印监听列表,addEventListener以后也打印监听列表,对象

打印的结果显示,addEventListener以前若是监听列表为空,那么addEventListener以后会成功添加一个监听,可是若是addEventListener以前监听列表有一个监听了,那么addEventListener以后,监听列表只会剩下最新添加的那个监听!这就是问题所在了,可是为何会出现这种状况呢?为何新的对象会覆盖旧的?继承

 

将本次遇到的问题简单化成以下例子:事件

image.png

能够看到,b实际上一直只有一个key,即'[object Object]'这个字符串,变化的只是value,在JS中,建立对象时,不论以什么类型的值作Key,JS会默认调用toString()方法将该key转成字符串类型,如数字类型:开发

image.png

能够看到key 1 变成了 '1',而当key时对象时,object.toString()的结果只会等于'[object Object]',以下图:字符串

image.png

这就是上面为何b对象永远只会有一个key =  '[object Object]'的缘由,JS不支持对象使用toString()方法,即不支持对象以对象作key。it

另外,对象转字符串,JS提供JSON.Stringify()特殊方法。class

 

解决方案

鉴于上面的分析结果,若是仍是执意想要用状态对象作key的话,可使用JSON.Stringify(state),但这显得不够优雅,最后的解决方案是在每一个状态对象中,增长一个uuid属性,以该uuid做为Key,存入监听列表中。

相关文章
相关标签/搜索