下面是两个代码片段 - 一个在Go中,另一个在JavaScript中 - 基本上做同样的事情。
// 转到
package main
import "fmt"
type Engine struct {
bootTimeInSecs int
}
func (e *Engine) Start() {
fmt.Printf("Engine starting in %s seconds ...", e.bootTimeInSecs)
}
type Start func()
type BenchmarkSuite struct {
workloads []string
start Start
}
func main() {
engine := Engine{10}
benchmarkSuite := BenchmarkSuite{workloads: []string{}, start: engine.Start}
benchmarkSuite.start()
}
输出
Engine starting in 10 seconds ...
// JavaScript
function Engine(bootTimeInSecs) {
this.bootTimeInSecs = bootTimeInSecs
}
Engine.prototype.constructor = Engine
Engine.prototype.Start = function() {
console.log("Engine starting in " + this.bootTimeInSecs + " seconds ...")
}
function BenchmarkSuite(workloads, start) {
this.workloads = workloads
this.start = start
}
BenchmarkSuite.prototype.constructor = BenchmarkSuite
engine = new Engine(10)
benchmarkSuite = new BenchmarkSuite([], engine.Start)
benchmarkSuite.start()
输出
Engine starting in undefined seconds ...
我知道JavaScript中的解决方法,但这不是问题。为什么JavaScript决定不保留 原始函数的执行上下文?
答案 0 :(得分:1)
在javascript中,当您将对象传递给engine
构造函数时,函数不会绑定到对象BenchmarkSuite
。
您必须将对象显式绑定到函数。 这就是你必须要做的事情
benchmarkSuite = new BenchmarkSuite([], engine.Start.bind(engine))
bind()的最简单用法是创建一个函数,无论它如何被调用,都使用特定的值调用。新JavaScript程序员的一个常见错误是从对象中提取方法,然后调用该函数并期望它将原始对象用作其对象(例如,通过在基于回调的代码中使用该方法)。然而,如果没有特别小心,原始对象通常会丢失。使用原始对象从函数创建绑定函数,巧妙地解决了这个问题
您可以参考here了解更多信息
function Engine(bootTimeInSecs) {
this.bootTimeInSecs = bootTimeInSecs
}
Engine.prototype.constructor = Engine
Engine.prototype.Start = function() {
console.log("Engine starting in " + this.bootTimeInSecs + " seconds ...")
}
function BenchmarkSuite(workloads, start) {
this.workloads = workloads
this.start = start
}
BenchmarkSuite.prototype.constructor = BenchmarkSuite
engine = new Engine(10)
benchmarkSuite = new BenchmarkSuite([], engine.Start.bind(engine))
benchmarkSuite.start()