可以将文章内容翻译成中文,广告屏蔽插件可能会导致该功能失效(如失效,请关闭广告屏蔽插件后再试):
问题:
I need to add elements to an ArrayList
queue whatever, but when I call the function to add an element, I want it to add the element at the beginning of the array (so it has the lowest index) and if the array has 10 elements adding a new results in deleting the oldest element (the one with the highest index).
Does anyone have any suggestions?
回答1:
List
has the method add(int, E)
, so you can use:
list.add(0, yourObject);
Afterwards you can delete the last element with:
if(list.size() > 10)
list.remove(list.size() - 1);
However, you might want to rethink your requirements or use a different data structure, like a Queue
EDIT
Maybe have a look at Apache's CircularFifoQueue
:
CircularFifoQueue
is a first-in first-out queue with a fixed size that replaces its oldest element if full.
Just initialize it with you maximum size:
CircularFifoQueue queue = new CircularFifoQueue(10);
回答2:
Using Specific Datastructures
There are various data structures which are optimized for adding elements at the first index. Mind though, that if you convert your collection to one of these, the conversation will probably need a time and space complexity of O(n)
Deque
The JDK includes the Deque
structure which offers methods like addFirst(e)
and offerFirst(e)
Deque<String> deque = new LinkedList<>();
deque.add("two");
deque.add("one");
deque.addFirst("three");
//prints "three", "two", "one"
Analysis
Space and time complexity of insertion is with LinkedList
constant (O(1)
). See the Big-O cheatsheet.
Reversing the List
A very easy but inefficient method is to use reverse:
Collections.reverse(list);
list.add(elementForTop);
Collections.reverse(list);
If you use Java 8 streams, this answer might interest you.
Analysis
- Time Complexity:
O(n)
- Space Complexity:
O(1)
Looking at the JDK implementation this has a O(n)
time complexity so only suitable for very small lists.
回答3:
You can take a look at the add(int index, E element):
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).
Once you add you can then check the size of the ArrayList and remove the ones at the end.
回答4:
You may want to look at Deque. it gives you direct access to both the first and last items in the list.
回答5:
What you are describing, is an appropriate situation to use Queue
.
Since you want to add
new element, and remove
the old one. You can add at the end, and remove from the beginning. That will not make much of a difference.
Queue has methods add(e)
and remove()
which adds at the end the new element, and removes from the beginning the old element, respectively.
Queue<Integer> queue = new LinkedList<Integer>();
queue.add(5);
queue.add(6);
queue.remove(); // Remove 5
So, every time you add an element to the queue
you can back it up with a remove
method call.
UPDATE: -
And if you want to fix the size of the Queue
, then you can take a look at: - ApacheCommons#CircularFifoBuffer
From the documentation
: -
CircularFifoBuffer is a first in first out buffer with a fixed size
that replaces its oldest element if full.
Buffer queue = new CircularFifoBuffer(2); // Max size
queue.add(5);
queue.add(6);
queue.add(7); // Automatically removes the first element `5`
As you can see, when the maximum size is reached, then adding new element automatically removes the first element inserted.
回答6:
I think the implement should be easy, but considering about the efficiency, you should use LinkedList but not ArrayList as the container. You can refer to the following code:
import java.util.LinkedList;
import java.util.List;
public class DataContainer {
private List<Integer> list;
int length = 10;
public void addDataToArrayList(int data){
list.add(0, data);
if(list.size()>10){
list.remove(length);
}
}
public static void main(String[] args) {
DataContainer comp = new DataContainer();
comp.list = new LinkedList<Integer>();
int cycleCount = 100000000;
for(int i = 0; i < cycleCount; i ++){
comp.addDataToArrayList(i);
}
}
}
回答7:
Java LinkedList provides both the addFirst(E e) and the push(E e) method that add an element to the front of the list.
https://docs.oracle.com/javase/7/docs/api/java/util/LinkedList.html#addFirst(E)
回答8:
you can use this code
private List myList = new ArrayList();
private void addItemToList(Object obj){
if(myList.size()<10){
myList.add(0,obj);
}else{
myList.add(0,obj);
myList.remove(10);
}
}
回答9:
You can use
public List<E> addToListStart(List<E> list, E obj){
list.add(0,obj);
return (List<E>)list;
}
Change E with your datatype
If deleting the oldest element is necessary then you can add:
list.remove(list.size()-1);
before return statement. Otherwise list will add your object at beginning and also retain oldest element.
This will delete last element in list.
回答10:
You can use list methods, remove and add
list.add(lowestIndex, element);
list.remove(highestIndex, element);
回答11:
I had a similar problem, trying to add an element at the beginning of an existing array, shift the existing elements to the right and discard the oldest one (array[length-1]).
My solution might not be very performant but it works for my purposes.
Method:
updateArray (Element to insert)
- for all the elements of the Array
- start from the end and replace with the one on the left;
- Array [0] <- Element
Good luck
回答12:
import java.util.*:
public class Logic {
List<String> list = new ArrayList<String>();
public static void main(String...args) {
Scanner input = new Scanner(System.in);
Logic obj = new Logic();
for (int i=0;i<=20;i++) {
String string = input.nextLine();
obj.myLogic(string);
obj.printList();
}
}
public void myLogic(String strObj) {
if (this.list.size()>=10) {
this.list.remove(this.list.size()-1);
} else {
list.add(strObj);
}
}
public void printList() {
System.out.print(this.list);
}
}