Java 反转堆栈并添加到 ArrayList 的最有效方法

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/1245060/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-12 07:24:00  来源:igfitidea点击:

Most efficient way to reverse a stack and add to an ArrayList

javadata-structuresperformancestackarraylist

提问by Dave Morgan

I have two collections - an ArrayList and a Stack. I use the stack because I needed some simple pop/push functionality for this bit of code. The ArrayList is essentially the out variable as this is a small section of code in the function.

我有两个集合 - 一个 ArrayList 和一个 Stack。我使用堆栈是因为我需要一些简单的弹出/推送功能来处理这段代码。ArrayList 本质上是 out 变量,因为这是函数中的一小部分代码。

So, the variables are defined as such, then code is run to add elements to the stack.

因此,变量被定义为这样,然后运行代码以将元素添加到堆栈中。

ArrayList<String> out = new ArrayList<String>();

/* other code.. */

Stack<String> lineStack = new Stack<String>();

/* code that adds stuff to the stack */

The question is, now that I have a fully populated stack, how do I place it in the out ArrayList in a reverse order then from the pop order.

问题是,既然我有一个完全填充的堆栈,我如何将它以与弹出顺序相反的顺序放置在 out ArrayList 中。

My first thought up solution was

我第一个想到的解决方案是

 while(!lineStack.empty()) {
     out.add(0, lineStack.pop());
 }

... which works, but I worry about the efficiency of adding an element to the beginning of the ArrayList (which forces all existing elements to need to shift.. it's a linked list (I believe).. big deal.. but still a concern). Also, I am running this through a loop... perhaps unnecessarily.

...这是有效的,但我担心将元素添加到 ArrayList 开头的效率(这会强制所有现有元素需要移动......它是一个链表(我相信)......大不了......但仍然在意)。此外,我正在通过一个循环运行它......也许是不必要的。

So, my second solution that didn't involve looping (at least in my code, i'm sure the back end calls are doing it).

所以,我的第二个解决方案不涉及循环(至少在我的代码中,我确定后端调用正在这样做)。

 List l = lineStack.subList(0, lineStack.size());
 out.addAll(l);

I know I don't need to allocate the list, but it'll keep for cleaner code. However, I am not sure if this will give me a particularly helpful performance gain.

我知道我不需要分配列表,但它会保留更清晰的代码。但是,我不确定这是否会给我带来特别有用的性能提升。

So, my question is: Which of these will likely be most efficient for SMALL to MEDIUM size sets? If there is a more efficient solution, what would it be?

所以,我的问题是:对于小型到中型尺寸的套装,哪些可能最有效?如果有更有效的解决方案,那会是什么?

采纳答案by Jon Skeet

The Iterable<T>implementation order of Stack<T>goes in the order you want anyway, so you can just use

Iterable<T>实现顺序Stack<T>无论如何都按照您想要的顺序进行,因此您可以使用

new ArrayList<String>(stack);

Here's a short but complete example:

这是一个简短但完整的示例:

import java.util.*;

public class Test
{
    public static void main(String[] args)
    {
        Stack<String> stack = new Stack<String>();
        stack.push("Bottom");
        stack.push("Middle");
        stack.push("Top");

        List<String> list = new ArrayList<String>(stack);

        for (String x : list)
        {
            System.out.println(x);
        }
    }
}

This prints out:

这打印出来:

Bottom
Middle
Top

(which is the opposite order to what you'd get if you popped them).

(这与弹出它们时得到的顺序相反)。

EDIT: One other question - do you really need it in an ArrayList<String>anyway? Stack<T>implements List<T>; what special features of ArrayListdo you need? (I'm not saying you don'tneed them, just checking!)

编辑:另一个问题 - 你真的需要它ArrayList<String>吗?Stack<T>实施List<T>; ArrayList你需要什么特殊功能?(我不是说你没有需要他们,只是检查!)

回答by Toad

Subclass the ArrayList and add a pop and push method. Use this as the Stack class.

继承 ArrayList 并添加一个 pop 和 push 方法。将此用作 Stack 类。

When you are ready, assign it to an Arraylist variable and you're ready

准备好后,将其分配给一个 Arraylist 变量,您就准备好了

回答by dfa

making use of Stack.toArray is simple:

使用 Stack.toArray 很简单:

@Test
public void stackToList() {
    Stack<String> stack = new Stack<String>();
    stack.push("aaa");
    stack.push("bbb");
    stack.push("ccc");
    List<String> list=  Arrays.asList(stack.toArray(new String[0]));
    Assert.assertEquals(Arrays.asList("aaa", "bbb", "ccc"), list);
}

回答by Spork Witch

If you don't need it as an array, but another stack would work, why not:

如果您不需要它作为数组,但另一个堆栈可以工作,为什么不:

Stack<String> reversedStack = new Stack<String>(); while (!oldStack.empty()) { reversedStack.push(oldStack.pop()); }

Stack<String> reversedStack = new Stack<String>(); while (!oldStack.empty()) { reversedStack.push(oldStack.pop()); }

Quick, simple, and easy to see what it's doing.

快速、简单且易于查看它在做什么。

回答by Anand Immannavar

Stack is subclass of Collections and Collections has reverse method, So you can just do -

Stack 是 Collections 的子类,Collections 有reverse 方法,所以你可以这样做 -

   Stack originalStack = ...
   Collections.reverse(originalStack);