How do you fill an array with a for loop?
I'm trying to do this, but I need to fill my array at declaration. Or Am I just wrong?
I need to do this with a 2 dimensional array, it's not necessary, just 2 arrays is also fine
Don't use a for loop. You can use Array.init or Array.zeroCreate if you want to fill it with the default value.
For 2d arrays the same functions are available in the module Array2D, here's an example:
let x: int [,] = Array2D.zeroCreate 2 6
It creates and initialise an array of 2x6 with 0.
Filling your array at the declaration is actually a good practice, that's why this way is better than using for loops.
Related
I it possible to create a two dimensional array of two dimensional arrays in Delphi; and if so how do you access the addresses in it?
My aim is to create something similar to a sudoku grid where you have smaller grids inside of a bigger one.
It would work much better in stead of ex. Declaring multiple 2D arrays of the same type or one big array.
Something like
type
TSmallGrid = array[1..3, 1..3] of Integer;
TBigGrid = array[1..3, 1..3] of TSmallGrid;
should work. Access to BigArray: TBigGrid would be with standard Pascal array syntax:
MyInt := BigArray[1, 2, 1, 2]; // or even BigArray[1, 2][1, 2] to emphasize the nesting
or
SmallArray := BigArray[1, 2];
I have a dozens of arrays with different array names and I would like to do some mathematical calculations in to for loop array by array. I srucked in calling these array into for loop. Is there anybody can help me with this problem? text1 array contains array names. My "s" struct has all these arrays with the same name content of text1 array.
text1=['s.CustomerArray.DistanceDriven','s.CustomerArray.TimeDriven'];
for i=1:3
parameter=str2num(text1(i));
k=size(parameter,2);
a=100;
y=zeros(a,k);
end
After this part my some other calculations should start using "parameter"
Regards,
Eren
I think you are doing several things wrong, here are some pointers.
Rather than listing them manually, consider looping over the fieldnames which can be obtained automatically.
If you are looping over strings, make sure to use a cell array with , rather than a matrix.
If you have a constant, declare it outside the loop, rather than inside the loop. This won't break the code but just makes for obsolete evaluations.
If you want to store results obtained inside a loop, make sure to add an index to the variable that you loop over.
That being said, here is a guess at what you are trying to do:
f = fieldnames(s.CustomerArray);
y = cell(numel(f),1);
parameter = NaN(numel(f),1);
for t = 1:numel(f)
parameter(t) = s.CustomerArray.(f{t});
y{t} = zeros(100,numel(f{t}));
end
I had to read data from a file and store all data in a one dimensional array.
However, Some data I have to store in a matrix (2 dimensional array) How Can I do this?
For example if my data is 1x7 array [1,2,3,1,5,2,8] and the first to 6th belong to a matrix 2x3 how can I store in a new array variable?
Suppose that your 7-element array is called array7, then the following expression should return a 2x3 array containing the first 6 elements of array7
reshape(array7(1:6),[2,3])
If that puts the elements into the new array in the wrong order, try
reshape(array7(1:6),[2,3],order=[2,1])
Note that I've used a named optional argument in the second version, there is another optional argument (pad) which would be, by default, the 3rd argument to reshape.
Is it possible to apply the idea of array in C to MATLAB
For example, if we have
Double array[10];
and if we want to assign a value we write for example
Array[5]=2;
Is there any way to write equivalent one in MATLAB ?
I'm not sure what you mean by "Is it possible to apply the idea of array in C to MATLAB". An array is just a 1D list of numbers (or other data types). MATLAB primarily is designed to work with matrices (MATLAB is short for Matrix laborartory) and an array or vector is simply a special case of a matrix. So I guess the answer to your question is yes, if I have understood correctly.
To initialise arrays or matrices in MATLAB we use zeros or ones:
>> array = zeros(1,5)
array =
0 0 0 0 0
We can then index elements of the array in the same way as C:
>> array(3) = 3
array =
0 0 3 0 0
Note, however, that MATLAB array indexing is one based whereas C arrays are zero based.
This article describes matrix/array indexing in MATLAB.
You can define your own class, override the [] operator.
I described the mechanism in Here
Since it is a custom function, you might as well change the 1-based indexing to 0-based indexing.
Regarding the constructor, I doubt that you can do it.
Anyhow, why would you want to do it?
You will confuse all of the Matlab users, and cause havoc.
When in Rome, do as Romans do.
Yes you can. Arrays are used in C and MATLAB and they can be used for the same functions. Except, please keep in mind the array-indexing of C and MATLAB are different.
The first element of a C array has an index of zero. i.e. in X = [10 20 30 40], x[0] will return 10. But in MATLAB, this will give an error. To access the number 10, you have to use the expression x[1] in MATLAB.
There is no indexing operator []. You must use () for indexing array.
If you write
x = 1:10;
x[2]
then you'll get the following error
x[2]
|
Error: Unbalanced or unexpected parenthesis or bracket.
Is there any way to "vector" assign an array of struct.
Currently I can
edges(1000000) = struct('weight',1.0); //This really does not assign the value, I checked on 2009A.
for i=1:1000000; edges(i).weight=1.0; end;
But that is slow, I want to do something more like
edges(:).weight=[rand(1000000,1)]; //with or without the square brackets.
Any ideas/suggestions to vectorize this assignment, so that it will be faster.
Thanks in advance.
This is much faster than deal or a loop (at least on my system):
N=10000;
edge(N) = struct('weight',1.0); % initialize the array
values = rand(1,N); % set the values as a vector
W = mat2cell(values, 1,ones(1,N)); % convert values to a cell
[edge(:).weight] = W{:};
Using curly braces on the right gives a comma separated value list of all the values in W (i.e. N outputs) and using square braces on the right assigns those N outputs to the N values in edge(:).weight.
You can try using the Matlab function deal, but I found it requires to tweak the input a little (using this question: In Matlab, for a multiple input function, how to use a single input as multiple inputs?), maybe there is something simpler.
n=100000;
edges(n)=struct('weight',1.0);
m=mat2cell(rand(n,1),ones(n,1),1);
[edges(:).weight]=deal(m{:});
Also I found that this is not nearly as fast as the for loop on my computer (~0.35s for deal versus ~0.05s for the loop) presumably because of the call to mat2cell. The difference in speed is reduced if you use this more than once but it stays in favor of the for loop.
You could simply write:
edges = struct('weight', num2cell(rand(1000000,1)));
Is there something requiring you to particularly use a struct in this way?
Consider replacing your array of structs with simply a separate array for each member of the struct.
weights = rand(1, 1000);
If you have a struct member which is an array, you can make an extra dimension:
matrices = rand(3, 3, 1000);
If you just want to keep things neat, you could put these arrays into a struct:
edges.weights = weights;
edges.matrices = matrices;
But if you need to keep an array of structs, I think you can do
[edges.weight] = rand(1, 1000);
The reason that the structs in your example don't get initialized properly is that the syntax you're using only addresses the very last element in the struct array. For a nonexistent array, the rest of them get implicitly filled in with structs that have the default value [] in all their fields.
To make this behavior clear, try doing a short array with clear edges; edges(1:3) = struct('weight',1.0) and looking at each of edges(1), edges(2), and edges(3). The edges(3) element has 1.0 in its weight like you want; the others have [].
The syntax for efficiently initializing an array of structs is one of these.
% Using repmat and full assignment
edges = repmat(struct('weight', 1.0), [1 1000]);
% Using indexing
% NOTE: Only correct if variable is uninitialized!!!
edges(1:1000) = struct('weight', 1.0); % QUESTIONABLE
Note the 1:1000 instead of just 1000 when indexing in to the uninitialized edges array.
There's a problem with the edges(1:1000) form: if edges is already initialized, this syntax will just update the values of selected elements. If edges has more than 1000 elements, the others will be left unchanged, and your code will be buggy. Or if edges is a different type, you could get an error or weird behavior depending on its existing datatype. To be safe, you need to do clear edges before initializing using the indexing syntax. So it's better to just do full assignment with the repmat form.
BUT: Regardless of how you initialize it, an array-of-structs like this is always going to be inherently slow to work with for larger data sets. You can't do real "vectorized" operations on it because your primitive arrays are all broken up in to separate mxArrays inside each struct element. That includes the field assignment in your question – it is not possible to vectorize that. Instead, you should switch a struct-of-arrays like Brian L's answer suggests.
You can use a reverse struct and then do all operations without any errors
like this
x.E(1)=1;
x.E(2)=3;
x.E(2)=8;
x.E(3)=5;
and then the operation like the following
x.E
ans =
3 8 5
or like this
x.E(1:2)=2
x =
E: [2 2 5]
or maybe this
x.E(1:3)=[2,3,4]*5
x =
E: [10 15 20]
It is really faster than for_loop and you do not need other big functions to slow your program.