我在打印MergeSort时遇到问题。我需要帮助打印出每个一步一步的过程,因为它正在对ArrayList进行排序。
以下示例来自InsertionSort,因为我在每次交换ArrayList中的两个元素时都会打印它:
11 79 60 45 START
11 79 60 45
11 60 79 45
11 45 60 79结束
有没有为MergeSort做这个,同时从头到尾显示整个数组(如上所述?)
代码:
import java.util.ArrayList;
public class Merge
{
public static void main (String [] args)
{
Merge run = new Merge();
run.test();
}
public void test ( )
{
ArrayList<Integer> numbers = new ArrayList<Integer>();
for (int i = 0; i < 16; i++)
{
numbers.add(new Integer(1 + (int)(Math.random() * 100)));
}
printArray(numbers);
mergeSort(numbers);
printArray(numbers);
}
public void printArray (ArrayList<Integer> array)
{
System.out.println("\n\n");
for (int i = 0; i < array.size(); i++)
{
System.out.printf("%-5d",array.get(i).intValue());
}
System.out.println("\n\n");
}
public void mergeSort (ArrayList<Integer> array)
{
int length = array.size();
if (length < 2)
{
return; // the array is already sorted in this case
}
// divide
ArrayList<Integer> array1 = new ArrayList<Integer>();
ArrayList<Integer> array2 = new ArrayList<Integer>();
int i = 0;
while (i < length/2)
{
array1.add(array.remove(0)); // move the first n/2 elements to array1
i++;
}
while (!array.isEmpty())
{
array2.add(array.remove(0)); // move the rest to array2
}
mergeSort(array1);
mergeSort(array2);
merge(array1,array2,array);
}
public void merge (ArrayList<Integer> array1, ArrayList<Integer> array2, ArrayList<Integer> array)
{
while (!array1.isEmpty() && !array2.isEmpty())
{
if ((array1.get(0).compareTo(array2.get(0)) <= 0))
{
array.add(array1.remove(0));
}
else
{
array.add(array2.remove(0));
}
}
while(!array1.isEmpty()) // move the remaining elements of array1
{
array.add(array1.remove(0));
}
while(!array2.isEmpty()) // move the remaining elements of array2
{
array.add(array2.remove(0));
}
}
}
答案 0 :(得分:2)
如果你将一些偏移量传递给mergeSort
,你可以将子阵列打印到你完成交换时缩进到完整数组中的位置,但是因为你只传递部分的如果阵列向下,您将无法以这种方式显示完整的阵列。但是,有一种更快的方法可以让你。
不是创建新数组并传递它们,而是传递数组和2个索引,即开始和结束点。因此,您对第一个说mergeSort(array, 0, n)
,然后对递归调用说mergeSort(array, 0, n/2)
和mergeSort(array, n/2, n)
。你只在这些范围内进行拆分和合并。然后在合并时,可以打印出整个合并的数组。这将显示每次合并的步骤。在底层,它将显示1-1交换(如果它发生)。这是唯一的&#34;一步一步&#34;你可以在合并排序中看到。
答案 1 :(得分:1)
没有看到你的代码,很难确切知道,但我从这里抓住了一个Mergesort实现:http://www.vogella.de/articles/JavaAlgorithmsMergesort/article.html。
我已将其更新为您想要的打印效果。
public class Mergesort
{
private int[] numbers;
private int[] helper;
private int number;
public void sort(int[] values)
{
this.numbers = values;
number = values.length;
this.helper = new int[number];
System.out.println("START");
mergesort(0, number - 1);
System.out.println("END");
}
private void mergesort(int low, int high)
{
// Check if low is smaller then high, if not then the array is sorted
if (low < high)
{
// Get the index of the element which is in the middle
int middle = (low + high) / 2;
// Sort the left side of the array
mergesort(low, middle);
// Sort the right side of the array
mergesort(middle + 1, high);
// Combine them both
merge(low, middle, high);
}
}
private void merge(int low, int middle, int high)
{
// Copy both parts into the helper array
for (int i = low; i <= high; i++)
{
helper[i] = numbers[i];
}
int i = low;
int j = middle + 1;
int k = low;
// Copy the smallest values from either the left or the right side back
// to the original array
while (i <= middle && j <= high)
{
if (helper[i] <= helper[j])
{
numbers[k] = helper[i];
i++;
}
else
{
numbers[k] = helper[j];
j++;
}
k++;
}
// Copy the rest of the left side of the array into the target array
while (i <= middle)
{
numbers[k] = helper[i];
k++;
i++;
}
}
private void printArray()
{
for(int x : numbers)
System.out.print(x + " ");
System.out.println(" ");
}
}
如果您不想打印到控制台,可以将输出构建为输出的String,并在完成后将其返回。
答案 2 :(得分:1)
这是一个小的Merge排序算法程序。我复制了算法 http://en.wikipedia.org/wiki/Merge_sort。您可以将其作为JUnittest运行或运行main方法。
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import junit.framework.TestCase;
/**
* Simple MergeSortTest
*/
public class MergeSortTest extends TestCase {
private static int FIRST_ENTRY = 0;
public static void main(String[] args) {
MergeSortTest mergesorttest = new MergeSortTest();
Integer [] unsortedInt = {1,38, 27, 110, 9, 82, 10, 100, 299, 13};
List<Integer> unsorted = Arrays.asList(unsortedInt);
List<Integer> sorted = mergesorttest.mergeSort(unsorted);
System.out.println(sorted.toString());
}
public void testMergeSort() {
Integer [] unsortedInt = {1,38, 27, 110, 9, 82, 10, 100, 299, 13};
List<Integer> unsorted = Arrays.asList(unsortedInt);
List<Integer> sorted = mergeSort(unsorted);
assertEquals("[1, 9, 10, 13, 27, 38, 82, 100, 110, 299]", sorted.toString());
}
private List<Integer> mergeSort(List<Integer> list) {
List<Integer> result;
List<Integer> left = new ArrayList<Integer>();
List<Integer> right = new ArrayList<Integer>();;
int middle;
int counter;
if (list.size() <= 1) {
return list;
}
middle = list.size() / 2;
for (counter = 0; counter < middle; counter++) {
left.add(list.get(counter));
}
for (counter = middle; counter < list.size(); counter++) {
right.add(list.get(counter));
}
left = mergeSort(left);
right = mergeSort(right);
result = merge(left, right);
System.out.println(result);
return result;
}
private List<Integer> merge(List<Integer> left, List<Integer> right) {
List<Integer> result = new ArrayList<Integer>();
while (!left.isEmpty() || !right.isEmpty()) {
if (!left.isEmpty() && !right.isEmpty()) {
if (left.get(FIRST_ENTRY) <= right.get(FIRST_ENTRY)) {
handle(left, result);
} else {
handle(right, result);
}
} else if (!left.isEmpty()) {
handle(left, result);
} else if (!right.isEmpty()) {
handle(right, result);
}
}
return result;
}
private void handle(List<Integer> list, List<Integer> result) {
if (!list.isEmpty()) {
result.add(list.get(FIRST_ENTRY));
list.remove(FIRST_ENTRY);
}
}
}