Home > Web Front-end > JS Tutorial > body text

LeetCode Meditations: Decode Ways

王林
Release: 2024-07-29 00:14:52
Original
644 people have browsed it

LeetCode Meditations: Decode Ways

Let's start with the description for this problem:

You have intercepted a secret message encoded as a string of numbers. The message is decoded via the following mapping:

"1" -> 'A' "2" -> 'B' ... "25" -> 'Y' "26" -> 'Z'

However, while decoding the message, you realize that there are many different ways you can decode the message because some codes are contained in other codes ("2" and "5" vs "25").

For example, "11106" can be decoded into:

  • "AAJF" with the grouping (1, 1, 10, 6)
  • "KJF" with the grouping (11, 10, 6)
  • The grouping (1, 11, 06) is invalid because "06" is not a valid code (only "6" is valid).

Note: there may be strings that are impossible to decode.

Given a string s containing only digits, return the number of ways to decode it. If the entire string cannot be decoded in any valid way, return 0.

The test cases are generated so that the answer fits in a 32-bit integer.

For example:

Input: s = "12"

Output: 2

Explanation: "12" could be decoded as "AB" (1 2) or "L" (12).
Copy after login

Or:

Input: s = "226"

Output: 3

Explanation: "226" could be decoded as "BZ" (2 26), "VF" (22 6), or "BBF" (2 2 6).
Copy after login

Or:

Input: s = "06"

Output: 0

Explanation: "06" cannot be mapped to "F" because of the leading zero ("6" is different from "06"). In this case, the string is not a valid encoding, so return 0.
Copy after login

The constraints are:

  • 1 <= s.length <= 100
  • s contains only digits and may contain leading zero(s).

I think this is one of those problems that you think is not so difficult at first glance until you attempt to solve it.

First, let's start with the simplest insight: a character can be decoded as either itself (as only one character) or the part of a two-digit number.
If it's the first option, we can only have digits from 1 to 9, as 0 by itself is not mapped to anything.
However, a two-digit number can be from 10 up to 26.

As with the previous problems in this chapter, we can start by creating a dp array to hold the number of ways to decode up to each character as we iterate through the string.
Very similar to Climbing Stairs, we have to initialize our array with the length s.length + 1 as we need to consider the fact that we haven't decoded anything yet.
In other words, when there are no characters, there's only one way to "decode": not decoding at all.

So, we can initialize all the values as 0s, except for the first index which is going to be 1.

let dp = Array.from({ length: s.length + 1 }, () => 0);

dp[0] = 1;




Again, similar to the previous problems, we have to keep the bottom two values, so we have to initialize the second slot of our array which corresponds to the number of ways to decode the first character in the string.

We know that we can't decode it if it's '0', so the number of ways to decode it will be 0 in this case.
Note that not being able to decode is different from not doing any decoding at all: in the first case, the number of ways to decode is 0, but in the second case (as we just did with dp[0]), it can be said that the number of ways to decode is 1.

In all the other cases, there is only one way to decode it because it's just a single character. So, we'll initialize dp[1] accordingly:

dp[1] = (s[0] === '0') ? 0 : 1;
Copy after login

Now we can start iterating from the third index. We'll look at both the previous digit and the previous two digits at the same time.

As long as the previous digit is not the number 0, we can add whatever that's in the previous slot of our array.

And, as long as the previous two digits constitute a number that's between 10 and 26, we can add that corresponding solution as well. All in all, it can look like this:

for (let i = 2; i <= s.length; i++) {
  const prevDigit = s[i - 1];
  const twoPrevDigits = s.slice(i - 2, i);
  if (+prevDigit !== 0) {
    dp[i] += dp[i - 1];
  }

  if (10 <= +twoPrevDigits && +twoPrevDigits <= 26) {
    dp[i] += dp[i - 2];
  }
}
Copy after login
Note
We're converting the string characters to numbers with the handy unary plus operator. We know from the problem constraints that the string s only contains digits.

At this point, we have the result in the last index (which corresponds to s.length) so we can just return it:

function numDecodings(s: string): number {
  /* ... */

  return dp[s.length]; 
}
Copy after login

Overall, this is how our solution looks like:

function numDecodings(s: string): number {
  let dp = Array.from({ length: s.length + 1 }, () => 0);

  dp[0] = 1;
  dp[1] = (s[0] === '0') ? 0 : 1;

  for (let i = 2; i <= s.length; i++) {
    const prevDigit = s[i - 1];
    const twoPrevDigits = s.slice(i - 2, i);
    if (+prevDigit !== 0) {
      dp[i] += dp[i - 1];
    }

    if (10 <= +twoPrevDigits && +twoPrevDigits <= 26) {
      dp[i] += dp[i - 2];
    }
  }

  return dp[s.length];
}
Copy after login

Time and space complexity

Both the time and space complexity for this solution are O(n)O(n) O(n) as we iterate through all the characters doing a constant operation, and we have to keep an array whose size will grow as our input size increases.


Next up is the problem called Coin Change. Until then, happy coding.

The above is the detailed content of LeetCode Meditations: Decode Ways. For more information, please follow other related articles on the PHP Chinese website!

source:dev.to
Statement of this Website
The content of this article is voluntarily contributed by netizens, and the copyright belongs to the original author. This site does not assume corresponding legal responsibility. If you find any content suspected of plagiarism or infringement, please contact admin@php.cn
Popular Tutorials
More>
Latest Downloads
More>
Web Effects
Website Source Code
Website Materials
Front End Template
About us Disclaimer Sitemap
php.cn:Public welfare online PHP training,Help PHP learners grow quickly!