Java endless list - java

I think it is a standard problem. I need a list that I can iterate for and backward. If iterating forward and the iterator riches e.g. 80% of length of the list, new element must be added to the end of list and the same number of elements must be deleted from the beginning of list. This should happen during iteration without influencing the iterator. The current iterator should be still valid. The same procedures should work, if the iterator goes backward.
Is there any kind of list, queue or stack in any collection that fulfills these requirements? Anybody know?
Thx

this can be very easily implemented using array.
Set initial size of the array.
Create Array of that size and you desired type
Create index (int for example) which is incremented/decreased when iterating the array.
Add logic to track the index (e.g. if index>0.8*size -> add more elements to the array)
I would use the java ArrayList object for this job.

What you are talking about is not an endless list, but a circular list (endless list would not delete from the beginning).
What you want is a function with a normal list inside, that takes an iterator as parameter and just rolls over when it reaches the end. So element 101 of 100 element list, is element 1 being overwritten.

Related

Why use ArrayList if requirement is not clear?

I have found following question on www.javatpoint.com
If you were to use a List implementation,but not sure which one to, because the requirement is not yet clear. In this case which List implementation will you use ?
options:
1. ArrayList
2. LinkedList
Correct answer for this is ArrayList
But there is no explanation why, Please help me to uderstand
Simple Term
ArrayList : Iterating Over An ArrayList is faster than Linked List, Because All Elements Stored in Contiguous Memory Location. But Performing Operation Like Delete Will Reduce Performance Because Again Entire List Order Changes (Like if you delete element at position 3rd then all next elements location are currentLocation - 1).
LinkedList : Slower When Iteration Performed(As Compare To ArrayList). But Delete and Update Operation Becomes Faster Because If you delete any element at any position only previous and after element locations are changed(Not Entire List).
So When You Don't Have Clear Requirements Just Iteration Is Basic Need (And Array List Gives Best Performance).
One possible reason might be that elements in ArrayList consume less memory space than in LinkedList, because each element in LinkedList contains a value plus a pointer to the next element, while an element in ArrayList has only value
ArrayList stores elements in array in insert order. You can get value by its index in array.
LinkedList stores your elements in Node objects that references each other. Each Node references previous and next Node. You can get elements sequentially starting from both sides. You can also get elements by index but it's not as fast as in ArrayList. Use LinkedList when you need sequential access, like queue or stack data structure
From what I've read in the past: An ArrayList essentially acts as a better array, allowing for dynamic resizing. A LinkedList is a double linked list which causes it to have better performance on adding and removing items from the list, but getting and setting at arbitrary positions is slower than an ArrayList. So, the question is most likely assuming that, generally, a program will be getting and setting values more than it is adding and removing values, which is a fairly reasonable assumption, but the question in question is incorrect.

Why is accessing an item by index slower in a linked list than an array?

I think I am missing a very obvious point but could not find it in my Java textbook.
I understand that node storage does not necessarily have to be contiguous in memory for linked list. Does this also mean that a linked list is not indexable? If so, then the only way to find an item in a linked list is to traverse the list, right, whereas you can get from an array by index?
Why is accessing an item by index slower in a linked list than an array?
A linked list has a chain of entries. If you want to get (say) the element at position 42, the code has to:
get the entry for the first element (position 0)
follow the next link to the entry for position 1
follow the next link to the entry for position 2
and so on .... 42 times in total.
There is no short cut.
I am still not understanding why a linked list is not indexable ....
Now a LinkedList is indexable in the sense that there is a get(int) operation that works. It is just that indexing a LinkedList is inefficient. In general, it takes O(N) steps to perform a get(i) in a linked list of length N. By contrast with an array, or an ArrayList, you can retrieve any element of the data structure in one step. We say that the complexity is O(1).
Contrast this with Set objects in general, and HashSet in particular. The HashSet class is NOT indexable because there is no get(int) method to retrieve the set element at position i. Indeed, even the notion of "position i" in a set is meaningless. The ordering of the elements in a Set is unspecified and (for some Set implementations, like HashSet) it may be effectively indeterminate.
Some Linked list implementations provide a way to access to it's elements using index, but the fact is that if you want to get 10th element in linked list your compiler still has to go through all the sequence from 0 to 9 because the elements may be spread over the memory. On the other hand when you ask for 10th element in an array using index, compiler computes the exact position of 10th element and jumps directly to that element. Array and list have different purposes; if your algorithm requires go back and forward over your data structure, then it is much efficient to use array. If you need mostly add/remove operations, then it is efficient to use list
With a linked list you can add and remove elements at any time so index it has no sense. Imagine that you create an index that points at the third element of the list. After that, you insert a new element at the beginning of the list. What value should return the index?
However it could be possible for example create an index at the middle of the list and use it only if you add o remove elements in the last half of the list.
#paxdiablo explains it very well here Is there a known implementation of an indexed linked list?

