有一个数组,每隔两个数删掉一个数,到末尾又循环到开头继续进行,求最后一个被删除的数的原始下标位置

源代码中有较详细的注释,这里就不多写了。

/**
 * 有一个数组a[N],要求每隔两个数删掉一个数,到末尾则又循环到开头继续进行
 * 求最后一个被删掉的数的原始下标位置
 * 
 *  例如,一个数组:{0, 1, 2, 3, 4, 5, 6, 7} 
 *  0->1->2(第一遍,删除)->3->4->5(第一遍,删除)->6->7->
 *  0(第二遍,删除)->1->2(已删除)->3->4(第二遍,删除)->5(已删除)->6->7...
 *  循环直到数组中最后一个元素被删除
 *  
 *  当然,这里并未真正删除元素,只是用标志位表示已经被删除
 * 
 * @author Wll
 *
 */
public class DeleteEveryTwo {
	public static void main(String[] args) {
		int index = getLastDeletedIndex(8);
		System.out.println("The last index deleted is " + index);
	}

	/**
	 * 
	 * @param a
	 *            数组长度
	 * @return 最后被删除的数的原始下标
	 */
	public static int getLastDeletedIndex(int len) {
		if (len <= 0) { // 如果数组长度不满足要求则返回 -1
			return -1;
		}

		int[] arr = new int[len];
		for (int i = 0; i < len; i++) { // 初始化每个元素的值为当前下标
			arr[i] = len;
		}

		final int DELFLAG = len + 1; // 删除标志位
		int currentSize = len; // 记录数组当前有效长度(即未被置为删除标志的元素个数),最后变为 0
		final int STEP = 2; // 步长
		int count = 0; // 步长计数
		int lastDelIndex = 0; // 记录最后被删除的元素的下标
		int i = 0; // 循环下标

		while (currentSize != 0) {
			if (arr[i] != DELFLAG) { // 判读当前元素是否等于删除标志
				if (count++ == STEP) { // 当步长计数满足步长则
					arr[i] = DELFLAG; // 将元素置为删除标志位
					lastDelIndex = i; // 记录该处下标
					currentSize--; // 有效数组长度减 1
					count = 0; // 步长计数归零
					System.out.println("Deleted index is " + i % len);
				}
			}
			i = (i + 1) % len; // 下标取余实现循环下标
		}
		return lastDelIndex;
	}
}


你可能感兴趣的:(排序算法)