ind2sub is not working properly.
3 vues (au cours des 30 derniers jours)
Afficher commentaires plus anciens
Hadi Kasasbeh
le 16 Août 2017
Commenté : Hadi Kasasbeh
le 16 Août 2017
I have the following piece of code where ind2sub is not working properly because when I plot the function PeLRTfusion in 3D, the results are not compatible. I want to find the coordinates of minimum value of PeLRTfusion. Also, when I use the resulted coordinates again in PeLRTfusion, the value of PeLRTfusion is different than the resulted min value from the code.
MuX1=1;
MuX2=2;
SigmaX1=1;
SigmaX2=0.5;
PH1=0.6;
PH0=1-PH1;
const=6;%A constant for how many sigmas away from the mean the program should go.
step=0.1;%To control the accuracy of the results.
Lower=-const*max(SigmaX1,SigmaX2);
Upper=const*max(SigmaX1,SigmaX2)+max(MuX1,MuX2);
LamdaSearchRange=Lower:step:Upper;
%Pe using the LRT fusion rule.
fun=@(Lamda1,Lamda2) PeLRTfusion(PH1,SigmaX1,SigmaX2,MuX1,MuX2,Lamda1,Lamda2);
PeOfLRT=bsxfun(fun,LamdaSearchRange,LamdaSearchRange');
[MinPeOfLRTval, MinIdx] = min(PeOfLRT(:));
MinPeOfLRTval
[MinLamda1Index, MinLamda2Index] = ind2sub(size(PeOfLRT),MinIdx);
MinLamda1=LamdaSearchRange(MinLamda1Index)
MinLamda2=LamdaSearchRange(MinLamda2Index)
Any help is really appreciated. Thank you.
Réponse acceptée
Stephen23
le 16 Août 2017
Modifié(e) : Stephen23
le 16 Août 2017
Your function PeLRTfusion returns different outputs values depending on the size of the inputs:
>> [v,x] = min(fun(LamdaSearchRange(29),LamdaSearchRange)) % scalar & vector
v =
-1.6092e+042
x =
70
>> [v,x] = min(fun(LamdaSearchRange(29),LamdaSearchRange(70))) % scalar & scalar
v =
0.022712
x =
1
So when you try it with two scalars it gives a different output than with a scalar and a vector. My installed help for bsxfun states "if an M-file function is specified, it must be able to accept either two column vectors of the same size, or one column vector and one scalar, and return as output a column vector of the size as the input values", which tell us that MATLAB passes the entire columns at once to fun. Unfortunately they seem to have removed this useful info from the online help.
In any case, you could either:
- fix your function to work correctly when called with column lambdas.
- use arrayfun (which works element-by-element), instead of bsxfun (which does not).
For the second option you simply need to replace this:
PeOfLRT=bsxfun(fun,LamdaSearchRange,LamdaSearchRange');
with this:
[L1,L2] = ndgrid(LamdaSearchRange);
PeOfLRT = arrayfun(fun,L1,L2);
which gives these values:
MinPeOfLRTval =
0.022712
MinIdx =
9758
MinLamda1Index =
29
MinLamda2Index =
70
We can check these values by hand:
>> fun(LamdaSearchRange(29),LamdaSearchRange(70))
ans =
0.022712
and by viewing the values in 3D:
>> surf(PeOfLRT)

Judging by the long trough there many be many values that are very close to the minimum. Lets check:
>> nnz(abs(PeOfLRT-min(PeOfLRT(:)))<1e-5)
ans =
141
>> nnz(abs(PeOfLRT-min(PeOfLRT(:)))<1e-6)
ans =
6
Which means that quite possibly the minimum value found depends on some floating point error more than being the "exact" function minimum.
Plus de réponses (0)
Voir également
Catégories
En savoir plus sur Creating and Concatenating Matrices dans Help Center et File Exchange
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!