JavaScript嵌套数组练习

时间:2017-06-21 18:19:18

标签: javascript arrays

我正在做一个嵌套数组'来自rithm学校的练习,练习说:

"给定以下数组,编写一个名为countVowels的函数,它返回每个字符串中所有元音的计数,无论大小写如何。要查看值是否为数组,您不能使用typeof,因为它将返回' object',所以一种方法是使用Array.isArray函数。"

我有点做了,但我不喜欢这个解决方案,而且我也不明白为什么我不能使用toLowerCase()函数而不指定索引,我会解决这个问题&#34 ;使用[0]。

所以,这是我不优雅的解决方案:

var vowels = ["a","e","i","o","u"];
function countVowels(array) {
  counter = 0;
  if (Array.isArray(array) == true) {
    for (var i = 0; i < array.length; i++) {
      if (Array.isArray(array[i]) == true) {
        for (var j = 0; j < array[i].length; j++) {
          if (Array.isArray(array[i][j]) == true) {
            for (var k = 0; k < array[i][j].length; k++) {
              if (Array.isArray(array[i][j][k])) {
                for (var l = 0; l < array[i][j][k].length; l++) {
                  for (var m = 0; m < array[i][j][k][l].length; m++) {
                    for (var v = 0; v < vowels.length; v++) {
                      if (array[i][j][k][l][m][0].toLowerCase() == vowels[v])
                        counter += 1;
                    }
                  }
                }
              }
              for (var l = 0; l < array[i][j][k].length; l++) {
                for (var v = 0; v < vowels.length; v++) {
                  if (array[i][j][k][l][0].toLowerCase() == vowels[v])
                    counter += 1;
                }
              }
            }
          }
          for (var k = 0; k < array[i][j].length; k++) {
            for (var v = 0; v < vowels.length; v++) {
              if (array[i][j][k][0].toLowerCase() == vowels[v])
                counter += 1;
            }
          }
        }
      }
      for (var j = 0; j < array[i].length; j++) {
        for (var v = 0; v < vowels.length; v++) {
          if (array[i][j][0].toLowerCase() == vowels[v])
            counter += 1;
        }
      }
    } // end of first for
  } // end of first if
  return counter;
}

2 个答案:

答案 0 :(得分:1)

您的代码建议您需要查看元音的嵌套数组,并且事先不知道它们被“埋葬”的深度。

在这种情况下,您可以通过使用递归来简化操作。这意味着当你得到一个数组时,你将在其中找到元音的工作转发给函数本身,每次更深一级,直到你到达一个字母,然后看它是否是一个元音(数1或0)

以下是您已经拥有的循环方式,但没有重复的代码:

// Global variable
var vowels = ['a', 'e', 'i', 'o', 'u'];

function countVowels(value) {
    var count = 0;
    if (Array.isArray(value)) {
        for (var i = 0; i < value.length; i++) {
            // Use recursion to get the deeper count
            count = count + countVowels(value[i]);
        }
    } else { // value is not an array. End of recursion
        // test whether character is in vowel array, and convert the boolean
        // result to a number (0 or 1) with the unary plus 
        count = +(vowels.indexOf(value.toLowerCase()) > -1);
    }
    return count;
}

// Sample input
var array = [[['x', 'a'], ['I']], [], [['U', 'b', ['o']]], 'E', 'T'];

console.log(countVowels(array)); // 5

非递归替代

当递归深度不是极端时,递归非常好。如果这是一个问题,请采用迭代方法:

// Global variable
var vowels = ['a', 'e', 'i', 'o', 'u'];

function countVowels(value) {
    var count = 0;
    var stack = [value];
    while (stack.length > 0) { // still some unprocessed values
        value = stack.pop(); // get one of them
        if (Array.isArray(value)) {
            // append array elements to the stack for later processing
            stack = stack.concat(value);
        } else if (vowels.indexOf(value.toLowerCase()) > -1) { 
            // value is a vowel. Increment the count                
            count = count + 1;
        } // If it is neither an array nor a vowel: nothing to do 
    }
    return count;
}

// Sample input
var array = [[['x', 'a'], ['I']], [], [['U', 'b', ['o']]], 'E', 'T'];

console.log(countVowels(array)); // 5

作弊; - )

还有另一种非传统的方式,这当然不是这项运动的目标。您可以使用数组的toString行为:该方法将数组转换为字符串,并且也会对所有嵌套数组执行此操作,因此您甚至不必担心嵌套。

然后你有一个字符串要解析,这要容易得多。

然后第二个“hack”将使用正则表达式一次性找到该字符串中的所有元音。然后你只需要算一下你的结果。

以下是代码:

function countVowels(value) {
    // Array to string, do global search, case insensitive, and return length
    return value.toString().match(/[aeiou]/gi).length; 
}

// Sample input
var array = [[['x', 'a'], ['I']], [], [['U', 'b', ['o']]], 'E', 'T'];

console.log(countVowels(array)); // 5

答案 1 :(得分:0)

重新修改@Trincot的优秀答案,因为你没有立即看到它是如何工作的:

在递归中,我们将问题分解为两种情况

在一种情况下,(非数组),我们可以立即回答元音的数量为1或0。

在另一种情况下,我们有阵列,我们无法立即回答。我们必须为数组的每个元素调用相同的函数,并添加答案。

&#13;
&#13;
var vowels = 'aeiou';

function countVowels(eitherArrayOrValue) {
    let count = 0;
    if (Array.isArray(eitherArrayOrValue)) { // If it we are being asked about an array
        for (var i = 0; i < eitherArrayOrValue.length; i++) {
            // Then look at each of the array elements in turn, counting their vowels. This is done by the function calling itself - this is called RECURSION
            count = count + countVowels(eitherArrayOrValue[i]);
        }
    } else { // not an array, so can just test directly
        if (vowels.indexOf(eitherArrayOrValue.toLowerCase()) > -1){
            count = 1;
       } else {
            count = 0;
       }
    }
    return count; // This is being returned either to the original caller or to this function itself if it has been self-called with an array element.
}

// Sample input
var array = [[['x', 'a'], ['I']], [], [['U', 'b', ['o']]], 'E', 'T'];

console.log(countVowels(array)); // 5
&#13;
&#13;
&#13;