Removing elements from the beginning vs the end

In the Collection framework tutorials for the List interface, there is an interesting quote regarding performance of removal of elements from a List implementation:
For many common List implementations, such as ArrayList, the performance of removing elements from the end of the list is substantially better than that of removing elements from the beginning.
The tutorials do not go further into explaining this and I am trying to understand exactly why it might be so.
Considering an ArrayList<Integer> list as below:
In the first scenario, if we remove the last 4 elements from the end of the list, then the values of these are set to null (or equivalent). My theory is that, when a copy operation is necessary, only the elements that are not null will be copied.
In the second scenario, if we remove the first 4 elements, they would be set to null again and again only non-null elements would be copied.
So from this point of view, the performances appear to be around the same. Is there another reason why the operation is faster if performed from the end?
On the other hand, for LinkedList, the inverse appears to be true; removal from the beginning is faster, whereas removal from the end requires an almost full traversal unless a tail-pointer
is kept.
As per my understanding,
ArrayList is an array implementation of a list. So if you remove elements from the beginning of an array you need to move all the remaining elements to fill up the elements that you removed. So this is going to essentially be a O(n-1) operation.However this is not the case when you remove elements from end of the list. This will be O(1).
There is more to removing elements from the beginning of the list than just setting the elements to null. You also need to move the remaining elements to fill in the vacated locations.
It's possible to use a variable to keep track of the "beginning" of the list without moving elements, but then you will sacrifice memory efficiency because of the unused elements in the array.
In ArrayList<> removing from start is slow because entire array will have to be shifted since the add function add the elements at and if we left the start empty then we will be wasting the memory.
If we take into account big(O) notation removing from start is essentially linear time O(n) while deleting from end is constant time O(1).
While Code-Apprentice's answer is correct, I'd like to elaborate on how you can verify the behavior that every entry is moved to the left by making an index-based lookup, i.e., calling list.get(index).
add two entries
remove the first element
check the value of the first element: is it now null or the previously second element?
The code to verify:
List<String> list = new ArrayList<>();
list.add("0");
list.add("1");
list.remove(0);
String entry0 = list.get(0);
System.out.println(entry0);
You suspected that null would be printed, but "1" is printed.
This confirms that all the elements are shifted to the left.
NB. I used Strings to avoid the confusion caused by remove(int index) and remove(Object o).

ArrayList - LinkedList Clarification

