我有一类想要简单的工厂方法的类:

class GTree{

    public static createNode(){
        return new GNode();
    }

}


这意味着我不想让使用者立即实例化GNode。

我该如何正确实施?

显然我做不到:

class GNode{
    constructor(){
        throw TypeError("This is nonsense");
    }
}


因为那样我再也无法创建节点了。
如何强制使用工厂?

最佳答案

这是比我之前的评论更简单的方案。只需在私有(但共享)范围内定义GNode类,因此这是可以从其调用构造函数的唯一位置,并且还可以重置.constructor属性,从而不会泄漏它:



const GTree = (function() {
    class GNode {
        constructor() {

        }

        someOtherMethod() {
            console.log("someOtherMethod");
        }
    }
    // reset public .constructor
    GNode.prototype.constructor = function() {
        throw new Error("Can't call GNode constructor directly");
    };

    class GTree {
        constructor() {
            this.nodes = [];
        }

        createNode() {
            let node = new GNode();
            this.nodes.push(node);
            return node;
        }

        get length() {
            return this.nodes.length;
        }
    }
    return GTree;
})();


let tree = new GTree();
let node1 = tree.createNode();
let node2 = tree.createNode();
node1.someOtherMethod();
console.log(tree.length + " nodes");

10-07 17:37