我的任务是在java中创建一个Deque,其中包括向左添加,向右添加,向左删除和向右删除的选项。
我已经对添加权进行了编码并成功删除了正确的方法但是我在尝试添加左侧并删除左侧工作时遇到了问题。
我想我在某个地方犯了大错。我刚刚尝试交换变量以便添加左边并反转计算,这些计算不起作用,并且会提出以下内容:
Exception in thread "main" java.lang.OutOfMemoryError: Java heap space
at java.util.Arrays.copyOf(Arrays.java:3332)
at java.lang.AbstractStringBuilder.expandCapacity(AbstractStringBuilder.java:137)
at java.lang.AbstractStringBuilder.ensureCapacityInternal(AbstractStringBuilder.java:121)
at java.lang.AbstractStringBuilder.append(AbstractStringBuilder.java:421)
at java.lang.StringBuffer.append(StringBuffer.java:265)
at datastructuresass1.DendQueue.toString(DendQueue.java:107)
at datastructuresass1.main.main(main.java:21)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:497)
at com.intellij.rt.execution.application.AppMain.main(AppMain.java:147)
我正在尝试使用数组创建双端队列。下面是我添加权限的代码并添加左方法:
添加左(不起作用)
public void addLeft(T o){
left = (left + 1) % arr.length;
arr[left] = o;
// if the array is full copy it to a larger one
if ((left + 1) % arr.length == right) {
T[] newarr = (T[]) new Object[arr.length * 2];
int i;
for (i = 0; i < arr.length; i++)
newarr[i] = arr[(right - i) % arr.length];
arr = newarr;
left = i - 1;
right = 0;
System.out.println("Array size increased to " +
arr.length);
}
添加权利(正在运作)
public void addRight(T o) {
right = (right + 1) % arr.length;
arr[right] = o;
// if the array is full copy it to a larger one
if ((right + 1) % arr.length == left) {
T[] newarr = (T[]) new Object[arr.length * 2];
int i;
for (i = 0; i < arr.length; i++)
newarr[i] = arr[(left + i) % arr.length];
arr = newarr;
left = 0;
right = i - 1;
System.out.println("Array size increased to " +
arr.length);
}
请有人向我解释为什么这个addLeft方法不起作用。这将是一个很大的帮助,因为我已经被困在这一段时间了!提前致谢。
答案 0 :(得分:0)
使用数组非常低效,尝试使用链表更容易! 并且对于队列来说更合适(更快),因为它不需要所有内存复制来添加和删除对象。它有addfirst和addlast等方法。
LinkedList是标准Java库的一部分:https://docs.oracle.com/javase/7/docs/api/java/util/LinkedList.html
请参阅https://en.wikipedia.org/wiki/Linked_list#Doubly_linked_list了解其工作原理
如果你的老师强迫你使用阵列,那么他就是坚果:D
答案 1 :(得分:0)
交换变量不够。
看起来left
计算似乎错误:left = (left + 1) % arr.length;
。你不应该递增,而是递减它。与right
不同,您使用模数(%
)运算符回绕0
。但left
必须处理简单的if
条件。
if (left - 1 < 0) //if left is going less than zero,
left = arr.length - 1; //wrap it back to the end of the array
else
left = left - 1; //else do normal decrement
arr[left] = o;
// if the array is full copy it to a larger one
// if left is at the begining & right's at the ending, then we're full
if ((left == 0 && right == arr.length - 1)
// or if decrementing leftwards reaches right, we're full
|| left - 1 == right) {
在数组复制循环中,无论向右或向左添加使数组都满,复制逻辑将保持不变。您只需将left
到right
的所有元素复制到0
到2n
的新数组中。因此,无需在数组复制逻辑中交换变量。您可以重复使用addRight()
中的逻辑。
希望这有助于朝着正确的方向前进。在您提供完整代码+触发该错误的测试用例之前,我无法重现您遇到的错误。
如果您还没有意识到,那么使用循环数组here就可以实现Deque。你可以学习&amp;了解哪里&amp;你为什么出错了此外,增加前/后声音比右/左更容易混淆。 :)