Home > front end >  Expand string broken up into repeated, nested components [closed]
Expand string broken up into repeated, nested components [closed]

Time:10-08

I'm working on a problem, where given a string with substrings in paranthesis followed by values in curly brackets, the string expands by repeating the substring that number of times. So if you had (ab(d){3}){2} you'd get abdddabddd.

I feel like Im on the right track but that 1. this is pretty inefficient and 2. the tests seem to not return. Would love some help!

public class ExpandedString {
    public static String expandedString(String inputStr) {
        while (inputStr.contains("(")) {
            for (int i = 0; i < inputStr.length(); i  ) {
                //check if there's something to repeat
                if (inputStr.charAt(i) == '{') {
                    int temp = i;
                    //find what you need to repeat
                    while (inputStr.charAt(temp) != '(') {
                        temp--;
                    }
                    String inputStr2 = inputStr.substring(i);
                    int numTimes = i   inputStr.indexOf("}");
                    //replace (blah) with blah times repeated numTimes
                    StringBuilder repeated = new StringBuilder(); 
                    for(int j = 0; j<numTimes;j  ) {
                        repeated.append(inputStr.substring(temp   1, i - 1));
                    }
                    inputStr.replace(inputStr.substring(temp, i), repeated.toString());
                    //start again
                    i = 0;
                }
            }
        }
        return inputStr;
    }

    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);

        // input for inputStr
        String inputStr = in .nextLine();

        String result = expandedString(inputStr);
        System.out.print(result);

    }
}

CodePudding user response:

Here is a solution that uses a stack of StringBuilders and a current StringBuilder.

When a ( is read, the current StringBuilder is pushed onto the stack and a new StringBuilder is created.

When a ) is read, the multiplier mul is extracted, and the value of the current StringBuilder is appended mul times to the StringBuilder popped from the stack.

Otherwhise, append the char to the current StringBuilder.

import java.util.Stack;

public class Expand
{
    public static String expand(String pattern)
    {
        StringBuilder sb = new StringBuilder();
        Stack<StringBuilder> stack = new Stack<StringBuilder>();
        int len = pattern.length();
        int i = 0;
        while(i<len)
        {
            char c = pattern.charAt(i);
            if(c=='(')
            {
                stack.push(sb);
                sb = new StringBuilder();
            }
            else if(c==')')
            {
                String s = sb.toString();
                int k = pattern.indexOf('}', i);
                int mul = Integer.parseInt(pattern.substring(i 2, k));
                sb = stack.pop();
                for(int j=0;j<mul;j  )
                    sb.append(s);
                i = k;
            }
            else
                sb.append(c);
            i  ;
        }
        return sb.toString();
    }

    public static void main(String[] args) 
    {
        System.out.println(expand("(ab(d){3}){2}"));
    }
}

Output:

abdddabddd

CodePudding user response:

An alternative way of getting the desired string using regex:

import java.util.Scanner;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

public class ExpandedString {
    public static String expandedString(String inputStr) {
        while (true) {
            Pattern pattern = Pattern.compile("(\\((\\w*)\\)\\{(\\d*)\\})", Pattern.CASE_INSENSITIVE);
            Matcher matcher = pattern.matcher(inputStr);
            if (!matcher.find())
                break;
            inputStr = matcher.replaceAll("$2".repeat(Integer.parseInt(matcher.group(3))));

        }
        return inputStr;

    }

    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);

        // input for inputStr
        String inputStr = in.nextLine();

        String result = expandedString(inputStr);
        System.out.print(result);

    }
}

I assume that string consists of word characters.

  • Related