how i can fix matlab function block coder.extrinsic issue ?
Show older comments
I am usign MATlab function block in my simulation model as relay such as
function y = fcn(P,T)
if(T <= 12.0)
y=1;
else
if (P <= 4800000)
y=0;
else
y=1;
end
end
and it is working well for my model
but I want to use mean of 5 maximum peaks value in a specific interval such as
function y = fcn(P,T)
if(T <= 12.0)
y=1;
else
if((mean(maxk(findpeaks(P((T >= 12) & (T <= 12.1))),5))) <= 4800000)
y=0;
else
y=1;
end
end
but when I use this command
(mean(maxk(findpeaks(P((T >= 12) & (T <= 12.1))),5)))
in my matlab function then following error appears
Function 'maxk' is not supported for code generation. Consider adding coder.extrinsic('maxk') at the top of the function to bypass code generation
where as this command is forking well in command window, I don’t know why this error appearing and how I can fix it
I need help regarding this issue
Answers (1)
Walter Roberson
on 8 Apr 2019
Right after the function line, add the line
coder.extrinsic('maxk');
Note: you will not be able to run your code with any acceleration turned on.
In order to be able to run your code with accelation turned on, you will need to convert to using sort() and extracting the values you are interested in.
21 Comments
zubair younas
on 9 Apr 2019
Walter Roberson
on 9 Apr 2019
You need to predefine a variable with zeros(1,5), and assign the output of the maxk(expression,5) to that variable. Then you can do the mean() calculation on that variable and so on.
zubair younas
on 11 Apr 2019
Walter Roberson
on 11 Apr 2019
function y = fcn(P,T)
coder.extrinsic('maxk');
maxk_result = zeros(1,5);
if (T <= 12.0)
y=1;
else
maxk_result = maxk(findpeaks(P((T >= 12) & (T <= 12.1))),5);
if ((mean(maxk_result)) <= 4800000)
y=0;
else
y=1;
end
end
However I would tend to expect that it will now complain about findpeaks().
Are you expecting your T to be a scalar or a vector? What output are you expecting if T > 12.1 ?
zubair younas
on 11 Apr 2019
Walter Roberson
on 11 Apr 2019
You need to defer the R=(maxk...) to after the else. Otherwise when T < 12, you are calling findpeaks with P(false) which is empty.
The code I posted uses the right order, but would still have problems if T > 12.1. I asked you what should be done for that case, but you did not happen to respond.
zubair younas
on 11 Apr 2019
Walter Roberson
on 11 Apr 2019
What is the structure of P ? Is it a static 2D array that has rows corresponding to time? Is it a changing vector all of which should be put through findpeaks provided the time is 12.0 to 12.1 ?
Walter Roberson
on 11 Apr 2019
function y = fcn(P,T)
persistent prev_y
if isempty(prev_y)
prev_y = 1;
end
coder.extrinsic('maxk');
R = zeros(1,5);
if T <= 12.0
y=1;
prev_y = y;
elseif T > 12.1
y = prev_y;
else
R = maxk(findpeaks(P),5);
y = double(mean(R) <= 4800000); %convert logical to numeric
prev_y = y;
end
zubair younas
on 11 Apr 2019
zubair younas
on 11 Apr 2019
Walter Roberson
on 11 Apr 2019
Is the first column of P time? Or the first row? That is, does a particular row or column of P need to be selected based upon the current time?
Or is the original P coming from a From File Block or something like that? Because if it is, then what you would receive at any time is probably going to be a vector representing the (interpolated) current value of P.
It is not obvious to me how R could be undefined. Did you copy that most recent version of mine, the one with the persistent variable ?
zubair younas
on 11 Apr 2019
zubair younas
on 11 Apr 2019
zubair younas
on 11 Apr 2019
Walter Roberson
on 11 Apr 2019
It looks to me as if your P is a timeseries. If so then at any time, the number of values that would be passed in through the P parameter would be the same as the number of columns of Scope2.signals.values, which is to say only 1. At the moment I do not understand what you would be findpeaks() of.
However, if the code before was working for you up to time 12.1, then try the code I posted that uses persistent
zubair younas
on 12 Apr 2019
zubair younas
on 12 Apr 2019
Walter Roberson
on 12 Apr 2019
Before T = 12, you are hitting the T <= 12.0 condition that does not require examining the input.
After T = 12, you start to try to use the contents of the P input. However, as I explained to you before, your P is a timeseries, and since it only has one column, you are only going to be passed one value of P at any given time -- the P appropriate for that time (either interpolated or held from the previous time that was explicitly in the data.)
zubair younas
on 13 Apr 2019
Walter Roberson
on 13 Apr 2019
You want to examine the peaks of something that is a single reading.
- You could give up on the idea of "peaks" and simply compare the single value in P to 4800000 .
- You could use a multi-tap delay line or memory buffer to hold on to a certain number of recent samples, and examine the peaks of those
- perhaps you could give up on the peaks part, and instead integrate your signal, and subtract from that the integral of the signal taken at an earlier time (and held through a delay line or something similar), and divide by the time difference, to get a mean of the entire signal over that time (there might well be other ways to create a "moving mean" block.) In context, perhaps that moving mean might be good enough for your purposes. It depends: is your signal prone to sharp narrow large spikes and that is why you are looking for peaks, or are you looking for the case where the signal value has become overall large for a while ?
- perhaps in context it would make sense to transform your timeseries into a constant block where the entire past and future history is available, and have your MATLAB Function Block somehow select from that based on time. Remember, though, that the function block is being invoked repeatedly, always for a specific time, not for a range of times.
Categories
Find more on Signal Generation 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!