Javascript数组作用域问题
已解决-此示例代码有效,因此我将其与未工作的代码进行了比较,发现了差异 在我的代码中,一个不起作用的代码,当声明颜色数组时,我忘记在它前面添加一个“var”Javascript数组作用域问题,javascript,arrays,html,scope,Javascript,Arrays,Html,Scope,已解决-此示例代码有效,因此我将其与未工作的代码进行了比较,发现了差异 在我的代码中,一个不起作用的代码,当声明颜色数组时,我忘记在它前面添加一个“var” m_color = []; m_color[0] = 255; m_color[1] = 255; m_color[2] = 255; m_color[3] = 255; 而不是: var m_color = []; m_color[0] = 255; m_color[1] = 255; m_color[2] = 255; m_color
m_color = [];
m_color[0] = 255;
m_color[1] = 255;
m_color[2] = 255;
m_color[3] = 255;
而不是:
var m_color = [];
m_color[0] = 255;
m_color[1] = 255;
m_color[2] = 255;
m_color[3] = 255;
就这样。没有生成错误,我猜它创建了一个由所有粒子共享的全局数组
谢谢大家的回答。我将使用它们来编写更好的javascript代码
旧问题(不再相关)如下:
我对javascript数组的作用域有一个疯狂的问题 我有一个类粒子:
function ParticleClass()
{
var m_color = [];
m_color[0] = 255;
m_color[1] = 255;
m_color[2] = 255;
m_color[3] = 255;
var m_red = 255;
var m_green = 255;
var m_blue = 255;
this.SetRandomColorRGB = SetRandomColorRGB;
this.SetRandomColorArray = SetRandomColorArray;
this.DrawParticleRGB = DrawParticleRGB;
this.DrawParticleArray = DrawParticleArray;
function SetRandomColorRGB()
{
m_red = Math.floor( Math.random() * 255 );
m_green = Math.floor( Math.random() * 255 );
m_blue = Math.floor( Math.random() * 255 );
}
function SetRandomColorArray()
{
m_color[0] = Math.floor( Math.random() * 255 );
m_color[1] = Math.floor( Math.random() * 255 );
m_color[2] = Math.floor( Math.random() * 255 );
}
function DrawParticleRGB( ctx )
{
// I draw the particle using m_red, m_green and m_blue.
}
function DrawParticleArray( ctx )
{
// I draw the particle using m_color[0], m_color[1], m_color[2]
}
}
然后我创建一个ParticleClass粒子数组并绘制它们
如果我创建一组粒子并尝试在屏幕上绘制它们,SetRandomColorRGB和DrawParticleRGB效果很好。每个粒子都有不同的颜色
如果使用SetRandomColorArray和DrawParticleArray,则所有粒子都具有相同的颜色。每次创建新粒子时,所有粒子都会更改为上次拾取的颜色集RandomColorArray
在我看来,数组共享内存,而其他变量则不共享。这是真的吗?这是Javascript的一个怪癖吗?还有别的事吗
谢谢。变量的作用域在函数ParticleClass()中。因此,在此空间中定义的函数中的变量将与其父函数共享作用域 这就是为什么有时候会在Javascript中看到这种模式-
var self = this;
$('.someClass').each(function(i) {
// function is defined as a closure
// but it shares its scope with its parent so it can see self and access the parent's
// pointer to this.
});
为什么不使用prototype来定义函数
例如
这将为您获得所需的命名空间
这里有一个例子:这样做并没有问题,但话说回来,你们这样做让生活变得更加困难;最好正确使用原型:
function ParticleClass()
{
this.m_color = [255, 255, 255, 255];
this.m_red = 255;
this.m_green = 255;
this.m_blue = 255;
}
(function(p) {
p.SetRandomColorRGB = function () {
this.m_red = Math.floor( Math.random() * 255 );
this.m_green = Math.floor( Math.random() * 255 );
this.m_blue = Math.floor( Math.random() * 255 );
}
p.SetRandomColorArray = function () {
this.m_color[0] = Math.floor( Math.random() * 255 );
this.m_color[1] = Math.floor( Math.random() * 255 );
this.m_color[2] = Math.floor( Math.random() * 255 );
}
p.DrawParticleRGB = function( ctx ) {
// I draw the particle using m_red, m_green and m_blue.
}
p.DrawParticleArray = function( ctx )
{
// I draw the particle using m_color[0], m_color[1], m_color[2]
}
}(ParticleClass.prototype);
这里。。。这可能有助于解释为什么会发生这种情况:
var data = {}; // create a data object
data.string = "hey society"; // Add a string value property
data.num = 0; // Add a integer value property
data.arr = [0,1,2]; // Add an array property
data.date = new Date(); // Add an object property
// here is where the fun starts!
// Create a var for string property
var sString = data.string; // sets to "hey society", as expected.. cool
data.string = "changed" // change the value and the compare :
data.string == sString // returns false, the values are different
// same happens for a number.
// Now lets copy this array
var oArr = data.arr; // (seeing the comment pattern? XD)
data.arr .push(3); // and modify it.
data.arr == oArr // should be false? Nope. returns true.
// arrays are passed by reference.
var oDate = data.date // what about objects?
data.date .setHours(0); // modify the variable and
oDate.getTime() == data.date.getTime() // it returns true, too!
// so, how do we fix the array problem?
// right in front of yer nose
var oArrFix = data.arr.splice(0) // get a new array based on
data.arr .push(4) // an unmodified version of the original
data.arr == oArrFix // false.. huh..
// How do we use this as a fix
data.arr["changed"] == false;
oArrFix = ChangeOriginalArray( data.arr );
// When you are expecting an array..
function ChangeOriginalArray( arr ) // pass as a parameter
{
var aArr = arr.splice(0); // make a copy!
if (aArr["changed"] == false) // check has same value!
{
aArr["newKey"] = "newVal"; // add a value
arr["changed"] = true; // change original value
}
return aArr;
}
oArrFix["newKey"] == data.arr["newKey"] // false
oArrFix["changed"] == true // no, created
data.arr["changed"] == oArrFix["changed"] // nah, passed by value, not reference
这不应该发生,我很确定不会发生。每个粒子应具有不同的阵列。你能提供一个你的代码的工作演示,这样我们就可以确切地知道出了什么问题吗?你确定它没有抛出任何错误吗<代码>this.DrawParticleRGB=DrawParticleRGB不应该是this.DrawParticleRGB=DrawParticleWithRGB
SetRandomColorRGB()
和SetRandomColorArray()
执行完全相同的操作,减去赋值的位置。就个人而言,我会在函数中添加this.m_red
等,但这是一种风格选择。问题必须在绘图函数中,除非代码中有错误(使用某种调试器捕捉任何警告或错误)。这不是确切的代码。我的代码中有更多的东西,所以我写了这个简单的版本。这就是为什么函数名是错误的。我将尝试创建一个JSFIDLE示例。
var data = {}; // create a data object
data.string = "hey society"; // Add a string value property
data.num = 0; // Add a integer value property
data.arr = [0,1,2]; // Add an array property
data.date = new Date(); // Add an object property
// here is where the fun starts!
// Create a var for string property
var sString = data.string; // sets to "hey society", as expected.. cool
data.string = "changed" // change the value and the compare :
data.string == sString // returns false, the values are different
// same happens for a number.
// Now lets copy this array
var oArr = data.arr; // (seeing the comment pattern? XD)
data.arr .push(3); // and modify it.
data.arr == oArr // should be false? Nope. returns true.
// arrays are passed by reference.
var oDate = data.date // what about objects?
data.date .setHours(0); // modify the variable and
oDate.getTime() == data.date.getTime() // it returns true, too!
// so, how do we fix the array problem?
// right in front of yer nose
var oArrFix = data.arr.splice(0) // get a new array based on
data.arr .push(4) // an unmodified version of the original
data.arr == oArrFix // false.. huh..
// How do we use this as a fix
data.arr["changed"] == false;
oArrFix = ChangeOriginalArray( data.arr );
// When you are expecting an array..
function ChangeOriginalArray( arr ) // pass as a parameter
{
var aArr = arr.splice(0); // make a copy!
if (aArr["changed"] == false) // check has same value!
{
aArr["newKey"] = "newVal"; // add a value
arr["changed"] = true; // change original value
}
return aArr;
}
oArrFix["newKey"] == data.arr["newKey"] // false
oArrFix["changed"] == true // no, created
data.arr["changed"] == oArrFix["changed"] // nah, passed by value, not reference