Java使用组合拆分字符串

时间:2015-01-29 12:10:35

标签: java

我的输入字符串是

element1-element2-element3-element4a|element4b-element5-

预期输出

element1-element2-element3-element4a-element5-
element1-element2-element3-element4b-element5-

因此短划线( - )是分隔符,管道(|)表示位置的两个替代元素。

我能够为包含单个管道的输入生成组合:

ArrayList<String> finalInput = new ArrayList<String>();
String Input = getInputPath();
StringBuilder TempInput = new StringBuilder();
if(Input.contains("|")) {
    String[] splits = Input.split("\\|", 2);
    TempInput.append(splits[0]+"-"+splits[1].split("-", 2)[1]);
    finalInput.add(TempInput.toString());
    TempInput = new StringBuilder();
    String[] splits1 = new StringBuilder(Input).reverse().toString().split("\\|", 2);
    finalInput.add(TempInput.append(splits1[0]+"-"+splits1[1].split("-", 2)[1]).reverse().toString());              
}

但如果有多个管道符号,则此逻辑会失败。

  • 如何仅在最后一次出现时拆分字符串?

有没有有效的方法将split String与组合一起使用?

输入

element1-element2-element3-element4a|element4b-element5-element6a|element6b

输出

element1-element2-element3-element4a-element5-element6a
element1-element2-element3-element4b-element5-element6a
element1-element2-element3-element4a-element5-element6b
element1-element2-element3-element4b-element5-element6b

5 个答案:

答案 0 :(得分:5)

递归帮助。

public static void main(String[] args) {
    produce("element1-element2-element3-element4a|element4b"
        + "-element5-element6a|element6b");
}

private static void produce(String input) {
    String[] sequence = input.split("-");
    String[][] elements = new String[sequence.length][];
    for (int i = 0; i < sequence.length; ++i) {
        elements[i] = sequence[i].split("\\|");
    }
    List<String> results = new ArrayList<>();
    walk(results, elements, 0, new StringBuilder());
}

private static void walk(List<String> results, String[][] elements,
        int todoIndex, StringBuilder done) {
    if (todoIndex >= elements.length) {
        results.add(done.toString());
        System.out.println(done);
        return;
    }
    int doneLength = done.length();
    for (String alternative : elements[todoIndex]) {
        if (done.length() != 0) {
            done.append('-');
        }
        done.append(alternative);
        walk(results, elements, todoIndex + 1, done);
        done.setLength(doneLength); // Undo
    }
}

String.split方法用于获取可导航的String[][]两次。为了构建最终的字符串,使用了StringBuilder

答案 1 :(得分:1)

我已经为你写了一个演示文章,因为我发布了你的评论,代码可能很难看,但是它有效

public class TestSplit {
    //define a stringList hold our result.
    private static List<String> stringList = new ArrayList<String>();

    //this method fork the list array when we meet a "|"
    public static void forkStringList(){
        List<String> tmpList = new ArrayList<String>();
        for(String s: stringList){
            tmpList.add(s);
        }
        stringList.addAll(tmpList);
    }

    //when we meet "|" split two elems, should add it to 
    //the string list half-half
    public static void addTowElems(String s1, String s2){
        for(int i=0;i<stringList.size()/2;i++){
            stringList.set(i,stringList.get(i)+s1);
        }
        for(int i = stringList.size()/2;i<stringList.size();i++){
            stringList.set(i,stringList.get(i)+s2);
        }
    }
    // if not meet with a "|" just add elem to everyone of the stringlist
    public static void addOneElem(String s){
        for(int i=0;i<stringList.size();i++){
            stringList.set(i,stringList.get(i)+s);
        }
    }

    public static void main(String[] argvs){
        //to make *fork*  run, we must make sure there is a "init" string 
        //which is a empty string.
        stringList.add("");
        // this is your origin string.
        String input = "a-b-c-d|e-f";
        for (String s: input.split("\\-")){
            if(s.contains("|")){
                //when meet with "|", first fork the stringlist 
                forkStringList();
                // then add them separately 
                addTowElems(s.split("\\|")[0],s.split("\\|")[1]);
            }else {
                // else just happily add the elem to every one 
                // of the stringlist
                addOneElem(s);
            }
        }
        //checkout the result, should be expected.
        System.out.println(stringList);
    }

}

答案 2 :(得分:0)

您可以在Java中使用StringTokenizer。基本上它会产生字符串的标记。

public StringTokenizer(String str, String delim)

以下是一个例子:

String msg = "http://100.15.111.60:80/"; 
char tokenSeparator= ':'; 
StringTokenizer st = new StringTokenizer(msg, tokenSeparator + "");          
while(st.hasMoreTokens()) {
    System.out.println(st.nextToken());
}

