词语搜索算法思想 - 第四步 拼音组合

第三步已经完成了词语的拼音转换,但是我们要解决汉字多音词产生的多种组合问题。

这个问题,我们先看下快速解决方式:

	public static void main(String[] args) {
//		String item = "娱乐八卦";
//		System.out.println(Arrays.toString(split(item)));
//		System.out.println(Arrays.toString(split("ylbg")));
//		System.out.println(Arrays.toString(split("yu,le,ba,gua")));
//		ArrayList<String[]> list = pinyin(item);
//		for (String[] arr : list) {
//			System.out.println(Arrays.toString(arr));
//		}
		System.out.println(Arrays.toString(composite()));
	}

	/**
	 * 拼音组合
	 */
	public static String[] composite() {
		String [] p1 = {"1", "2"};
		String [] p2 = {"3"};
		String [] p3 = {"4", "5"};
		String [] p4 = {"6"};
		
		ArrayList<String> list = new ArrayList<String>();
		for (int i = 0; i < p1.length; i++)
			for (int j = 0; j < p2.length; j++)
				for (int m = 0; m < p3.length; m++)
					for (int n = 0; n < p4.length; n++)
						list.add(p1[i] + p2[j] + p3[m] + p4[n]);
		return list.toArray(new String[list.size()]);
	}

输出:

[1346, 1356, 2346, 2356]

很理想,但是我们需要的是传入“ArrayList<String[]> list = pinyin(item);”,而上面我们的composite()方法是写死的多重循环得到的结果。

递归是一个思路,但是我们换个角度思考,可能会有新发现,因为大部分递归都隐藏一个非递归替代方法。

首先,我们得到的数据是一个二维数组:

String [] p1 = {"1", "2"};
String [] p2 = {"3"};
String [] p3 = {"4", "5"};
String [] p4 = {"6"};

每个数组的循环无非就是数组下标的移动,多个数组递归循环,无非就是p1的下标先移动,然后p2下标移动、然后p3下标移动、然后p4下标移动:

package test;

import java.lang.reflect.Array;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
/**
 * 多维数组组合类
 */
public class CompositeUtil<T extends Object> {
	private List<T[]> input;
	private T t = null;

	public CompositeUtil(List<T[]> input) {
		this.input = input;
		this.t = input.iterator().next()[0];
	}

	public List<T[]> getResult() {
		List<T[]> result = new ArrayList<T[]>();
		int[] counter = new int[this.input.size()]; // 下标数组
                // 监视下标移动
		System.out.println(Arrays.toString(counter));
		do {
			T[] aResult = getCurComposite(counter);
			result.add(aResult);
		} while (!incCounter(counter));
		return result;
	}

	private boolean incCounter(int[] counter) {
		boolean overflow = true;
		for (int i = 0; i < counter.length; i++) {
			T[] elementArray = (T[]) this.input.get(i);
			if (counter[i] < elementArray.length - 1) {
				counter[i]++;
				overflow = false;
				break; // 每次增加一个,后跳出循环
			} else {
				counter[i] = 0;
			}
		}
		// 监视下标移动
		System.out.println(Arrays.toString(counter));
		return overflow;
	}

	@SuppressWarnings("unchecked")
	private T[] getCurComposite(int[] counter) {
		T[] result = (T[]) Array.newInstance(t.getClass(), counter.length);//
		for (int i = 0; i < counter.length; i++) {
			T[] elementArray = (T[]) this.input.get(i);
			result[i] = elementArray[counter[i]];
		}
		return result;
	}

	public static void main(String[] args) {
		String[] array1 = { "1", "7" };
		String[] array2 = { "2", "3" };
		String[] array3 = { "4", "5", "6"};
		List<String[]> pinyinList = new ArrayList<String[]>();
		pinyinList.add(array1);
		pinyinList.add(array2);
		pinyinList.add(array3);
		
		CompositeUtil<String> t = new CompositeUtil<String>(pinyinList);
		List<String[]> list = t.getResult();
		System.out.println("===================================");
		for (String[] strings : list) {
			System.out.println(Arrays.toString(strings));
		}
	}
}

输出:

[0, 0, 0]
[1, 0, 0]
[0, 1, 0]
[1, 1, 0]
[0, 0, 1]
[1, 0, 1]
[0, 1, 1]
[1, 1, 1]
[0, 0, 2]
[1, 0, 2]
[0, 1, 2]
[1, 1, 2]
[0, 0, 0]
===================================
[1, 2, 4]
[7, 2, 4]
[1, 3, 4]
[7, 3, 4]
[1, 2, 5]
[7, 2, 5]
[1, 3, 5]
[7, 3, 5]
[1, 2, 6]
[7, 2, 6]
[1, 3, 6]
[7, 3, 6]

呵呵,运行正常。

现在我们把这个组合类使用到第三步,把多音词组合起来:

	public static void main(String[] args) {
		String item = "娱乐八卦";
//		System.out.println(Arrays.toString(split(item)));
//		System.out.println(Arrays.toString(split("ylbg")));
//		System.out.println(Arrays.toString(split("yu,le,ba,gua")));
		ArrayList<String[]> list = pinyin(item);
		for (String[] arr : list) {
			System.out.println(Arrays.toString(arr));
		}
		CompositeUtil<String> t = new CompositeUtil<String>(list);
		for (String[] strings : t.getResult()) {
			System.out.println(Arrays.toString(strings));
		}
//		System.out.println(Arrays.toString(composite()));
	}

输出:

[yu]
[le, yue]
[ba]
[gua]
[yu, le, ba, gua]
[yu, yue, ba, gua]

组合的数组已经好了。

你可能感兴趣的:(算法,思想,搜索,词语)