Can any one tell me clearly why ?
Reading is simple in ArrayList,( we can access through its array index ), why not in linkedList
Inserting element in arrayList is tough i heard why ? easy in linkedList why ?
Deleting element in arraylist is tough why ? easy in linkedList why ?
I know some thing about arrays, but what going in linkedXXX
Thank you.
In an ArrayList, you keep an array of references in memory, that is to say, you have a memory position. When you ask for the first element of an ArrayList, you just access the memory position. When you access the 10th element, you access the memory position + 10 times the size of a reference.
In an LinkedList, you have one element, which has a reference to the next. The next one references the next, and so on. As you can see, there is no direct way of accessing the 10th element in a LinkedList without going one by one getting the next element.
So, your questions:
Inserting element in arrayList is touch i heard why ? easy in linkedList why ?
There are two problems with inserting an element into an ArrayList:
When you put an element in position 3, you need to first move every element starting at position 3 and shift them right once (3 becomes 4, 4 becomes 5, etc...) so that 3 becomes empty and you can put in your new element
If the array that backs your ArrayList is already full, you need to create a new one! This is very costly, since you need to allocate the memory again, and then copy all elements to the new array, and destroy the old one.
In a Linkedlist, on the other hand, you go to element 1, which points to 2, and then go to 2. In 2, there's a reference to the old element 3, which you temporarily store elsewhere. You replace it with a reference to your new element, and in your new element, you make next point to the old 3. This is therefore way less costly.
Deleting element in arraylist is touch why ? easy in linkedList why ?
Similar reasons as inserting. In an ArrayList, you have to shift all the elements down again, in the LinkedList, once you are at element 2, you make its next point to 4, and voila, 3 is erased.
And for completeness
ArrayLists are great if you are going to access elements in a random order, but have the problems of adding and substracting. LinkedLists are great to add and remove, but getting an element that's not the first or last takes extra cost. So there's always a trade-off!
An ArrayList is backed by an array, which can't grow or shrink, nor can elements be inserted or removed. So insertion and removal are expensive operations, since a new array has to be created and the existing values copied from one array to the other. But an array can be accessed by index, so Random Access is much faster here.
A LinkedList consists of Node Objects that have pointers (yes, I know) to each other in one direction or both. It is very cheap to remove one of these nodes or insert a new one, but to get node nr. 12345, you have to start at the beginning and walk over 12344 nodes, which means random access is very expensive here. Note: A Java LinkedList is not only a List, btw, it also implements the Queue and Deque interfaces.
I think both are equally well suited for simple iteration, but the underlying mechanism is completely different.

What is the best way to remove the first element from an array?

I have string array (String[]) and I need to remove the first item. How can I do that efficiently?
The size of arrays in Java cannot be changed. So, technically you cannot remove any elements from the array.
One way to simulate removing an element from the array is to create a new, smaller array, and then copy all of the elements from the original array into the new, smaller array.
String[] yourArray = Arrays.copyOfRange(oldArr, 1, oldArr.length);
However, I would not suggest the above method. You should really be using a List<String>. Lists allow you to add and remove items from any index. That would look similar to the following:
List<String> list = new ArrayList<String>(); // or LinkedList<String>();
list.add("Stuff");
// add lots of stuff
list.remove(0); // removes the first item
Simplest way is probably as follows - you basically need to construct a new array that is one element smaller, then copy the elements you want to keep to the right positions.
int n=oldArray.length-1;
String[] newArray=new String[n];
System.arraycopy(oldArray,1,newArray,0,n);
Note that if you find yourself doing this kind of operation frequently, it could be a sign that you should actually be using a different kind of data structure, e.g. a linked list. Constructing a new array every time is an O(n) operation, which could get expensive if your array is large. A linked list would give you O(1) removal of the first element.
An alternative idea is not to remove the first item at all, but just increment an integer that points to the first index that is in use. Users of the array will need to take this offset into account, but this can be an efficient approach. The Java String class actually uses this method internally when creating substrings.
You can't do it at all, let alone quickly. Arrays in Java are fixed size. Two things you could do are:
Shift every element up one, then set the last element to null.
Create a new array, then copy it.
You can use System.arraycopy for either of these. Both of these are O(n), since they copy all but 1 element.
If you will be removing the first element often, consider using LinkedList instead. You can use LinkedList.remove, which is from the Queue interface, for convenience. With LinkedList, removing the first element is O(1). In fact, removing any element is O(1) once you have a ListIterator to that position. However, accessing an arbitrary element by index is O(n).
Keep an index of the first "live" element of the array. Removing (pretending to remove) the first element then becomes an O(1) time complexity operation.
To sum up, the quick linkedlist method:
List<String> llist = new LinkedList<String>(Arrays.asList(oldArray));
llist.remove(0);
An alternative ugly method:
String[] a ={"BLAH00001","DIK-11","DIK-2","MAN5"};
String[] k=Arrays.toString(a).split(", ",2)[1].split("]")[0].split(", ");

Categories