React本机密钥在for循环中没有正确更新?

时间:2016-05-02 12:21:40

标签: javascript arrays for-loop firebase react-native

我在我的React-native应用程序中有一个函数,我在其中循环遍历数组中的键并从Firebase中提取相应的引用。

然而,在我的for循环中,虽然总是评估正确的ref,但for循环内部的键值总是3,因此totalItemsCompleted(等于键的值的长度) userItemsArray)总是等于3。

 listenForItems(itemsRef) {
    var userItemsArray = {
        0: [1],
        1: [5, 6],
        2: [8, 9, 10],
        3: [11, 12, 13]
    };

    var pastItems = [];
    var currentItems = [];

    for (var key in userItemsArray) {
        console.log("KEY1 " + key); //key is correct here
        var itemRef = itemsRef.child(key);
        itemRef.on('value', (snap) => {
            var totalItemsOnList = snap.val().items.length;
            var totalItemsCompleted = userItemsArray[key].length;
            console.log("KEY2 " + key); //key is always 3 here
            if (totalItemsOnList===totalItemsCompleted) {
                pastItems.push({
                    title: snap.val().title,
            });
            }
            else {
                currentItems.push({
                    title: snap.val().title,
                });
            }

            this.setState({
                currentItems: this.state.currentItems.cloneWithRows(currentItems),
                pastItems: this.state.pastItems.cloneWithRows(pastItems)
            });
        });
    }
}

2 个答案:

答案 0 :(得分:1)

下一段代码可以轻松复制相同的流程:

for(var i= 0; i< 3; i++) setTimeout(()=> alert(i) ,i * 1000)

虽然您正在创建多个匿名函数实例,但它并未锁定到相应的key值,而是引用其“按名称”。 因此,任何处理程序调用的变量key都包含它在循环期间获得的最后一个值。

有不同的方法来处理它。 最简单的方法是将处理程序的创建包装成自调用的匿名函数:

temRef.on('value', ((keyFixedValue) => {
return (snap) => {/*all other code*/}
})(key))

另一种可能的方法是将key存储为适当HTML元素的属性值

答案 1 :(得分:1)

这里的问题是firebase的异步性质。你的for循环没有等待firebase调用完成,所以它不断更新键值。

使用密钥变量的内容你应该使用firebase快照的密钥,如下所示:

var itemRef = itemsRef.child(key);
    itemRef.on('value', (snap) => {
        var totalItemsOnList = snap.val().items.length;
        var totalItemsCompleted = userItemsArray[snap.key()].length;
        console.log("KEY2 " + snap.key());