stack.clear() faster or popping each element faster? - java

Similarly, to find the no of elements in a stack, is stack.size() call faster than popping each element and counting? Of course I don't need the stack anymore.

Stack inherits from Vector, and Vector is the class that defines the size() method, not Stack. Vector also has a protected field called elementCount, which is the number of valid elements in the Vector. I would assume that the size() method just returns this variable, making it much faster to call size() than to pop and count. Also, Vector has no need to do pops to count elements because popping is not a feature of Vector.

The answer depends on the implementation of the Stack class, but logically popping n times cannot be faster than obtaining count and calling clear: it is an O(n) algorithm.
Obtaining count, on the other hand, could be faster, because it can be done in a single access if Stack stores the number of items that it has, making it an O(1)* algorithm. Similarly, clearing the whole content in one go can be implemented as an O(1).
* O(1) is a fancy way of saying "does not depend on the number of elements on the stack".

You can write two functions and test your problem with those functions, you'll learn and figure out your question. Write one function popping each element, pushing it in another stack, and when finished push it all back in the original array (you want to keep the integrity of your stack when calling .size(), the size call should not modify your stack). The other with stack.size(). Then call each function in your main function and use a function like time() before and after each of the two function calls. You'll see a difference in time between the two functions. Just try it out!
Of course this depends on the implementation of the stack as mentioned in other answers. Just read the documentation of the stack interface and it should be in there.

Related

Why not use ListIterator for full LinkedList Operation?

My main question is if ListIterator or Iterator class reduces the time taken for removal of the elements from a given LinkedList and the same can be said while adding elements in the same given LinkedList using any one of the following classes above. What's the point of using the inbuilt functions of LinkedList class itself? Why should we perform any of the operations through LinkedList functions when we can use the ListIterator functions for better performance?
A ListIterator can indeed efficiently remove the node on which it is positioned. You can thus create a ListIterator, use next() two times to move the cursor, and then remove the node instantly. But evidently you did a lot of work before the actual removal.
Using ListIterator.remove is not more efficient "time complexity"-wise than removing through the LinkedList.remove(int index) if you need to construct the iterator. The LinkedList.remove method takes O(k) time, with k the index of the item you wish to remove. Removing this element with the ListIterator has the same timecomplexity since: (a) we create a ListIterator in constant time; (b) we call .next() k times, each operation in O(1); and (c) we call .remove() which is again O(1). But since we call .next() k times, this is thus an O(k) operation as well.
A similar situation happens for .add(..) on an arbitrary location (an "insert"), except that we here of course insert a node, not remove one.
Now since the two have the same time complexity, one might wonder why a LinkedList has such remove(int index) objects in the first place. The main reason is programmer's convenience. It is more convenient to call mylist.remove(5), than to create an iterator, use a loop to move five places, and then call remove. Furthermore the methods on a linked list guard against some edge-cases like a negative index, etc. By doing this manually you might end removing the first element, which might not be the intended behaviour. Finally code written is sometimes read multiple times. If a future reader reads mylist.remove(5), they understand that it removes the fifth element, wheres a solution with looping will require some extra brain cycles to understand what that part is doing.
As #Andreas says, furthermore the List interface defines these methods, and hence the LinkedList<T> should implement these.

How does java implement the conversion of LinkedList to ArrayList in Java?

