替换函数中的 _.each

Replacing _.each in a function

我有这个片段可以计算行数和 returns 在 MySQL table 中找到的行数。这是我使用 underscore.js 的 _.each 进行迭代的代码。

var all_rows = Noder.query('SELECT count(*) as erow from crud ', function(err, the_rows) {

            _.each(the_rows, function (corndog) {
            var trows = corndog.erow;
            console.log("All rows", trows);
            });

            // var das_rows = trows;
            // var total_pages = Math.ceil(das_rows / per_page);
            // console.log("Pages",total_pages);

         res.view('noder/orm', {
            layout: 'layout',
            js:the_rows,
            post:results,
            title: 'This is the hi page title. Gandalf The great.'
        });
        });

我想使用 trows 来计算要为我的分页代码创建的页面数。但是,我无法访问变量 trows.

这是console.log(the_rows);

的输出
[ RowDataPacket { erow: 12 } ]

有没有其他方法可以使 trows 可用于我的其余代码?

在循环外声明trows

var trows = 0;
_.each(the_rows, function (corndog) {
    trows += corndog.erow;
    console.log("All rows",trows);
});

问题是 var trows 只存在于迭代器内部,因为 function 创建了自己的范围来包含变量。

function (corndog) {
    var trows = corndog.erow;
    console.log("All rows",trows);
} // `trows` is removed from existence at this point

console.log(trows); // ReferencError

但是,function 确实可以访问周围范围内的变量。所以,你可以在函数外面声明trows,然后在里面赋值。

var trows;

_.each(the_rows, function (corndog) {
    trows = corndog.erow; // note removal of `var`
    console.log("All rows",trows);
});

console.log(trows); // 12

不过,当您只需要一个值时,_.each() 并不是真正必要的。您可以访问集合的特定索引并链接到您要查找的 属性 上:

var trows = the_rows[0].erow;

如果担心 the_rows 为空,您可以 test for that 避免错误 undefined:

var trows = the_rows.length ? the_rows[0].erow : null;

旁注:务必始终测试 err。如果发生这种情况,the_rows 可能会是 nullundefined

我可能不明白你在问什么 - 但是

var allTrows = [];
_.each(the_rows, function (corndog) {
        var trows = corndog.erow;
        console.log("All rows",trows);
         allTrows.push (trows);
});

然后 return allTrows 在你的 res.render.

虽然 Jonathan 和 Ilya 已经针对您的具体问题给出了实用的解决方案,但让我为标题中的问题提供一个通用的答案:

替换 _.each() 的最简单方法是使用普通 for 循环遍历数组:

for (var i = 0; i < the_rows.length; i++) {
    var row = the_rows[i];
    console.log( "In loop: row = the_rows[" + i + "] =", row );
}
console.log( "After loop: row =", row );

或者,在 ES6 或更高版本中,一个 for...of 循环:

for (var row of the_rows) {
    console.log( "In loop: row =", row );
}
console.log( "After loop: row =", row );

(你可以也可以使用for...in loop, but you probably shouldn't.

由于这些是 built-in 循环构造,并且不像 _.each() 那样涉及内部函数,因此其中定义的任何变量将在循环结束后保留​​其最后一个值。


另一种替换_.each的方法是使用JS数组的built-in .forEach()方法:

the_rows.forEach( function (row, i) {
    console.log( "In loop: row = the_rows[" + i + "] =", row );
} );

或者,如果您想使用此方法循环遍历看起来像数组但实际上不是数组的东西(例如,DOM NodeList):

Array.prototype.forEach.call( the_rows, function (row, i) {
    console.log( "In loop: row = the_rows[" + i + "] =", row );
} );

但是,由于 .forEach() 确实需要将循环 body 包装在一个内部函数中,就像 _.each() 一样,任何在其中使用 var 声明的变量都不会在循环外可用。但是,在循环函数 之外声明的变量在循环函数 内部是可见的,因此您可以这样做这个:

var last_row;
the_rows.forEach( function (row, i) {
    last_row = row;  // <-- no "var"!
    console.log( "In loop: last_row = row = the_rows[" + i + "] =", row );
} );
console.log( "After loop: last_row =", last_row );