Search code examples
javascriptarraysalgorithmfor-loopreduce

How does one, within a sequence of digits, count how many times a digit appears thats value is exactly one less than the previous digit's one?


code:

function OneDecremented(num) { 
  num = num.toString()
  var count = 0

  for(i = 1; i < num.length; i++) {
    if(num[i - 1] - num[i] === 1){
      count++
    }
  }
  return count

}
console.log(OneDecremented(9876541110))

so I'm struggling to understand two things:

  1. what's the difference between i and num[i]
  2. I don't understand how the calculation is happening inside the if statement, could someone break it down?

sorry if these questions sound too silly, I'm new to JS and couldn't really get my head around the arithmetic calculations. Thank you for you time.


Solution

  • That code is poorly written for few reasons, but most importantly, it leaks the i reference globally so, let's start with a better version:

    function OneDecremented(num) {
      var str = num.toString();
      var count = 0;
      for(var i = 1; i < str.length; i++) {
        if(str[i - 1] - str[i] === 1)
          count++;
      }
      return count;
    }
    

    Strings, in modern JS, can be accessed like arrays, and the index returns the char at the index position:

    if(str[i - 1] - str[i] === 1)
    // is the same as
    if ((str.charAt(i - 1) - str.charAt(i)) === 1)
    

    Once retrieved each char, the code does an implicit "char to number" conversion, thanks to the - operator, but if it was a + instead, it would've concatenated the two chars as string instead (so, be careful).

    It's always better to be explicit, but if you know how - works, it does the job for this task.

    The loop starts from 1, and it checks that the char at i - 1, which is in the first iteration the char at index 0, minus the current char, is 1, meaning the current char is one less the previous.

    When that's the case, the counter sums up.