未定义的 NodeJS 'toUpperCase'(从打字稿生成)

NodeJS 'toUpperCase' of undefined (generated from typescript)

为什么当我从 nodejs 启动时这有效:

var a = function (name) {
        return "Hello, " + name.toUpperCase();
    };
var result = a("bob");

console.log(result)

但是这个:

var A = (function () {
    function A(msg) {
        this.msg = " ";
        this.msg = msg;
    }
    A.prototype.hello = function (name) {
        return "Hello, " + name.toUpperCase();
    };
    A.prototype.helloToBob = function (fn) {
        return fn.apply("Bob");
    };
    return A;
})();
var test = new A("some message");
var msg = test.hello("Bob1");
var msg2 = test.helloToBob(test.hello);
console.log(msg);

失败:

    return "Hello, " + name.toUpperCase();
                            ^ TypeError: Cannot call method 'toUpperCase' of undefined

?

来自 TypeScript 代码的 JS 代码 generated/compiled。(编译无误)

问题出在这行代码中。

 return fn.apply("Bob");

这里有几个问题。

  1. .apply(obj, arrayOfArguments) 的第一个参数需要是您希望在方法调用期间将 this 指针设置为的对象。

  2. .apply() 的第二个参数是参数数组,而不是单个参数。

这是一个可能的解决方案,您使用 this 作为对象并切换到 fn.call(),因为 fn.apply() 接受一个参数数组,但您只有一个参数。

改变这个:

 return fn.apply("Bob");

对此:

return fn.call(this, "Bob");

并且,所有代码一起:

var A = (function () {
    function A(msg) {
        this.msg = " ";
        this.msg = msg;
    }
    A.prototype.hello = function (name) {
        return "Hello, " + name.toUpperCase();
    };
    A.prototype.helloToBob = function (fn) {
        return fn.call(this, "Bob");
    };
    return A;
})();
var test = new A("some message");
var msg = test.hello("Bob1");
var msg2 = test.helloToBob(test.hello);
console.log(msg);

仅供参考,还有其他解决方案。您也可以这样做:

var A = (function () {
    function A(msg) {
        this.msg = " ";
        this.msg = msg;
    }
    A.prototype.hello = function (name) {
        return "Hello, " + name.toUpperCase();
    };
    A.prototype.helloToBob = function (fn) {
        return fn("Bob");
    };
    return A;
})();
var test = new A("some message");
var msg = test.hello("Bob1");
var msg2 = test.helloToBob(test.hello.bind(test));
console.log(msg);

因为您应该传递给 apply() 的第一个参数是上下文对象,所以它不是函数本身的第一个参数。请检查文档。

由于 helloToBob() 是 A 的 class 方法,我假设您打算在当前对象的上下文中调用 fn,这是您想要的吗:

A.prototype.helloToBob = function (fn) {
    return fn.apply(this, ["Bob"]);
};

// or, since you have a single static argument, use function.call instead:

A.prototype.helloToBob = function (fn) {
    return fn.call(this, "Bob");
};