题目:
输入一个字符串数组,输出它的所有组合。
输入:[“id”,“name”,“age”]
输出:
[ [“id”],
[“name”],
[“age”],
[“id”,“name”],
[“id”,“age”],
[“name”,“age”],
[“id”,“name”,“age”]]
思路:
1.通过遍历长度来求出每个长度的所有组合。
2.访问到当前值的时候,它的组合有两个选择.
1)一是我要这个元素作为组合成员,那么就将其放入组合数组,递归求后面的,同时剩余长度-1;
2)二是我不要当前元素作为组合成员,那么就将前面加的这个元素删除,递归求后面的,此时剩余长度不变。
代码:
import java.util.*;
public class allCombine {
public static void main(String[] args) {
Scanner in=new Scanner(System.in);
//保存结果的二维数组
ArrayList<ArrayList<String>> data=new ArrayList<>();
//保存输入的数组
ArrayList<String> arr=new ArrayList<>();
//用于下面函数使用,记录每个组合的成员
ArrayList<String> temp=new ArrayList<>();
//输入
while(in.hasNext()) {
String d=in.nextLine();
if(d.equals("end")) break;
arr.add(d);
}
String[] arrs=new String[arr.size()];
arr.toArray(arrs);
int n=arrs.length+1;
//核心思想:根据组合的长度不同来划分,遍历长度1-len,依次计算每个长度的组合都有哪些
for(int i=1;i<n;i++) {
//求组合的核心算法
combine(data, arrs, 0, i, temp);
}
//输出
for(int i=0;i<data.size();i++) {
for(int j=0;j<data.get(i).size();j++) {
System.out.print(data.get(i).get(j)+" ");
}
System.out.println();
}
}
//求组合的核心算法,参数依次为:结果集,输入的数组,遍历输入数组的下标,当前组合的长度,当前组合的成员存放数组
public static void combine(ArrayList<ArrayList<String>> res, String[] arr, int start, int len, ArrayList<String> temp) {
//如果没有剩余的长度了,即此时的temp中存放了足够的成员,即输出到结果集,需要注意的是要新new一个ArrayList,若只用一个的话,它的值会跟着后面改变而改变
if(len==0) {
ArrayList<String> t=new ArrayList<>();
for(String a:temp) t.add(a);
res.add(t);
return;
}
//遍历完数组,退出
if(start>=arr.length) return;
//要当前值
temp.add(arr[start]);
combine(res, arr, start+1, len-1, temp);
//不要当前值
temp.remove(temp.size()-1);
combine(res, arr, start+1, len, temp);
}
}