I am implementing a public method that needs a data structure that needs to be able to handle insertion at two ends. Since ArrayList.add(0,key) will take O(N) time, I decide to use a LinkedList instead - the add and addFirst methods should both take O(1) time.
However, in order to work with existing API, my method needs to return an ArrayList.
So I have two approaches:
(1) use LinkedList,
do all the addition of N elements where N/2 will be added to the front and N/2 will be added to the end.
Then convert this LinkedList to ArrayList by calling the ArrayList constructor:
return new ArrayList<key>(myLinkedList);
(2) use ArrayList and call ArrayList.add(key) to add N/2 elements to the back and call ArrayList.add(0,key) to add N/2 elements to the front. Return this ArrayList.
Can anyone comment on which option is more optimized in terms of time complexity? I am not sure how Java implements the constructor of ArrayList - which is the key factor that decides which option is better.
thanks.
The first method iterates across the list:
http://docs.oracle.com/javase/1.5.0/docs/api/java/util/ArrayList.html#ArrayList(java.util.Collection)
Constructs a list containing the elements of the specified collection, in the order they are returned by the collection's iterator.
which, you can reasonably infer, uses the iterator interface.
The second method will shift elements every time you add to the front (and resize every once in a while):
http://docs.oracle.com/javase/1.5.0/docs/api/java/util/ArrayList.html#add(int, E)
Inserts the specified element at the specified position in this list. Shifts the element currently at that position (if any) and any subsequent elements to the right (adds one to their indices).
Given the official assumptions regarding the functions, the first method is more efficient.
FYI: you may get more mileage using LinkedList.toArray
I would suggest that you use an ArrayDeque which is faster than a LinkedList to insert elements at two ends and consumes less memory. Then convert it to an ArrayList using method #1.

How to allow an object to remove itself from a LinkedList in Java?

Main Question:
I'm seeking some way to give an object within a LinkedList a reference to itself within the list so that it can (efficiently) remove itself from said list (Without sorting through the list looking for itself. I'd like it to just directly cut itself from the list and tie the previous and next items together.).
Less Necessary Details:
I've done a reasonable amount of googling and not found anything other than people advising not to use circular references.
I'd like to do this as I'm designing a game, and in the game objects can implement various interfaces which allow them to be in various lists which are looped through in a prioritized manner. A single object might be in a draw loop, a loop which steps it through the frames of its animation, a high priority logic loop, and a low priority logic loop all at the same time. I would like to implement a removeFrom|TypeOfLoop| method in each appropriate interface so that if an object decides that it no longer needs to be in a loop it can directly remove itself. This keeps the objects that do the actual looping pleasantly simple.
Alternatively, If there is no way to do this, I'm thinking of implementing a flagging system where the list checks to see if each item wants to be removed based on a variable within the item. However, I dislike the idea of doing this enough to possibly just make my own LinkedList that is capable of removing by reference.
I did this recently. I was looking for an O(1) add O(1) remove lock-free Collection. Eventually I wrote my own Ring because I wanted a fixed-size container but you may find the technique I used for my first attempt of value.
I don't have the code in front of me but if memory serves:
Take a copy of Doug Lea's excellent Concurrent Doubly LinkedList and:
Expose the Node class. I used an interface but that is up to you.
Change the add, offer ... methods to return a Node instead of boolean. It is now no longer a java Collection, but see my comment later.
Expose the delete method of the Node class or add a remove method that takes a Node.
You can now remove elements from the list in O(1) time, and it is Lock Free.
Added
Here's an implementation of the remove(Node) method taken from his Iterator implementation. Note that you have to keep trying until you succeed.
public void remove(Node<E> n) {
while (!n.delete() && !n.isDeleted())
;
}
I think your alternative is much better than letting the item remove itself from the loop. It reduces the responsibilities of the objects in the list, and avoids circular references.
Moreover, You could use Guava's Iterables.filter() method and iterate over a filtered list, rather than checking explicitely if the object should be rendered or not at each iteration.
Even if what you want to do was possible, you would get a ConcurrentModificationException when removing an object from the list while iterating on it. The only way to do that is to remove the current object from the iterator.
If you're using LinkedList, there's no more efficient way to remove an item than to iterate over it and do iterator.remove() when you find your element.
If you're using google collections or guava, you can do it in a oneliner:
Iterables.removeIf(list.iterator(), Predicates.equalTo(this));
The easiest way would be changing your algorithm to use Iterator to iterate over List objects and use Iterator.remove() method to remove current element.

Non runtime allocation solution - ArrayList

