如何创建一个函数来创建一个函数来不断返回一个对象的键
我想创建一个函数来创建一个函数来不断返回一个对象的键,但我不确定如何编写它。如何创建一个函数来创建一个函数来不断返回一个对象的键
例如,我可以做如下:
var parent = {data: 123}
var child = {}
child.data = function() {
return parent.data
}
child.data() // 123
parent = {data: 456}
child.data() // 456
这工作得很好,但我想创建一个用于创建数据的功能,如一些功能:
var parent = {data: 123}
var child = {}
create_data_function(parent, child, "data")
child.data() // 123
parent = {data: 456}
child.data() // 456
下将不起作用,因为“from”变量被重新分配了
function create_data_function(from, to, key) {
to[key] = function() {
return from[key]
}
}
正在创建create_data_functio有可能吗? 我不确定搜索什么来寻找解决方案。
感谢您的阅读:)
让我们指的是最初的对象parent
点为对象1,并将新对象分配给parent
为对象2.
在parent
变量的值是一个对象引用,最初是一个参考对象物1时这样做:
create_data_function(parent, child, "data");
的值的parent
是REA d并传入create_data_function
。该值是对象1的参考。根本不涉及parent
变量传递到create_data_function
。它创建的功能将关闭在从create_data_function
调用创建它,这将始终包含一个参考from
参数对象1.
要创建一个函数,它你的描述,该功能必须有访问parent
变量本身。 JavaScript没有任何形式的传递参考(它允许你将一个变量的引用传递给一个函数),所以我们必须找到另一种方式来给create_data_function
访问parent
变量。
最简单的方法是确保create_data_function
关闭了parent
,通过在访问parent
一个范围界定它,就像这样:
var parent = {data: 123};
var child = {};
create_data_function(child, "data");
// ^---- Note we aren't passing in `parent`
snippet.log(child.data()); // 123
parent = {data: 456};
snippet.log(child.data()); // 456
function create_data_function(to, key) {
// Note no `from` ------------^
to[key] = function() {
return parent[key];
// ^^^^^^------ instead we use `parent` directly
};
};
<!-- Script provides the `snippet` object, see http://meta.stackexchange.com/a/242144/134069 -->
<script src="//tjcrowder.github.io/simple-snippets-console/snippet.js"></script>
这是可能的,因为create_data_function
在可以直接使用parent
变量的地方创建。
但是如果不是?我们希望通过传递一个存取功能解决它为create_data_function
,像这样:
// Note that because `parent` is a local within `test`,
// and `create_data_function` isn't, `create_data_function`
// doesn't have direct access to `parent` (it doesn't *close over*
// `parent`).
function test() {
var parent = {data: 123};
var child = {};
create_data_function(function() { // So we give it a function to call
return parent; // to get `parent`'s current value
}, child, "data");
snippet.log(child.data()); // 123
parent = {data: 456};
snippet.log(child.data()); // 456
}
function create_data_function(fromAccessor, to, key) {
// Accept the accessor -------^
to[key] = function() {
return fromAccessor()[key];
// Call it ----^^^^^^^^^^^^^^
};
};
test();
<!-- Script provides the `snippet` object, see http://meta.stackexchange.com/a/242144/134069 -->
<script src="//tjcrowder.github.io/simple-snippets-console/snippet.js"></script>
这与ES2015语法有点不太笨重,因为新箭头功能:
// THIS EXAMPLE REQUIRES ES2015 SUPPORT IN YOUR BROWSER
function test() {
var parent = {data: 123};
var child = {};
create_data_function(() => parent, child, "data");
// The accessor func ^^^^^^^^^^^^
snippet.log(child.data()); // 123
parent = {data: 456};
snippet.log(child.data()); // 456
}
function create_data_function(fromAccessor, to, key) {
to[key] = function() {
return fromAccessor()[key];
};
};
test();
<!-- Script provides the `snippet` object, see http://meta.stackexchange.com/a/242144/134069 -->
<script src="//tjcrowder.github.io/simple-snippets-console/snippet.js"></script>
感谢您的答案,是的,有点笨重的JavaScript,但似乎没有办法解决这个问题,一个好主意,将函数包装在一个函数 – John
只是好奇,你认为传递上下文参数如https: //jsfiddle.net/L7stc9rd/?它正在修改当然问题中的原始函数参数,但除此之外,我认为它会工作正常吗?虽然它遇到了jsfiddle – John
上的问题@John:只有当'parent'是一个对象的属性时才起作用。这将是如果'var parent'在全局范围,但通常你想避免全局性,所以...(你的小提琴不工作,因为jsFiddle的惊人的默认包装你的代码'window.onload = function() {/ * ..你的代码在这里...... * /};',所以你的'var parent'不在全局范围内。) –
I a @ T.J.Crowder。该代码适用于我:https://jsfiddle.net/ye7onjyu/ – sheeldotme
嗨@ T.J.Crowder,谢谢你试用它,我应该创建了一个jsfiddle,对此感到抱歉。 – John
我意识到原来的例子有一个错字,我想要做的是parent = {data:456},而不是parent.data = 456,我已经为你的小提琴派上了用场了,现在https://jsfiddle.net/hf664p15/ – John