Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Linked list vs. dynamic array for implementing a stack

I've started reviewing data structures and algorithms before my final year of school starts to make sure I'm on top of everything. One review problem said "Implement a stack using a linked list or dynamic array and explain why you made the best choice".

To me, it seemed more intuitive to use a list with a tail pointer to implement a stack since it may need to be resized often. It seems like for a large amount of data, a list is the better choice since a dynamic array re-size is an expensive operation. Additionally, with a list, you don't need to allocate any more space than you actually need so it's more space efficient.

However, a dynamic array would definitely allow for adding data far quicker (except when it needs to be resized). However, I'm not sure if using an array is overall quicker, or only if it doesn't need to be resized.

The book's solution said "for storing very large objects, a list is a better implementation" but I don't understand why.

Which way is best? What factors should be used to determine which implementation is "best"? Also, is any of my logic here off?

like image 410
Casey Patton Avatar asked Sep 13 '11 23:09

Casey Patton


People also ask

Is it better to implement stack with array or linked list?

The linked list versions have better worst-case behavior, but may have a worse overall runtime because of the number of allocations performed. The array versions are slower in the worst-case, but have better overall performance if the time per operation isn't too important.

Is linked list better for stack?

While a LinkedList provides all the operations that are needed to make a stack, it will perform poorly. Linked lists are good for inserting and removing elements at random positions. In a stack, we only ever append to or remove from the end which makes an ArrayList much more appealing to implement a stack.

Can stack be implemented using dynamic array?

Stack/ Stack Using Dynamic Array (Both Incremental and Doubling Strategy). Implementing stack using Dynamic Array to overcome the exception of Overflow when the array gets full. 3) Second approach is to increase the size of new array by twice. 4) Comparing the Time complexity in both the cases.

Which implementation of stack is best?

There is no better or worse approach to implement a stack but they have different advantages. Implementation based on linked list gives you more flexibility over the container's capacity since you can theoretically always add more elements to it. Array based stack is more limited in terms of capacity.


2 Answers

There are many tradeoffs involved here and I don't think that there's a "correct" answer to this question.

If you implement the stack using a linked list with a tail pointer, then the worst-case runtime to push, pop, or peek is O(1). However, each element will have some extra overhead associated with it (namely, the pointer) that means that there is always O(n) overhead for the structure. Additionally, depending on the speed of your memory allocator, the cost of allocating new nodes for the stack might be noticeable. Also, if you were to continuously pop off all the elements from the stack, you might have a performance hit from poor locality, since there is no guarantee that the linked list cells will be stored contiguously in memory.

If you implement the stack with a dynamic array, then the amortized runtime to push or pop is O(1) and the worst-case cost of a peek is O(1). This means that if you care about the cost of any single operation in the stack, this may not be the best approach. That said, allocations are infrequent, so the total cost of adding or removing n elements is likely to be faster than the corresponding cost in the linked-list based approach. Additionally, the memory overhead of this approach is usually better than the memory overhead of the linked list. If your dynamic array just stores pointers to the elements, then the memory overhead in the worst-case occurs when half the elements are filled in, in which case there are n extra pointers (the same as in the case when you were using the linked list), and in the best case when the dynamic array is full there are no empty cells and the extra overhead is O(1). If, on the other hand, your dynamic array directly contains the elements, the memory overhead can be worse in the worst-case. Finally, because the elements are stored contiguously, there is better locality if you want to continuously push or pop elements from the stack, since all the elements are right next to each other in memory.

In short:

  • The linked-list approach has worst-case O(1) guarantees on each operation; the dynamic array has amortized O(1) guarantees.
  • The locality of the linked list is not as good as the locality of the dynamic array.
  • The total overhead of the dynamic array is likely to be smaller than the total overhead of the linked list, assuming both store pointers to their elements.
  • The total overhead of the dynamic array is likely to be greater than that of the linked list if the elements are stored directly.

Neither of these structures is clearly "better" than the other. It really depends on your use case. The best way to figure out which is faster would be to time both and see which performs better.

Hope this helps!

like image 141
templatetypedef Avatar answered Oct 02 '22 10:10

templatetypedef


Well, for the small objects vs. large objects question, consider how much extra space to use for a linked list if you've got small objects on your stack. Then consider how much extra space you'll need if you've got a bunch of large objects on your stack.

Next, consider the same questions, but with an implementation based on dynamic arrays.

like image 35
Pillsy Avatar answered Oct 02 '22 09:10

Pillsy