Preallocate variables with unkown size

I pre allocate the two variables phi and phiPrime by setting a maximum size and then crop them afterwards. The thing is that both of them depend on vector b which changes its size in every ii.
I did something like the following but not sure if it is quite correct and computational effective.
but I'm not sure whether the way I preallocated the variables lead into wrong results or not.
function [G_dmg, G_orig, phic, inActiveSorted] = SH_decision(G_dmg, G_orig, phic)
N = numnodes(G_dmg);
inActive = find(degree(G_dmg)==0);
impact = -1* ones(1,length(inActive));
phi = zeros(N, 1);
phiPrime = zeros(N, 1);
phidPrime = zeros(N, 1);
lastIdx = 0;
numNeighborsPernode = [];
activeNeighbors = [];
for ii = 1:length(inActive)
b = neighbors(G_orig, inActive(ii));
if ~isempty (b)
degreeOrig = degree(G_orig, b);
degreeDmg = degree(G_dmg, b);
phi(lastIdx + 1: length(b)+lastIdx) = degreeDmg./degreeOrig;
phiPrime(lastIdx + 1: length(b)+lastIdx) = degreeRestoration./degreeOrig ;
impact(ii) = nnz(phi(lastIdx + 1: length(b)+lastIdx)<=phi & phiP(lastIdx + 1: length(b)+lastIdx)>phi);
phidPrime = phiPrime - phi;
lastIdx = lastIdx + length(b);
end
end
phi = phi(1:lastIdx, :);
phiPrime = phiPrime(1:lastIdx, :);
phidPrime = phidPrime(1:lastIdx, :);
end

2 Comments

Is phi and phiPrime are vectors at the end?
Why you are using (lastIdx + 1: length(b)+lastIdx) as the index while saving inside loop?
Thanks for your reply.
Yes, I'm getting them as vectors.

Sign in to comment.

 Accepted Answer

Bruno Luong
Bruno Luong on 23 May 2022
Edited: Bruno Luong on 23 May 2022
You can compute exactly the size needed for your vectors
A = G_orig.adjacency;
A(inActive,:) = 0;
m = nnz(A(:,inActive));
phi = zeros(m, 1);
phiPrime = zeros(m, 1);
...

13 Comments

Bruno Luong
Bruno Luong on 24 May 2022
Edited: Bruno Luong on 24 May 2022
I only answer the preallocation part, as the subject of the question suggests "Preallocate variables with unkown size".
The rest of the code (strated from the for-loop) of what to compute I did not make any comment, since I cannot guess what you want from your code (without any relevant comment), and you never clearly state what you the function suppose to compute.
You are right. I neither added comments to my code nor I stated what I am trying to compute. I appologize.
I tried my best to explain my function mechanism by adding relevant comments. Hope this elaborates the issue I'm facing. thanks again for taking some time to help me over. Much appreciated.
It looks like what you want is to use sortrows
[impactandphid, idx] = sortrows([impact(:) phidPrime(:)],'[-1 -1])
It will sort impact (in descending order) then if draw sort phidPrime (also in descending order).
phidPrime and impact have different dimensions, so I'm getting the "Dimensions of arrays being concatenated are not consistent." error.
The second array is whatever you state here:
inActivesorted (size of 20x1) = [155 344 50 66 71 2 5 14 39 3 22 89 86 65 222 16 74 11 19 20]
I don't know how this is named/computed in your code, it's tha same length (20) as imp.
imp (size of 20x1) = [4 4 3 3 3 3 2 2 2 2 2 2 2 1 1 1 1 1 1 1]'.
There are three variables, imp, inActivesorted and phidPrime. Both inActivesorted and imp have the same size. phidPrime as I stated in my comment have a bigger size.
>Sorry I still don't quite understand what you are trying to do. Your description is not clear to me at all.
You say it yourself
% I noticed that some of inactive nodes after sorting them have the same impact so I am trying to have
% a second criteria based on the difference between phi and phiPrime of each one of those nodes having the same
% impact but it looks it's impossible since phidPrime has a different size
% than imp
May be you want to compute the sum of the difference over b of (phiPrime - phi) in the first for-loop? Who knows? We are not here to define for your what you want to compute.
Then compute the average of phidPrime values in the first loop then use it later.
Thank you much. But could you please tell me how to group the values of phidPrime based on the values in
numNeighborsPerNode
numNeighborsPerNode = [1 1 1 3 3 1 6 0 1 1]
phidPrime = [0.20 0.17 0.20 0.20 0.11 0.25 0.25 0.20 0.25 0.17 0.25 0.25 0.17 0.25 0.33 0.25 0.20 0.20];
% I must find the average of the elements of phidPrime based on the values
% in numNeighborsPerNode. For instance, phidPrime(1) is the only neighbor node. But
% phidPrime(4), phidPrime(5), phidPrime(6) are 3 nodes based on numNeighborsPerNode(4) and I should
% find the average value among them. And do the same pattern for other
% phidPrime
In the for-loop instead of
phiPrime(lastIdx + 1: length(b)+lastIdx) = degreeRestoration./degreeOrig;
do
avgphiPrime(ii) = mean(degreeRestoration./degreeOrig);
Shall I do the same for phi as well?
Bruno Luong
Bruno Luong on 25 May 2022
Edited: Bruno Luong on 25 May 2022
If you need it, yes.

Sign in to comment.

More Answers (0)

Categories

Find more on Loops and Conditional Statements in Help Center and File Exchange

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!