Javascript Weakmap引用在继承中丢失

Javascript Weakmap引用在继承中丢失,javascript,class,ecmascript-6,private-members,Javascript,Class,Ecmascript 6,Private Members,我在使用javascript处理类的私有成员时遇到了一个问题,我自己无法解决这个问题 "use strict"; var privateData = new WeakMap(); class Fruit{ constructor(name){ privateData.set(this, {name: name}); } name(){ return privateData.get(this).name; } } class

我在使用javascript处理类的私有成员时遇到了一个问题,我自己无法解决这个问题

"use strict";
var privateData = new WeakMap();


class Fruit{
    constructor(name){
        privateData.set(this, {name: name});
    }

    name(){
        return privateData.get(this).name;
    }
}

class Orange extends Fruit{
    constructor(){
        super("Orange");
    privateData.set(this, {color: "blue"});
    }

    color(){
        return privateData.get(this).color;
    }
}

var fruit = new Fruit("Apple");
alert(fruit.name());
var orange = new Orange();
alert(orange.name());
第一输出:苹果 第二个输出:未定义

我的猜测是,我正在覆盖“this”,因为如果我删除

return privateData.get(this).color;

它可以工作。

是的,对象是唯一的,并且您将使用
实例作为键两次。第二次
set
调用将覆盖第一次调用的值,并且只保留对象的
.color
属性

最简单的解决方案是为每个属性使用一个弱贴图:

var privateNames = new WeakMap();
class Fruit {
    constructor(name) {
        privateNames.set(this, name);
    }
    get name() {
        return privateNames.get(this);
    }
}

var privateColors = new WeakMap();
class Orange extends Fruit {
    constructor() {
        super("Orange");
        privateColors.set(this, "blue");
    }
    get color() {
        return privateColors.get(this);
    }
}
或者,您必须对存储的
数据
对象进行变异:

var privateData = new WeakMap();
class Fruit {
    constructor(name) {
        privateData.set(this, {name: name});
    }
    get name() {
        return privateData.get(this).name;
    }
}

class Orange extends Fruit {
    constructor() {
        super("Orange");
        privateData.get(this).color = "blue";
    }
    get color() {
        return privateData.get(this).color;
    }
}

您正在将该值更改为
{color:'blue'}
,因此访问
name
之后将返回
未定义的
。WeakMap不会神奇地合并这些值。为什么要与“私人成员”发生冲突?你几乎不需要它们。