I'm making a game in Java. I need some solution for my current runtime allocation, caused by my ArrayList. Every single minute or 30 seconds the garbage collector starts to runs because of I am calling for draw and updates-method through this collection.
How should I be able to do a non runtime allocation solution?
Thanks in advance and if needed, my code is posted below from my Manager class which contains the ArrayList of objects.:
Some code:
#Override
public void draw(GL10 gl) {
final int size = objects.size();
for(int x = 0; x < size; x++) {
Object object = objects.get(x);
object.draw(gl);
}
}
public void add(Object parent) {
objects.add(parent);
}
//Get collection, and later we call the draw function from these objects
public ArrayList<Object> getObjects() {
return objects;
}
public int getNumberOfObjects() {
return objects.size();
}
More explanation: The reason I mix with this is because (1) I see that the ArrayList implementation is slow and causing lags and (2) that I want to merge the objects/components together. When firing an update call from my Thread-class, it goes through my collection, send things down the tree/graph using the Manager's update function.
When looking at an Open Source project, Replica Island, I found that he used an alternative class FixedSizeArray that he wrotes on his own. Since I'm not that good at Java, I wanted to make things easier and now I'm looking for another solution. And at last, he explained WHY he made the special class:
FixedSizeArray is an alternative to a standard Java collection like ArrayList. It is designed to provide a contiguous array of fixed length which can be accessed, sorted, and searched without requiring any runtime allocation. This implementation makes a distinction between the "capacity" of an array (the maximum number of objects it can contain) and the "count" of an array (the current number of objects inserted into the array). Operations such as set() and remove() can only operate on objects that have been explicitly add()-ed to the array; that is, indexes larger than getCount() but smaller than getCapacity() can't be used on their own.
I see that the ArrayList implementation is slow and causing lags ...
If you see that, you are misinterpreting the evidence and jumping to unjustifiable conclusions. ArrayList is NOT slow, and it does NOT cause lags ... unless you use the class in a particularly suboptimal way.
The only times that an array list allocates memory are when you create the list, add more elements, copy the list, or call iterator().
When you create the array list, 2 java objects are created; one for the ArrayList and one for its backing array. If you use the initialCapacity argument and give an appropriate value, you can arrange that subsequent updates will not allocate memory.
When you add or insert an element, the array list may allocate one new object. But this only happens when the backing array is too small to hold all of the elements, and when it does happen the new backing array is typically twice the size of the old one. So inserting N elements will result in at most log2(N) allocations. Besides, if you create the array list with an appropriate initialCapacity, you can guarantee that there are zero allocations on add or insert.
When you copy a list to another list or array (using toArray or a copy constructor) you will get 1 or 2 allocations.
The iterator() method creates a new object each time you call it. But you can avoid this by iterating using an explicit index variable, List.size() and List.get(int). (Be aware that for (E e : someList) { ... } implicitly calls List.iterator().)
(External operations like Collections.sort do entail extra allocations, but that is not the fault of the array list. It will happen with any list type.)
In short, the only way you can get lots of allocations using an array list is if you create lots of array lists, or use them unintelligently.
The FixedSizedArray class you have found sounds like a waste of time. It sounds like it is equivalent to creating an ArrayList with an initial capacity ... with the restriction that it will break if you get the initial capacity wrong. Whoever wrote it probably doesn't understand Java collections very well.
It's not quite clear what you are asking, but:
If you know at compile time what objects should be in the collection, make it an array not an ArrayList and set the contents in an initialisation block.
Object[] objects = new Object[]{obj1,obj2,obj3};
What makes you think you know what the GC is reclaiming? Have you profiled your application?
What do you mean by "non-runtime allocation"? I'm really not even sure what you mean by "allocation" in this context... allocation of memory? That's done at runtime, obviously. You clearly aren't referring to any kind of fixed pool of objects that are known at compile time either, since your code allows adding objects to your list several different ways (not that you'd be able to allocate anything for them at compile time even if you were).
Beyond that, nothing in the code you've posted is going to cause garbage collection by itself. Objects can only be garbage collected when nothing in the program has a strong reference to them, and your posted code only allows adding objects to the ArrayList (though they can be removed by calling getObjects() and removing from that, of course). As long as you aren't removing objects from the objects list, you aren't reassigning objects to point to a different list, and the object containing it isn't itself becoming eligible for garbage collection, none of the objects it contains will ever be available for garbage collection either.
So basically, there isn't any specific problem with the code you've posted and your question doesn't make sense as asked. Perhaps there are more details you can provide or there's a better explanation of what exactly your issue is and what you want. If so, please try to add that to your question.
Edit:
From the description of FixedSizeArray and the code I looked at in it, it seems largely equivalent to an ArrayList that is initialized with a specific array capacity (using the constructor that takes an int initialCapcacity) except that it will fail at runtime if something tries to add to it when its array is full, where ArrayList will expand itself to hold more and continue working just fine. To be honest, it seems like a pointless class, possibly written because the author didn't actually understand ArrayList.
Note also that its statement about "not requiring any runtime allocation" is a bit misleading... it does of course have to allocate an array when it is created, but it just refuses to allocate a new array if its initial array fills up. You can achieve the same thing using ArrayList by simply giving it an initialCapacity that is at least large enough to hold the maximum number of objects you will ever add to it. If you do so, and you do in fact ensure you never add more than that number of objects to it, it will never allocate a new array after it is created.
However, none of this relates in any way to your stated issue about garbage collection, and your code still doesn't show anything that would cause huge numbers of objects to be garbage collected. If there is any issue at all, it may relate to the code that is actually calling the add and getObjects methods and what it's doing.

