作为一项学校作业,我应该使用至少2个线程进行多线程快速排序算法,但是我的代码出现了一些问题,我似乎无法修复。
编辑:这是它不是多线程时的样子。我已经确认这有效。
public class Sorter
{
private int[] mInts;
public void QuickSort()
{
QuickSort(mInts, 0, mInts.Length - 1);
}
public Sorter(int[] ints)
{
mInts = ints;
}
private int Partition(int[] ints, int left, int right)
{
int pivotIndex = (right + left) / 2;
int pivotValue = ints[pivotIndex];
Swap(ints, right, pivotIndex);
int storeIndex = left;
for (int i = left; i <= right - 1; i++)
{
if (ints[i] < pivotValue)
{
Swap(ints, storeIndex, i);
storeIndex++;
}
}
Swap(ints, storeIndex, right);
return storeIndex;
}
private void Swap(int[] ints, int x, int y)
{
int temp = ints[x];
ints[x] = ints[y];
ints[y] = temp;
}
private void QuickSort(int[] ints, int left, int right)
{
if (left < right)
{
int newIndex = Partition(ints, left, right);
QuickSort(ints, left, newIndex - 1);
QuickSort(ints, newIndex + 1, right);
}
}
以上工作正常,下面的代码没有。现在它没有正确排序,在我看来,加粗的代码片段必须位于其他地方......或者什么?我很难理解线程编程,所以我希望有人可以给我一些关于如何解决这个问题的指示,而不必在可能的情况下重构我的整个程序。下面是我使用线程版本的程度。
public class Sorter
{
private int[] mInts;
Thread myThread = null;
int numThreads = 0;
int maxThreads = 10;
public void QuickSort()
{
QuickSort(mInts, 0, mInts.Length - 1);
}
public Sorter(int[] ints)
{
mInts = ints;
}
private int Partition(int[] ints, int left, int right)
{
int pivotIndex = (right + left) / 2;
int pivotValue = ints[pivotIndex];
Swap(ints, right, pivotIndex);
int storeIndex = left;
for (int i = left; i <= right - 1; i++)
{
if (ints[i] < pivotValue)
{
Swap(ints, storeIndex, i);
storeIndex++;
}
}
Swap(ints, storeIndex, right);
return storeIndex;
}
private void Swap(int[] ints, int x, int y)
{
int temp = ints[x];
ints[x] = ints[y];
ints[y] = temp;
}
private void QuickSort(int[] ints, int left, int right)
{
if (left < right)
{
int newIndex = Partition(ints, left, right);
if (numThreads < maxThreads)
{
numThreads++;
myThread = new Thread(new ParameterizedThreadStart(startSort));
myThread.Start(new SortParameters(this, ints, left, newIndex - 1));
**QuickSort(ints, newIndex + 1, right);**
}
}
}
static void startSort(Object obj)
{
SortParameters sortParams = (SortParameters)obj;
sortParams.instance.QuickSort(sortParams.ints, sortParams.left, sortParams.right);
}
public class SortParameters
{
public Sorter instance;
public int[] ints;
public int left;
public int right;
public SortParameters(Sorter instance, int[] ints, int left, int right)
{
this.instance = instance;
this.ints = ints;
this.left = left;
this.right = right;
}
}
}
感谢您的帮助!
答案 0 :(得分:0)
问自己以下几点:
n
元素运行多少个线程?我在下面提供了我的解决方案,但您可能想先自己考虑一下。
以下是我的答案:
理论上,您的代码将计算log 2 (n)quicksorts,因为它在分区后将每个排序分为2个子查询。在您的线程版本中,您为每个子查询启动一个补充线程,因此总共可以启动多个线程。
您提供的代码实际上限制了maxThreads
值的已启动线程数。所以实际上,如果log 2 (n
)&gt; maxThreads
,即。如果n
&gt; 2 maxThreads
,代码将达到可能的并发线程的最大数量。
在线程代码中,在突出显示的部分周围,对该最大值的测试决定了任何递归调用的执行。因此,如果n
高于第2点中提到的限制,代码将停止正常工作。
修复很简单,添加else
子句以完成当前线程的排序。
if (numThreads < maxThreads)
{
numThreads++;
myThread = new Thread(new ParameterizedThreadStart(startSort));
myThread.Start(new SortParameters(this, ints, left, newIndex - 1));
}
else {
QuickSort(ints,left,newIndex - 1);
}
QuickSort(ints, newIndex + 1, right);
正如你所看到的,我也从测试中移出了当前线程将运行的部分。