I am a new programmer writing a sudoku program. I have guess values stored into a linked list structure. I have a method which determines where the best guess location is and then guesses all possible values for that entry.
My specific question is that when I loop thru to enter multiple guesses, the subsequent guesses overwrite the earlier guesses so I end up with guessQueue holding multiple copies of the same guess. How should I call the loading into the linked list to avoid this problem? I created a short sample method which illustrates the point here (and hopefully is SCCE):
public void TestLinkedList(){
LinkedList testQueue = new LinkedList();
int[][] testGrid = new int[9][9];
for (int k=0;k<10;k++){
for (int j=0;j<9;j++){
for (int jj=0;jj<9;jj++){
testGrid[j][jj]=k;
}
}
testQueue.addLast(testGrid);
}
}
I expect each entry in the linked list to contain an array with each value in the array 1 higher than the previous entry into the linked list, but all the values in the arrays in the linked list are the same
The Arrays class and the Collections framework can help you out:
Java Code:
T[] array= new T[ ... ];
List list= new LinkedList(Arrays.asList(array));
Related
I am trying to update the order of my doubly linked list based on an array with the same elements in the updated order.
For example if I have:
cat->dog->rabbit->panda
And I want to reorder to have the order of the array:
String[] pets = {"dog", "rabbit", "panda", "cat"};
For context: I am new to Java and programming in general so not sure how to do so. Essentially, what I am doing is that I shuffled the elements of a seating arrangement and the doubly linked list is a non-shuffled version of those students. I just want to update the doubly linked list to match the order of the new shuffled version. I want a function that can do so.
I have methods to access the last and first elements of the doubly linked list and the ability to go left or right from one element. I want to do this with elementary knowledge, without using maps and stuff. Sorry if it sounds like a hassle, I just want to understand what's happening!
If your linked list class has the same operations as a standard LinkedList, you can create a map of pets to their indices in the array:
Map<String, Integer> arrayIndices =
IntStream.range(0, pets.length)
.boxed()
.collect(Collectors.toMap(i -> pets[i], i -> i));
Then sort the list with a custom comparator that sorts by array index:
linkedList.sort(Comparator.comparing(arrayIndices::get));
Instead of creating a mam and then comparing, I would declare an array with the order expected:
String[] order = {"cat","dog","rabbit","panda"};
Then I would trace a sorting algorithm, here is an example (very simple one):
for (int i=0; i < pets.length(); i++){
for (int k=0, k < order.length(); k++){
if (pets[i] == order[k]){
if (i != k){
String store = pets[k];
pets[k] = pets[i];
pets[i] = store;
}else{
// Proper position
}
}
}
}
This takes longer to code than what markovv answered; however, you don't dive have to dive into Maps.
I'm running the following code, but getting error The method trimToSize() is undefined for the type List<Integer>
public class ListPerformance {
public static void main(String args[]) {
List<Integer> array = new ArrayList<Integer>();
List<Integer> linked = new LinkedList<Integer>();
//Initialize array with random elements in the first 50 positions, do other operations
addElement(array,"beginning");
//Resize to 100
for(int a=100;a<array.size();a++) {
array.remove(a);
}
linked.trimToSize();
}
...
I thought I did everything correctly as shown at this tutorial on ArrayList.trimToSize(). Why can't I use .trimToSize() here?
EDIT2: So thanks to the posters/commenters, I now know that my mistake was creating with element of List instead of ArrayList. But what about custom methods? Should I take those as arraylist/linked list or regular ol' List? What is considered "good-practice"? Or does that also depend on whether or not I need to use ArrayList-specific methods?
Thanks again!
trimToSize() is a method of the ArrayList class, not the List interface. Since you're storing your variables as List<Integer>, you can only use methods that are part of the List interface.
Change your variable declarations to:
ArrayList<Integer> array = new ArrayList<Integer>();
LinkedList<Integer> linked = new LinkedList<Integer>();
And you should be fine in your main, so long as you only try and trim array. You can't trim linked at all, because it's nonsensical to trim a LinkedList; they do not allocate additional buffer space past their capacity as appending to a LinkedList is always O(1), where as appending to a full ArrayList is O(n).
trimToSize() is a method of ArrayList but not of List. Not all Lists can be trimmed (e.g.: LinkedList)
List<Integer> linked = new LinkedList<Integer>();
linked.trimToSize();
You're calling it on the LinkedList. If you want to call it on the ArrayList use
ArrayList<Integer> array = new ArrayList<Integer>();
instead of the first line. (tell your compiler it's not any List, but an ArrayList)
This question already has answers here:
Removing an element from an Array (Java) [duplicate]
(15 answers)
Closed 9 years ago.
I have an array of Contact objects that has a MAX of 50 Contacts, but will have much less, so the array is initialized with a size of 50. But I need my method to remove the Contact and shift everything after it up. What I have seems to work at times, but not every time.
public Contact remove(String lstnm)
{
int contactIndex = findContactIndex(lstnm); // Gets the index of the Contact that needs to be removed
Contact contactToBeRemoved;
if(contactIndex == -1) // If the Contact is not in the Array
{
contactToBeRemoved = null;
}
else
{
contactToBeRemoved = Contact_List[contactIndex]; // Assigns the Contact that is going to be removed
for(int i = contactIndex; i < numContacts; i++) // From where the Contact was removed to the last Contact in the list
{
Contact_List[i] = Contact_List[i + 1]; // Shift all of the Contacts after the one removed down
}
numContacts -= 1; // One Contact is removed from the total number of Contacts
}
return contactToBeRemoved;
}
Arrays a fixed size you cannot resize them. ArrayList on the other hand auto resize each time you add a element.
So if I have a Array of 5 I can put 5 items in it, no more no less. One thing you can do is set objects in the Array to be null or 0.
Edit: With regards to your comment, just sort the Array. Look up a easy bubble sort algorithm in Java.
try
System.arraycopy(contactList, contactIndex + 1, contactList, contactIndex, contactList.length - contactIndex - 1);
Note that System.arraycopy is the most efficient way to copy / move array elements
your code would give exception at numContacts'th iteration since i+1 will go beyond size of array.
for(int i = contactIndex; i < numContacts-1; i++)
{
Contact_List[i] = Contact_List[i + 1];
}
Contact_List[Contact_List.length-1] = null;
Ps: its a very bad practice to use Array in such scenario, consider using ArrayList instead.
Why don't you convert your array into a List and use the remove(Object o) method that does exactly what you describe?
It would save you some time and some testing.
for such purpose use ArrayList
ArrayList<Contact> array = new ArrayList<Contact>(50);
creates a dynamic array with initial capacity of 50 (this can increase as more elements gets added to the ArrayList)
array.add(new Contact());
array.remove(contact); //assuming Contact class overrides equals()
ArrayList internally maintains an array and does re-sizing, restructuring as the elements are added or removed from it.
You can also use Vector<Contact> which is similar data-structure, but thread safe.
Array's become pretty useless when you know how to use arrayList, in my opinion. I suggest using arrayLists.
ArrayList tutorial
do like this when creating ht econtact arrayList:
import java.util.ArrayList;
public static void main(String args[]){
ArrayList<Contact> contacts = new ArrayList();
contacts.add(new Contact());
}
Use arrayLists, its the best way. Read tutorials, the are plenty of them.
I suggest it cause arralist are dynamic, that means you can add and remove items and it resized itself for you.
Hope I could help even if my answers isnt very complete
use collection rather than array so that you dont have to do all the shifting processes!
collection automatically shifts the elements and you dont have to worry about it!
you may do as follow,
ArrayList<Contact> list=new ArrayList<Contact>();
Contact c=new Contact();
Contact.Add(Contact);
Contact.remove(Contact);
and any more behaviours are available in ArrayList!
you may write you remove method as follows
public Contact remove(String lstnm)
{
Contact c=new Contact(1stnm);
Contact contactToBeRemoved=list.get(1);
List.remove(c);
return contactToBeRemoved;
}
but you have to override the equal() and compareTo() method of the object class in the Contact class!
otherwise nothing will work properly!
I'm attempting a radix sort but I'm having trouble addressing arraylists of arraylists. The list has 10 spaces, each with a bucket of size n.
ArrayList<ArrayList<Integer>> list = new ArrayList<ArrayList<Integer>>(10);
ArrayList<Integer> bucket = new ArrayList<>();
bucket.add(99);
list.add(bucket);
list.add(bucket);
list.get(0).add(12); (6)
When I attempt to add in a value using (6) it adds 12 for each arraylist within list (presumably because they are both buckets). How can I initialize the arraylist properly such that I treat each arraylist in list independently? And would I access the elements of each arraylist in list in a similar fashion?
I think what you're looking for is
for (int i = 0; i < 10; i++) {
list.add(new ArrayList<>());
}
You can set a size for each bucket if you want also - I think by passing the desired size to the ArrayList constructor
When you add 12 to the ArrayList in list, you are adding to a referenced ArrayList, which in this case is bucket. list.get(0) and list.get(1) will both return a reference to the same ArrayList, bucket.
What is the best way to do a resizable array in Java? I tried using Vector, but that shifts all elements over by when when you do an insert, and I need an array that can grow but the elements stay in place. I'm sure there's a simple answer for this, but I still not quite sure.
As an alternative, you could use an ArrayList. It is a resizable-array implementation of the List interface.
Usage (using String):
List<String> myList = new ArrayList<String>();
myList.add("a");
myList.add("c");
myList.add("b");
The order will be just like you put them in: a, c, b.
You can also get an individual item like this:
String myString = myList.get(0);
Which will give you the 0th element: "a".
Like Sanjo pointed out: "An array is a static datastructure, so they can't grow". The list interface can by backed by an array(for example ArrayList like Kevin pointed out in his post). When the list structure is full and a new item has to be added to the list. Then the structure first creates a new array which can contain the old elements plus the new element which has to be added to the list.
The list interface has a different implementations which all have there pros/cons and you should pick the one best solving your problem-set. Below I will try to give a short summary when to use which implementation:
Not thread-safe implementations:
ArrayList: Resizable-array implementation of the List interface. You should use this implementation when you are doing a lot of size, isEmpty, get, set, iterator, and listIterator operations run in constant time. The add operation runs in amortized constant time, that is, adding n elements requires O(n) time. I think you should use this implementation when doing more lookups(get()) then adding items to list(add()).
LinkedList: This implementation is not backup by an array but "links" the nodes together. In my opinion you should use this implementation when you are doing more add() then get().
Thread-safe implementations:
Be aware that these list implementations aren't thread-safe which means it is possible to get race conditions when accesing them from multiple threads. If you want to use List implementations from multiple threads I would advise you to study the java.util.concurrent package and use implementation from that class.
You probably should use ArrayList instead of Vector for reasons explained in other answers.
However ...
I tried using Vector, but that shifts all elements over by when when you do an insert, and I need an array that can grow but the elements stay in place.
When you do an insertElementAt(pos, elem), you have specifically asked for the element shifting. If you don't want the elements to be shifted, you should use set(pos, elem) instead. Or if you want to add the element at the end of the vector, you can also use add(elem).
Incidentally, the previous paragraph applies to all implementations of List, not just Vector, though the implementation details and performance vary across the different kinds of List.
I tried using Vector, but that shifts all elements over by when when you do an insert, and I need an array that can grow but the elements stay in place.
You probably want to use ArrayList instead of Vector.
They both provide about the same interface, and you can replace elements with both of them by calling set(idx, element). That does not do any shifting around. It also does not allow you to grow the array, though: You can only insert at already occupied positions (not beyond the current size of the array), to add new elements at the end you have to use add(element).
The difference between ArrayList and Vector is that Vector has synchronization code which you most likely do not need, which makes ArrayList a little faster.
If you want to operate array data after all element had already inserted or deleted, there is a way that try to create a LinkedList or ArrayList, its simply resize, after the data input is finished, you can transfer the ArrayList to an Array, then do all the things you normally to Array.
ArrayList and LinkedList
Space Complexity:
a) ArrayList:
Allocates a chunk of memory when you initialize and doubles everytime it reaches it max size whenever you add an element dynamically.
b) LinkedList:
It allocates memory only everytime you add an item to the list.
Runtime Complexity:
a) ArrayList:
Search is faster, insertion and deletion is slower compared to linked list
b) LinkedList:
Insertion and deletion is faster, search is slower compared to array list
An array cannot be resized dynamically in Java. The solution to this is using ArrayList or creating another temporary array and then assign it.
You can find tutorials about ArrayList, but if you just want custom ResizableArray in Java. Here's it is. But it's NOT recommend to use! It's just a FAKE resizable array and heap memory will be increased when you create too many objects. This is just to show you the idea.
The Interface
public interface Resizable<T> {
void add(T data);
int delete(int index);
int size();
void print();
}
Implementation Class
public class ResizeableImpl<T> implements Resizable<T> {
private Object[] temp = null;
private Object[] originals = new Object[0];
#Override
public void add(T data) {
Object[] temp = new Object[originals.length+1];
for (int i=0; i<originals.length; i++) {
temp[i]=originals[i];
}
temp[originals.length]=data;
originals=temp;
}
#Override
public int delete(int index) {
int success=0;
switch (originals.length) {
case 0: //No Data to delete
success=0;
break;
case 1: //One Data is delete and so no data, too!
originals = new Object[0];
success = 1;
break;
default: //>=2
int count=0;
originals[index]=null;
temp = new Object[originals.length-1];
for (int i=0; i<originals.length; i++) {
if (originals[i]!=null)
temp[count++]=originals[i];
}
originals = temp;
success = 1;
}
return success;
}
#Override
public int size() {
return originals.length;
}
#Override
public void print() {
StringBuilder sb = null;
if (originals.length==0) {
System.out.println("No data available!");
return;
}
for (int i=0; i<originals.length; i++) {
if (sb==null) {
sb = new StringBuilder();
sb.append(originals[i]);
}
else {
sb.append(", "+originals[i]);
}
}
sb.append(".");
System.out.println(sb.toString());
}
}
Main method
public class App {
public static void main(String[] args) {
//Program to interfaces, not implementations
Resizable<Integer> obj = new ResizeableImpl<>();
obj.add(13);
obj.add(20);
obj.add(17);
obj.add(25);
obj.add(100);
obj.add(12);
obj.print();
int result = obj.delete(2); //This will delete 17.
if (result==1) {
System.out.println("Deletion is successful!");
}
obj.print();
obj.delete(3); //This will delete 100.
obj.print();
}
}
Output
13, 20, 17, 25, 100, 12.
Deletion is successful!
13, 20, 25, 100, 12.
13, 20, 25, 12.
Use either ArrayList or LinkedList.
Using wonderful classes in Collections framework is the better than using arrays.
But in case your question is from a "quizzing" perspective, here is what you should do.
Create your own resize method such as:
int[] oldArray = {1,2,3};
int oldSize = java.lang.reflect.Array.getLength(oldArray);
Class elementType = oldArray.getClass().getComponentType();
Object newArray = java.lang.reflect.Array.newInstance(
elementType,newSize);
int preserveLength = Math.min(oldSize,newSize);
if (preserveLength > 0)
System.arraycopy (oldArray,0,newArray,0,preserveLength);
oldArray = newArray;