remove repeated vaules _stack&array

I want to write a program to implement an array-based stack, which accept integer numbers entered by the user.the program will then identify any occurrences of a given value from user and remove the repeated values from the stack,(using Java programming language).
I just need your help of writing (removing values method)
e.g.
input:6 2 3 4 3 8
output:6 2 4 8
Consider Collection.contains (possibly in conjunction with Arrays.asList, if you are so unfortunate), HashMap, or Set.
It really depends on what you have, where you are really going, and what silly restrictions the homework/teacher mandates. Since you say "implement an array-based stack" I am assuming there are some silly mandates in which case I would consider writing a custom arrayContains helper* method and/or using a secondary data-structure (Hash/Set) to keep track of 'seen'.
If you do the check upon insertion it's just (meta code, it's your home work :-):
function addItem (i) begin
if not contains(stack, i) then
push(stack, i)
end if
end
*You could use the above asList/contains if you don't mind being "not very efficient", but Java comes with very little nice support for Arrays and thus the recommendation for the helper which is in turn just a loop over the array returning true if the value was found, false otherwise. (Or, perhaps return the index found or -1... your code :-)
Assuming that the "no-duplicates" logic is a part of the stack itself, I would do the following:
1) Implement a helper method:
private boolean remove(int item)
This method should scan the array, and if it finds the item it should shrink the array by moving all subsequent items one position backwards. The returned value indicates whether a removal took place.
2) Now it is easy to implement the push method:
public void push(int item) {
if (!remove(item)) {
arr[topPos++] = item;
}
}
Note that my solution assumes there is always enough space in the array. A proper implementation should take care of resizing the array when necessary.
The question is an interesting (or troubling) one in that it breaks the spirit of the stack to enforce such a constraint. A pure stack can only be queried about its top element.
As a result, doing this operation necessarily requires treating the stack not as a stack but as some other data structure, or at least transferring all of the data in the stack to a different, intermediate data structure.
If you want to accomplish this from within the stack class itself, others' replies will prove useful.
If you want to accomplish this from outside of the stack, using only the traditional methods of a stack interface (push() and pop()), your algorithm might look something like this:
Create a Set of Integers to keep track of values encountered so far.
Create a second stack to hold the values temporarily.
While the stack isn't empty,
Pop off the top element.
If the set doesn't contain that element yet, add it to the set and push it onto the second stack.
If the set does contain the element, that means you've already encountered it and this is a duplicate. So ignore it.
While the second stack isn't empty,
Pop off the top element
Push the element back onto the original stack.
There are various other ways to do this, but I believe all would require some auxiliary data structure that is not a stack.
override the push method and have it run through the stack to determine whether the value already exists. if so, return false otherwise true (if you want to use a boolean return value).
basically, this is in spirit of the answer posted by Mr. Schneider, but why shrink the array or modify the stack at all if you can just determine whether a new item is a duplicate or not? if it's a duplicate, don't add it and the array does not need to be modified. am i missing something?

Categories

Resources