Open In App

JavaScript Program to Decode a String Recursively Encoded as Count Followed by Substring

Given an encoded string, the encoding is done as follows: The string is divided into substrings. Each substring is followed by a number, representing the count of times that substring should be repeated.

The task is to decode this encoded string recursively and return the decoded string.



<count>[sub_str] ==> The substring 'sub_str' appears count times.

Examples:

Input : str[] = "2[ni]"
Output : nini
Input : str[] = "2[f2[k]]"
Output : fkkfkk
Input : str[] = "3[b2[ca]]"
Output : bcacabcacabcaca

Table of Content

Approach 1: Using two Stacks

Example:This example shows the use of the above-explained appraoch.






// Javascript program to decode a string recursively
// encoded as count followed substring
  
// Returns decoded string for 'str'
function decode(str) {
    let integerstack = [];
    let stringstack = [];
    let temp = "",
        result = "";
  
    // Traversing the string
    for (let i = 0; i < str.length; i++) {
        let count = 0;
  
        // If number, convert it into number
        // and push it into integerstack.
        if (str[i] >= "0" && str[i] <= "9") {
            while (str[i] >= "0" && str[i] <= "9") {
                count = count * 10 + str[i] - "0";
                i++;
            }
  
            i--;
            integerstack.push(count);
        }
  
        // If closing bracket ']', pop element
        // until '[' opening bracket is not found
        // in the character stack.
        else if (str[i] == "]") {
            temp = "";
            count = 0;
  
            if (integerstack.length > 0) {
                count =
                    integerstack[integerstack.length - 1];
                integerstack.pop();
            }
  
            while (
                stringstack.length > 0 &&
                stringstack[stringstack.length - 1] != "["
            ) {
                temp =
                    stringstack[stringstack.length - 1] +
                    temp;
                stringstack.pop();
            }
  
            if (
                stringstack.length > 0 &&
                stringstack[stringstack.length - 1] == "["
            ) {
                stringstack.pop();
            }
  
            // Repeating the popped string 'temo'
            // count number of times.
            for (let j = 0; j < count; j++) {
                result = result + temp;
            }
  
            // Push it in the character stack.
            for (let j = 0; j < result.length; j++) {
                stringstack.push(result[j]);
            }
  
            result = "";
        }
  
        // If '[' opening bracket, push it
        // into character stack.
        else if (str[i] == "[") {
            if (str[i - 1] >= "0" && str[i - 1] <= "9") {
                stringstack.push(str[i]);
            } else {
                stringstack.push(str[i]);
                integerstack.push(1);
            }
        } else {
            stringstack.push(str[i]);
        }
    }
  
    // Pop all the element, make a
    // string and return.
    while (stringstack.length > 0) {
        result =
            stringstack[stringstack.length - 1] + result;
        stringstack.pop();
    }
  
    return result;
}
  
let str = "3[f2[jk]]";
console.log(decode(str));

Output
fjkjkfjkjkfjkjk

Approach 2: Without Stacks

Algorithm for better understanding.

Example: Below is the implementation of the above approach.




// Function to decode given encoded string
function decodeString(s) {
    let result = "";
  
    for (let i = 0; i < s.length; i++) {
        if (s[i] !== "]") {
            // If the current character is 
            // not a closing bracket,
            // append it to the result string.
            result += s[i];
        } else {
            // If the current character is 
            // a closing bracket:
  
            // Create a temporary string to 
            // store the substring within
            // the corresponding opening bracket.
            let temp = "";
            while (
                result.length > 0 &&
                result[result.length - 1] !== "["
            ) {
                // Keep popping characters from the 
                // result string and add them to the
                // temp string until we reach the opening bracket.
                temp = result[result.length - 1] + temp;
                result = result.slice(0, -1);
            }
  
            result = result.slice(0, -1); // Remove the opening bracket
  
            // Extract the preceding number and convert it to an integer.
            let num = "";
            while (
                result.length > 0 &&
                !isNaN(result[result.length - 1])
            ) {
                // Keep popping characters from the 
                // result string and add them to
                // num string
                // until we encounter a non-digit character.
                num = result[result.length - 1] + num;
                result = result.slice(0, -1);
            }
            let int_num = parseInt(num);
  
            // Append the substring to the result string,
            // repeat it to the required number of times.
            while (int_num--) {
                result += temp;
            }
        }
    }
  
    // Return the decoded string.
    return result;
}
  
// Driver code to test above function
let str = "2[1[a]2[b]]";
console.log(decodeString(str));

Output
abbabb

Article Tags :