This programmers stack exchange question enlightened me to the java programming concept container objects are passed in as pointers. Upon learning that, I have an issue with my code because of that concept.
Here is my code:
public double findRollingPivots(ArrayList<Double> listOfCurrentPivots, ArrayDeque<Double> dequeOfAllPivots, double rollingPeriodLength) {
double returnSignal = 0; //this is whatever signal to be returned-- BD BO or profit target
double containerOfPivots = 0; //this holds all of the pivots to be divided in dequeOfCurrentPivots
listOfCurrentPivots.remove(4); /***line4***/
listOfCurrentPivots.add(dequeOfAllPivots.removeLast());
for (int i = 0; i < rollingPeriodLength; i++) { /***line 6***/
containerOfPivots += listOfCurrentPivots.get(i);
}
returnSignal = containerOfPivots / rollingPeriodLength;
return returnSignal;
My issue is that on line 4, I will not always be removing the element at the fourth index. It would be much easier to just call removeLast() on a deque and just push the new element on each time.
But, if I use a deque, then on line 6, I will be losing all of my elements when I add them to the containerOfPivots variable. I tried to get around this by creating a temporary deque to use so I can keep the parameter value, but that doesn't work either. So, is there a way to use a deque and not have to worry about depleting the size of it in a function? Am I overlooking something?
If I understand your question correctly (you'd like to avoid modifying the original list within your function), you can make a copy of the collection with all the same elements.
List<Double> newList = new ArrayList<Double>();
newList.addAll(listOfCurrentPivots);
Any changes made to newList will have no effect on the elements contained in listOfCurrentPivots. This will not duplicate the amount of data we are dealing with either. Each list will reference the same object in memory. Since we are dealing with Doubles they are immutable so we don't have to worry about operations that would modify these objects.
for example: why this statement long[] n= new long[]; is wrong but this statement
long[][] n= new long[1][]; is right? How does the memory know how much memory needs to be assigned to the object in the second statement?
How does the memory know how much memory needs to be assigned to the object in the second statement?
Two things to remember here to figure out what's going on:
2D Java arrays aren't square, they're arrays of arrays.
You specify the size of an array when it's created.
So in this example, you're creating an array of longs (of size 1) to hold another array of longs - but you're not yet creating the second array (so you don't need to specify how large it will be.) In effect, the first array provides an empty "slot" (or slots if the outer array is longer than 1) for the inner array(s) to sit in - but the inner array(s) haven't yet been created, so their size doesn't need to be specified.
It doesn't just create an array of arbitrary length at all, it simply doesn't create any inner arrays.
You can perhaps see this more clearly if you try to access or store a long in the 2D array:
long[][] x = new long[2][];
x[0][0] = 7;
...will produce a NullPointerException (on the second line), because there is no inner array there to access.
In the first example that doesn't compile, you're trying to actually create an array of longs, but not giving it a dimension, hence the error.
when you write this - long[][] n= new long[1][];
you are creating array of arrays of long but you are not actually initializing those arrays right now
So if you do n[0] == null it will return true
that way you are free to initialize new array in any point of time later-
n[0] = new long[10];
So the point is - you need to provide size while initializing your array , that is why long[] n= new long[]; is wrong
Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 9 years ago.
Improve this question
If I have a pointer in C++, let's say int* array;, I allocate memory for the array with
array=new int[10];
Then, I initialize all 10 elements of the array, with 0,1,2,3...
After that, I do array=new int[15];
will the initial first 10 values still be there? I assume not, correct me if I'm wrong.
In C there is the function realloc, which has the effect described above. Is there any equivalent in C++ or java?
How can I dynamically expand an array (without using Vector class, and without copying the array each time in another array with double capacity) in C++ or Java?
Whenever you do new int[X] where X is an integer, in both C++ and Java, you obtain a reference to a newly allocated array.
In Java, arrays are automatically initialized so that each entry has its default value (0 for primitive data types, null for reference data types). In C++, the array is not initialized, you get garbage on it.
If you do:
array = new int[10];
array[0] = 0;
array[1] = 1;
// etc
array = new int[15];
the second time you create an array and put a reference to it in the variable array, you simply lose the reference to your first array. Since it is a new array, it will obey the language's rules for newly allocate arrays: in Java, array will now point to an array of size 15 filled with zeroes; in C++, array will point to an array of size 15 filled with garbage.
In Java, the lost array will be eventually garbage collected for you. In C++, you've just created a memory leak.
Both languages forbid you to resize or, as you put, dynamically expand an array. You can create a new one, copy everything from the old one to the new one, and discard the old one. They might provide methods that make these operations for you, but you won't expand the existing array, you will simply create a new one and copy the data from the old one to the new one.
In Java there's no realloc (but it has Arrays.copyOf, which works similarly), and in C++ (and C as well), realloc won't really extend the array; it will allocate more memory elsewhere, deallocate the memory previously allocated, and return the new pointer: you'd have to replace any existing pointers to the new address!
Finally, for collection classes that dynamically resize themselves, they usually have an internal array and, whenever that array gets full, the class does all that resizing internally: it allocates a new one, bigger, copies the elements, and discards the old one. Since the array is completely encapsulated in the class, you don't need to worry about references to the old array as I explained above.
In java memory management is under control of JVM. That is the beautity of java. You can use System.arraycopy() function to make a copy of an array. If your aim is to expand array just give a bigger array as destination array.
On the other hand you can use collections framework for dynamically expanding collections.
The heart of array concept, both in C++ and Java, is fixed size collection. realloc may look like some kind of backdoor in this conception, but it still doesn't promise to expand given array - it may create array in other location, copy original content and release original memory. And quite probably it will.
So, if you want variable size collection, use std::vector in C++ and ArrayList in Java. Or you can code this functionality by yourself. But I'm afraid you will have to start with own memory allocator, as you cannot make standard one expand once allocated chunk of memory.
will the initial first 10 values still be there?
In C++, there will be somewhere, but you have lost your handle to them. They will be inaccessible. This constitures a memory leak.
int* array=new int[10]; // array points to dynamically allocated array
array=new int[15]; // array points to a completely different place now
In the example above, the array pointer is the only handle you have on the first dynamically allocated array. By making it point elsewhere, you leak the array.
Note also that in C++ the elements of the array are not zero initialized. In order to do that, you need to value initialize the array:
int* array=new int[10]();
// ^^
In Java you cannot dynamically extend an array. There are different data structures for that like ArrayList.
In Java, in your example if no reference is left to the first array with size 10, it will be collected by GarbageCollector.
How can I dynamically expand an array (without using Vector class, and without copying the array each time in another array with double capacity) in Java?
In java.util.Arrays, there are a lot of method to use. In your situation you need copyOf
Api Docs
array = Arrays.copyOf(array, 15);
In C++ new always returns a pointer.
The name of arrays is a pointer to the first element in the array so here is what would happen.
int *array; //get a point of type int
array=new int[10]; //allocate 10 ints, and set the array ponter to the first one
array = new int[15] //allocate 15 ints, and set the array pointer to the first one
the problem is now we have no way of knowing where in memory the first 10 ints are. The operating systems "thinks" we are using it b/c we asked for it. but we cann't use it b/c we don't know where it is.
now for something helpful. Use vectors, vectors are objects in c++ that have dynamic memory allocation built into them, so you don't have to manually do it your self.
If you really want to see how it is done, you can make object that handle memory allocation your self.
The best option in C++ is stl and std::vector<int> I have no idea why you can't use it but lets say, that you can't. Probably the best way:
const int c_startSize = 10;
const int c_increasing = 13; //1.3
int * array;
int arraySize = c_startSize;
array = new int[arraySize];
//some code
//now we need to increase size of array.
int * tmp;
tmp = new int[arraySize * c_increasing / 10];
for (int i = 0; i < arraySize; i++)
tmp[i] = array[i];
arraySize = arraySize * c_increasing / 10;
delete [] array;
array = tmp;
//some code
It is probably the only way. Of course you can use realloc or memcpy to copy values, but it is based on void pointers and for beginners usually it is more tricky. Hopefully this helped, don't forget to make a class or a struct for this thing, otherwise, it will be to much of mess.
EDIT:
Forgot to mention, my answer includes C++ only, no JAVA.
Yes, there is an equivalent in C++, which is Standard C++.
std::vector<int> array(10);
And then
array.resize(15);
The vector manages its storage memory exactly the way you expect. The vector has been designed to replace C's reallocated array pointers. To replace on-stack arrays, you have std::array since C++11. To replace on-stack VLAs, you will have std::dynarray in C++14 or C++17.
And don't get lured, realloc occasionally copies its data. (When it does not find enough space in-place to get your reallocated buffer)
About the equivalent of realloc for C++, no, there is no renew corresponding to new the way there is a realloc corresponding to malloc. And it is not something missing in the language. It has been addressed with the std::vector class. It manages its memory itself, it is efficient, and no, it is not unpure style to use it. It is the standard way in C++ to have an array that can resize.
I have an array
String[] path={abc,bcd};
I pass this array in a method:
addElement(path);
In method
void addElement(String[] path)
{
// here i got value suppose "qsd" and i want to add it after "bcd" ie 2 index of array
path[path.lenght]="qsd";
}
But this is giving me an error.
I dont want to use an ArrayList.
The biggest problem is that arrays in Java are not trivially resizable. What you wind up doing instead is actually creating a new array, and adding each of the elements to that. This will be slower than the ArrayList code, and uglier as well.
This also means that any code which points to the old array will no longer work. If you only have one instance, you could have addElement return the new array like so
String[] addElement(String old[]){
String arr[] = new String[old.length+1];
//copy all the elements in old...
arr[old.length] = "whatever";
return arr;
}
Then use
path = addElement(path);
You should use ArrayList
Otherwise you have to resize the array by allocating new memory of the size of the original array +1, copy the elements from the old one to the new one, and add in the new element.
You can't change the size of emulated array in GWT (even if javascript arrays support this stuff). You'll have always to create a new instance of array. Most common way to solve this problem is to use one of the collection classes (like java.util.ArrayList) . Example:
ArrayList<String> path = new ArrayList<String>(Arrays.asList("abc","bbc"));
path.add("qsd");
can anyone tell me the error in this java declaration String[][] t=new String[15][15]; this works fine and if i use String[][] t=new String[][]; because i need to declare the variable t as dynamic as i am not sure how much values i am going to store in t.
Use ArrayList (or other array object who can handle any number of objects). A java array always has a fixed length since some memory will be reserved for the array.
ArrayList creates such array as well to store the objects. Of you add more abjects as the current reserved size of the array than ArrayList will create a new bigger array (+50% if i'm correct). There are some other implementations that act a bit different (for example they create a new array 100% of the original one when the array is full. If performance is really important for you than you can look into this.
ArrayList<ArrayList<String> t = new ArrayList<ArrayList<String>();
void fill() {
ArrayList<String> t2 = new ArrayList<String>();
t2.add("somestring");
String s = "someotherstring";
t2.add(s);
t.add(t2);
}
If you don't know how big it needs to be just declare it as
String[][] t;
and once you know how big it needs to be you can do (before trying to use the array)
t = new String[15][15];
If you're never sure how big the array need to be, you'll need to use something like a List of Lists.
List<List<String>> t = new ArrayList<List<String>>;
public void add(String str, int row, int col) {
while (row >= t.size())
t.add(new ArrayList<String>());
List<String> row_list = t.get(row);
while (col >= row_list.size())
row_list.add("");
row_list.set(col, str);
}
In Java array objects are always of fixed length. Once you have allocated them you cannot change their size. An array variable can be made to point to different array objects of different size. So you can allocate:
String[][] t;
which doesn't point to an object and allocate an object later once you know the size:
int n1,n2;
// calculate n1,n2
t = new String[n1][n2];
If you need a structure where the size can change you are much better off using ArrayList, which can be dynamically resized.
Declare it as String [][]t = null;
And Reinitialize it with actual length once you get it.
t=new String[x][y];
As bemace said, just because you are declaring the variable doesn't mean you have to initialize it immediately.
As Mark said, arrays have a fixed size. Once an array is initialized(not declared, initialized) it has a fixed size.
So, there are two possibilities:
Either you will know how big the array needs to be before you need to start using it, in which case you can simply delay your initialization as suggested by bemace.
Or you won't know how big it needs to be before you start using it, in which case you need to use a dynamically sized data structure(s). Check out the Java Collections API:
tutorial
api reference
There are several good answers already, but it has now been revealed in a comment to Mark Baijens' answer that the purpose of this question is that raju need a key to multi-value mapping.
Mark followed up that comment by suggesting raju use a HashMap<String, String> hashMap = new HashMap<String, String>(); — however that only works for a single key-value pair.
What raju needs is a
Map<String, Collection<String>> t
= new HashMap<String, List<String>>();
Adding the first value for a key requires initialization of a List for that bucket, while adding additional values requires fetching the existing list and adding the new value.
Note I used Collection<String> in the declaration, so it could be a List if the order of values is important, or it could be a Set to prevent duplicate values under the same key.
This would probably be best implemented as a Class itself, perhaps
public class MultiValueMap<K, V> extends Map<K, V>
{
...
}
so the initialization of the List on the first put(key, value) and the subsequent .add(value) to the list could be hidden in the implementation.