答案 3 :(得分:0)

这是我的迭代解决方案:

import java.util.*;

public class PathParser {

    private static final String DELIMINATOR_CONCAT = "-";
    private static final String DELIMINATOR_OPTION = "|";

    private List<String> paths;
    private List<String> stack;

    private List<String> parse(final String pathSpec) {
        stack = new ArrayList<String>();
        paths = new ArrayList<String>();
        paths.add("");
        final StringTokenizer tok = createStringTokenizer(pathSpec);
        while (tok.hasMoreTokens()) {
            final String token = tok.nextToken();
            parseToken(token);
        }
        if (!stack.isEmpty()) {
            updatePaths();
        }
        return paths;
    }

    private void parseToken(final String token) {
        if (DELIMINATOR_CONCAT.equals(token)) {
            updatePaths();
        } else if (DELIMINATOR_OPTION.equals(token)) {
            // nothing to do
        } else {
            stack.add(token);
        }
    }

    private void updatePaths() {
        final List<String> originalPaths = new ArrayList<String>(paths);
        paths.clear();
        while (stack.size() > 0) {
            paths.addAll(createNewPaths(originalPaths));
        }
    }

    private List<String> createNewPaths(final List<String> originalPaths) {
        final List<String> newPaths = new ArrayList<String>(originalPaths);
        addPart(newPaths, stack.remove(0));
        addPart(newPaths, DELIMINATOR_CONCAT);
        return newPaths;
    }

    private void addPart(final List<String> paths, final String part) {
        for (int i = 0; i < paths.size(); i++) {
            paths.set(i, paths.get(i) + part);
        }
    }

    private StringTokenizer createStringTokenizer(final String pathSpec) {
        final boolean returnDelimiters = true;
        final String delimiters = DELIMINATOR_CONCAT + DELIMINATOR_OPTION;
        return new StringTokenizer(pathSpec, delimiters, returnDelimiters);
    }

    public static void main(final String[] args) {
        final PathParser pathParser = new PathParser();
        final String input = "element1-element2-element3-element4a|element4b|element4c-element5-element6a|element6b|element6c";
        System.out.println("Input");
        System.out.println(input);
        System.out.println();

        final List<String> paths = pathParser.parse(input);

        System.out.println("Output");
        for (final String path : paths) {
            System.out.println(path);
        }
    }
}

输出:

Input
element1-element2-element3-element4a|element4b-element5-element6a|element6b

Output
element1-element2-element3-element4a-element5-element6a-
element1-element2-element3-element4b-element5-element6a-
element1-element2-element3-element4a-element5-element6b-
element1-element2-element3-element4b-element5-element6b-

答案 4 :(得分:0)

这有助于实现相同的目标..

public class MultiStringSplitter {
    public static void main(String arg[]) {
        String input = "a-b|c-d|e-f|g-h";
        String[] primeTokens = input.split("-");
        String[] level2Tokens = null;
        String element = "";
        String level2element = "";
        ArrayList stringList = new ArrayList();
        ArrayList level1List = new ArrayList();
        ArrayList level2List = new ArrayList();

        for (int i = 0; i < primeTokens.length; i++) {
            // System.out.print(primeTokens[i]);


            if (primeTokens[i].contains("|")) {
                level2Tokens = primeTokens[i].split("\\|");
                for (int j = 0; j < level2Tokens.length; j++) {
                    for (int k = 0; k < stringList.size(); k++) {
                        element = (String) stringList.get(k);
                        level2element = element + level2Tokens[j];
                        level2List.add(level2element);
                    }
                }
                stringList = new ArrayList();
                for (int w = 0; w < level2List.size(); w++) {
                    stringList.add(level2List.get(w));
                }
                level2List = new ArrayList();

            }
            else {
                if (stringList.size() > 0) {
                    for (int z = 0; z < stringList.size(); z++) {
                        element = (String) stringList.get(z);
                        element = element + primeTokens[i];
                        level1List.add(element);
                    }
                    stringList = new ArrayList();
                    for (int w = 0; w < level1List.size(); w++) {
                        stringList.add(level1List.get(w));
                    }
                    level1List = new ArrayList();

                }
                else {
                    element = element + primeTokens[i];
                    if (stringList.size() == 0) {
                        stringList.add(element);
                    }
                }
            }
        }

        for (int q = 0; q < stringList.size(); q++) {
            System.out.println(stringList.get(q));
        }
    }
}  

输入:a-b|c-d|e-f|g-h

输出:

    abdfh
    acdfh
    abefh
    acefh
    abdgh
    acdgh
    abegh
    acegh