Javascript ES6中导致错误的类的实例化和排序

Javascript ES6中导致错误的类的实例化和排序,javascript,ecmascript-6,gulp,Javascript,Ecmascript 6,Gulp,我在游戏中使用ES6类。我有两个问题: 问题1)我正在为BattleMode和ExplorationMode实例化两个单例类,并传入一个初始参数type 即使我是console.loggingexplorationMode(一个explorationMode的实例),它也会显示类战斗模式,类型为exploration。为什么会这样 问题2)我正在使用gulp和babel将脚本编译成main.js。上面的ExplorationMode和BattleMode都继承自父类Mode。Gulp运行mode

我在游戏中使用ES6类。我有两个问题:

问题1)我正在为
BattleMode
ExplorationMode
实例化两个单例类,并传入一个初始参数
type

即使我是console.logging
explorationMode
(一个
explorationMode
的实例),它也会显示
类战斗模式,类型为
exploration
。为什么会这样

问题2)我正在使用gulp和
babel
将脚本编译成
main.js
。上面的
ExplorationMode
BattleMode
都继承自父类
Mode
。Gulp运行
modes/
文件夹,并按顺序将它们添加到
main.js

显然,ES6关心JavaScript的顺序,这意味着如果
BattleMode
Mode
的子级,那么它会说找不到父级

未捕获的TypeError:超级表达式必须为null或函数,而不是未定义的

这将强制重命名
mode.js
,使其在文件夹顺序中首先出现。那真是太骇人听闻了。如果我预编了
A_模式
,错误就会消失

除了重命名或指定gulp中的每个父对象出现在其子对象之前,还有更好的解决方案吗

否则,我可以只使用对象:

var Mode = Mode || {};

Mode.BattleMode = Mode.BattleMode || {
    doThing : function () {
         ...

问题1:

class StateManager {
    constructor(type) {
        if (!stateManagerInstance) {
            stateManagerInstance = this;
        }
        this.type = type;
        const battleMode = new BattleMode('battle');
        const explorationMode = new ExplorationMode('exploration');

        console.log('MODE: ', explorationMode); // Wrong
        ...
控制台输出:

模式:类战斗模式{类型:“探索”,屏幕状态:“战斗”}

模式:

探索模式:

/*
  Define as Singleton
 */
let explorationInstance = null;

class ExplorationMode extends Mode {
    constructor(type) {
        super(type);

    this.type = type;

        if (!explorationInstance) {
            explorationInstance = this;
        }

    this.screenState = '';

        return explorationInstance;
  }
作战模式:

/*
  Define as Singleton
 */
let battleInstance = null;

class BattleMode extends Mode {
    constructor(type) {
        super(type);

    this.type = type;

        if (!battleInstance) {
            battleInstance = this;
        }

    this.screenState = '';

        return battleInstance;
  }

问题2:

大口喝:


这就是为什么单例可以是反模式的一个例子。它提供了额外的复杂性,但没有真正的好处。子类甚至不能从继承中受益

由于
作战模式
探索模式
都继承自
模式
模式
构造函数首先被评估。第一个实例保存到
modeInstance
。由于首先实例化了
BattleMode
,因此无论在子构造函数中发生什么,它都是
BattleMode
的一个实例


在这种情况下,以及其他许多单例类都应该用普通对象替换。

为什么文件系统顺序决定文件的执行顺序?情况不应该如此。这确实是一种黑客行为,您的JS文件执行顺序应该与文件系统中的顺序无关。也许您需要一个按正确顺序导入文件的容器文件,您只需运行容器文件。单例是不了解对象的人的发明。“我正在实例化两个单例类”-@Ele用例主要局限于只有
结构的语言。JS不是这些语言中的一种。“除了重命名,还有更好的解决方案吗?”-当然有。始终使用
import
明确声明模块之间的依赖关系。
/*
  Define as Singleton
 */
let battleInstance = null;

class BattleMode extends Mode {
    constructor(type) {
        super(type);

    this.type = type;

        if (!battleInstance) {
            battleInstance = this;
        }

    this.screenState = '';

        return battleInstance;
  }
gulp.task('build-dev', function() {
    gulp.run('scripts');
  gulp.watch('js/**/*.js', function() {
    gulp.run('scripts');
  });
});

gulp.task('scripts', function() {
    return gulp.src([
            'js/**/*.js',
        ])
        .pipe(babel({
            presets: ['es2015']
        }))
        .pipe(concatJs('main.js'))
        .pipe(gulp.dest('build/js'));
});