变量在第二次被引用时会丢失值
Variable loses value when referenced a second time
我有一些Ajax,它从数据库中获取信息并将其存储在一个名为targetVocab
的数组中。此信息用于在调用setVocab()时设置vocab
的值。这在第一次运行时很好,但当再次播放按钮被按下,第二次调用setVocab时,它就不起作用了。第二次出现targetVocab为空。这是我的简化脚本。。。
var targetVocab;
var vocab;
var request = new goog.net.XhrIo();
goog.events.listen(request, "complete", function(){
if (request.isSuccess()) {
response = request.getResponseJson();
targetVocab = response['targetVocab'];
setVocab(targetVocab);
}
});
request.send("load_vocab.php");
var setVocab = function(targetVocab) {
vocab = targetVocab;
}
var getVocab = function() {
return vocab;
}
goog.events.listen(playAgainButton, ['mousedown', 'touchstart'], function(e) {
getVocab();
});
更新:我已经意识到,无论我对vocab
做什么,都同样适用于targetVocab
。我最初的想法是,我可以在整个应用程序中拼接vocab
中的元素,然后通过再次将vocab
设置为targetVocab
将其重置为原始状态。有没有办法将vocab
设置为等于targetVocab
,而不以这种方式连接两个?
您需要以不同的方式定义函数setVocab。
我刚刚意识到的第二件事是:你应该写两个函数——一个set函数和一个GET函数——这样就不会再拼接了。
例如
function setVocab(targetVocab){
vocab = targetVocab;
}
通过这种方式,您可以确保将targetVocab作为变量真正传递给它。现在GET函数相应地:
function getVocab(){
return vocab;
}
或者将其放入一个(不推荐)中
function setVocab(targetVocab){
if(targetVocab!=""){
vocab = targetVocab;
}else{
return vocab;
}
}
现在,根据您已经实现的内容,调用
goog.events.listen(playAgainButton, ['mousedown', 'touchstart'], function(e) {
getVocab();
});
或者如果你实现了"不推荐"的代码,那么就使用这个
goog.events.listen(playAgainButton, ['mousedown', 'touchstart'], function(e) {
setVocab("");
});
和
goog.events.listen(request, "complete", function(){
if (request.isSuccess()) {
response = request.getResponseJson();
targetVocab = response['targetVocab'];
setVocab(targetVocab); //chaged here
}
});
我认为您的问题是由将vocab设置为targetVocab引起的。在JavaScript中,当您将一个新变量设置为对象变量的值时,两个变量将指向同一个对象:
var a = [{a:0}];
var b = a
a.splice(0,1);
console.log(b);//=[] empty array
你要找的是克隆你的对象,我可以在闭包库中找到goog.object.clone和goog.object.unsafeClone。
clone将只执行浅层复制,因此如果您的数组包含不可变对象或主类型,则可以使用clone,但如果您要像下面的示例中那样对克隆的数组执行操作,则需要unsafeClone:
var a = [{a:0}];
var b = goog.object.clone(a);
a[0].a=22;
console.log(b[0]);//=22
// b isn't even an array here so I'm not sure what clone does
// but it doesn't do much
console.log(b instanceof Array);//false
如果您永远不会更改数组项的值,也永远不会调用会更改项内部值的函数(如copiedarray[0].changevalue();
或copiedarray[index].someval=newval;
),那么您可以复制对新数组中项的引用:
var a = [{a:0}];
var b = a.concat([]);
// can't do a[0].a=newValue or it'll permanently change
a.splice(0,1);
console.log(b[0]);//=0
UnsafeClone将完全克隆对象,但当任何对象(属性)的属性引用自身时,您将面临启动永不终止循环的风险:
var a = [{a:0}];
var b = goog.object.unsafeClone(a);
a[0].a=22;
console.log(b[0]);//=0
console.log(b instanceof Array);//true
就你而言;由于要复制的对象来自JSON字符串,因此不会有循环引用,但可能有更好的方法,因为unsafeClone可能比goog.json.parse
慢
...
if (request.isSuccess()) {
targetVocab = request.getResponseText();
setVocab();
}
...
var setVocab = function() {
vocab = goog.json.parse(targetVocab)['targetVocab'];
}
...
- Javascript Select OnChange没有'不要第二次工作
- 相同的RegExp返回不同的结果-第一次是正确的结果,第二次是null
- 单击仅在第二次单击后有效
- 推特引导:弹出窗口不会在第一次点击时出现,但会在第二次点击时显示
- 第二次点击具有不同功能的按钮并更改文本
- 更改第二次推送时不起作用的元素高度
- 在第二次选择中选择2更改属性
- on(“点击”)仅在第二次点击后触发
- 在HTML中,如果第二次加载相同的脚本文件,它还会被加载吗
- Sails.js/Waterline.add()和.remove()仅适用于第二次调用
- 尝试在两次迭代中警告同一选择器的值,在第一次迭代中得到正确的值,而在第二次迭代中获得不正确的值.为什么?
- java脚本中的谷歌地图在第二次点击时不起作用
- 更改类名后,将第二次单击事件附加到元素
- 提交按钮只能在onchange调用输入文本后第二次点击时工作
- 将音频第二次转换为分钟和秒格式
- Jquery移动转换复选框在Jquery onclick函数()中第二次选中不起作用
- 在连续第二次单击时禁用href
- 正在给用户第二次尝试
- 第二次渲染时主干未捕获引用错误
- 变量在第二次被引用时会丢失值