javascript比较数组中的对象

时间:2011-05-18 22:33:55

标签: javascript dom

我在页面上有一个图片网格。并且,我想周期性地在一个对象数组中随机交换一个50个中的一个 - 但前提是它们还没有在网格中。最后一部分是我的代码未能做到的。

我首先获得所有50个项目,并将它们放入allmedia数组中:

// initialize
var allmedia = getAllMedia();
var imagesInGrid = [];

当我将项目放在网格中时,我添加了一个网格项数组:

imagesInGrid.push(allmedia [i]); // while looping to fill DOM grid

然后,每隔8秒我运行一个getRandomImage()例程,该例程从allmedia数组中随机获取一个图像,然后测试它以查看它是否已经存在于DOM中。

function getRandomImageNotInGrid(){
    var randomNumber = Math.floor(Math.random() * allmedia.length);
    if (!isInArray(allmedia[randomNumber], imagesInGrid)) {
        return allmedia[randomNumber];
    } else {
        return getRandomImageNotInGrid();
    }
}

function isInArray(item, arr) {
    if(arr[0]===undefined) return false;
    for (var i=arr.length;i--;) {
        if (arr[i]===item) {
            return true;
        }
    }
    return false;
}

但当我单步执行代码时,(arr [i] === item)测试失败了。我可以看到两个对象完全相同,但===并没有看到这是真的。

这是ByReference / ByValue问题吗?我做错了什么?

的console.log:

arr[i]===item
false
arr[i]==item
false
typeof item
"object"
typeof arr[i]
"object"

修改::

在下面的输出中,我不明白为什么arr [0]与'item'不同。当我将项目放入页面时,我使用与allmedia完全相同的对象,并相应地更新imagesInGrid。

console.dir(arr[0]);
    Object
        caption: Object
        comments: Object
        created_time: "1305132396"
        filter: "Poprocket"
        id: "69204668"
        images: Object
        likes: Object
        link: "http://instagr.am/p/EH_q8/"
        location: Object
        tags: Array[2]
        type: "image"
        user: Object
        __proto__: Object

console.dir(item);
    Object
        caption: Object
        comments: Object
        created_time: "1305132396"
        filter: "Poprocket"
        id: "69204668"
        images: Object
        likes: Object
        link: "http://instagr.am/p/EH_q8/"
        location: Object
        tags: Array[2]
        type: "image"
        user: Object
        __proto__: Object

3 个答案:

答案 0 :(得分:2)

不是从allmedia中随机选择一个,而是从allmedia中删除一个吗?

var randomNumber = Math.floor(Math.random() * allmedia.length);
imagesInGrid.push(allmedia.splice(randomNumber,1));

答案 1 :(得分:0)

使用===时,您将通过引用比较对象。您使用什么类型的对象进行比较?你确定它们是同一个对象参考吗?例如,如果您使用的是字符串,则可能需要使用==而不是===。如果您使用的是DOM对象,则需要像Alxandr建议的那样比较源代码。

此外,您的for循环语法似乎是错误的:

for (var i=arr.length;i--;)

应该是:

for (var i=arr.length - 1; i >= 0; i--)

......如果我没弄错的话。

答案 2 :(得分:0)

您不会显示有关如何创建图像“对象”或如何在DOM中添加和删除它们的任何代码。如果要创建图像元素并在数组中存储引用,那么将DOM元素替换为数组中的元素,那么比较应该有效。

但是,如果您的图像对象是用于创建要显示的图像元素的数据包,那么它们将永远不会彼此相等。每个javascript对象都是唯一的,它只会与自身相等。

但我怀疑最简单的解决方案是ic3b3rg建议的 - 当你选择它时从allMedia移除对象,这样你就不必测试它是否已经在imagesInGrid中,因为你可以只选择一次图像。如果您希望显示屏永久显示,那么当allmedia为空时,将imagesInGrid中的所有图片放回其中并重新开始。

修改

你的问题是for循环。设置时:

for (var i=arr.length;i--;) {
  // On first iteration, i=arr.length
  // so arr[i] is undefined
}

i在第一个循环 之后才会递减,因此请设置i=arr.length-1。将while与递减计数器一起使用更为常见:

var i = arr.length;
while (i--) {
  // i is decremented after the test
}