How to use subsref in MATLAB - matlab

I use 16a. I found overloading subsref makes any function calls to an object call (). I am not sure if this is the correct use of subsref. For example,
classdef A < handle
methods
function obj = A(varargin)
end
function v = subsref(obj, S) %#ok<STOUT,INUSD>
assert(false);
end
function c = foo(obj) %#ok<MANU>
c = 1;
end
end
end
Then I god the following errors when using foo.
>> a = A()
a =
A with no properties.
>> a.foo()
Error using A/subsref (line 6)
Assertion failed.
8 assert(false);
If I removed subsref, it works fine. In terms of
http://www.mathworks.com/help/matlab/ref/subsref.html
subsref is called only when A{i}, A(i) or A.field. Since foo is a method, why is subsref still called?

This is completely expected behavior, because to MATLAB, A.field and A.method both use the dot referencing and therefore are processed by subsref. The typical way of getting around this is to instead call your class methods using the standard function call rather than a dot referenced method call.
method(A)
%// Rather than
A.method()
This usage is also superior as it can operate on arrays of objects rather than only scalars. Also, it is more performant.

Related

Can I write multiple statements in an anonymous function? [duplicate]

I'd like to do something like this:
>> foo = #() functionCall1() functionCall2()
So that when I said:
>> foo()
It would execute functionCall1() and then execute functionCall2(). (I feel that I need something like the C , operator)
EDIT:
functionCall1 and functionCall2 are not necessarily functions that return values.
Trying to do everything via the command line without saving functions in m-files may be a complicated and messy endeavor, but here's one way I came up with...
First, make your anonymous functions and put their handles in a cell array:
fcn1 = #() ...;
fcn2 = #() ...;
fcn3 = #() ...;
fcnArray = {fcn1 fcn2 fcn3};
...or, if you have functions already defined (like in m-files), place the function handles in a cell array like so:
fcnArray = {#fcn1 #fcn2 #fcn3};
Then you can make a new anonymous function that calls each function in the array using the built-in functions cellfun and feval:
foo = #() cellfun(#feval,fcnArray);
Although funny-looking, it works.
EDIT: If the functions in fcnArray need to be called with input arguments, you would first have to make sure that ALL of the functions in the array require THE SAME number of inputs. In that case, the following example shows how to call the array of functions with one input argument each:
foo = #(x) cellfun(#feval,fcnArray,x);
inArgs = {1 'a' [1 2 3]};
foo(inArgs); %# Passes 1 to fcn1, 'a' to fcn2, and [1 2 3] to fcn3
WORD OF WARNING: The documentation for cellfun states that the order in which the output elements are computed is not specified and should not be relied upon. This means that there are no guarantees that fcn1 gets evaluated before fcn2 or fcn3. If order matters, the above solution shouldn't be used.
The anonymous function syntax in Matlab (like some other languages) only allows a single expression. Furthermore, it has different variable binding semantics (variables which are not in the argument list have their values lexically bound at function creation time, instead of references being bound). This simplicity allows Mathworks to do some optimizations behind the scenes and avoid a lot of messy scoping and object lifetime issues when using them in scripts.
If you are defining this anonymous function within a function (not a script), you can create named inner functions. Inner functions have normal lexical reference binding and allow arbitrary numbers of statements.
function F = createfcn(a,...)
F = #myfunc;
function b = myfunc(...)
a = a+1;
b = a;
end
end
Sometimes you can get away with tricks like gnovice's suggestion.
Be careful about using eval... it's very inefficient (it bypasses the JIT), and Matlab's optimizer can get confused between variables and functions from the outer scope that are used inside the eval expression. It's also hard to debug and/or extent code that uses eval.
Here is a method that will guarantee execution order and, (with modifications mentioned at the end) allows passing different arguments to different functions.
call1 = #(a,b) a();
call12 = #(a,b) call1(b,call1(a,b));
The key is call1 which calls its first argument and ignores its second. call12 calls its first argument and then its second, returning the value from the second. It works because a function cannot be evaluated before its arguments. To create your example, you would write:
foo = #() call12(functionCall1, functionCall2);
Test Code
Here is the test code I used:
>> print1=#()fprintf('1\n');
>> print2=#()fprintf('2\n');
>> call12(print1,print2)
1
2
Calling more functions
To call 3 functions, you could write
call1(print3, call1(print2, call1(print1,print2)));
4 functions:
call1(print4, call1(print3, call1(print2, call1(print1,print2))));
For more functions, continue the nesting pattern.
Passing Arguments
If you need to pass arguments, you can write a version of call1 that takes arguments and then make the obvious modification to call12.
call1arg1 = #(a,arg_a,b) a(arg_a);
call12arg1 = #(a, arg_a, b, arg_b) call1arg1(b, arg_b, call1arg1(a, arg_a, b))
You can also make versions of call1 that take multiple arguments and mix and match them as appropriate.
It is possible, using the curly function which is used to create a comma separated list.
curly = #(x, varargin) x{varargin{:}};
f=#(x)curly({exp(x),log(x)})
[a,b]=f(2)
If functionCall1() and functionCall2() return something and those somethings can be concatenated, then you can do this:
>> foo = #() [functionCall1(), functionCall2()]
or
>> foo = #() [functionCall1(); functionCall2()]
A side effect of this is that foo() will return the concatenation of whatever functionCall1() and functionCall2() return.
I don't know if the execution order of functionCall1() and functionCall2() is guaranteed.

Inheritance in matlab

I am having some trouble with matlab. I am working with b-splines. Sometimes I want to work with the actual spline, while other times I only want to use the so-called basis functions. Without diving into the theory of b-splines, the practical difference is that the when I want to work with the b-spline, I need an extra method and property. I want this property to be initialized by passing it in the constructor.
What I have so far (with most irrelevant methods and properties removed) hopefully roughly demonstrates the behavior that I want:
bsplinespace.m:
classdef bsplinespace < handle
properties
p % polynomial degree
end
methods
function result = bsplinespace(p)
result.p = p;
end
end
end
bspline.m:
classdef bspline < bsplinespace
properties
controlpoints
end
methods
function result = bspline(p, controlpoints)
result.controlpoints = controlpoints;
end
function result = getp(this)
result = this.p;
end
end
end
However, in this scenario the bspline constructor calls the bsplinespace constructor without passing any arguments, causing it to crash:
Not enough input arguments.
Error in bsplinespace (line 8)
result.p = p;
Error in bspline (line 7)
function result = bspline(p, controlpoints)
To be more explicit, what I want is:
One class bsplinespace, which has a constructor which accepts one parameter p
A class bspline, which is the same, but has an extra property and method
Is there an elegant way to implement this?
In your constructor method for bspline, you need to explicitly call the superclass constructor with input argument p:
function result = bspline(p, controlpoints)
result#bsplinespace(p)
result.controlpoints = controlpoints;
end
Otherwise MATLAB will call the superclass constructor with zero input arguments, and you'll get the error you're seeing.
It's a perfectly sensible design, and allows you to control the details of how arguments to the subclass constructor are passed through to the superclass constructor (or not, if you'd like to provide default arguments instead).

Can an anonymous function in MATLAB have more than one line? [duplicate]

I'd like to do something like this:
>> foo = #() functionCall1() functionCall2()
So that when I said:
>> foo()
It would execute functionCall1() and then execute functionCall2(). (I feel that I need something like the C , operator)
EDIT:
functionCall1 and functionCall2 are not necessarily functions that return values.
Trying to do everything via the command line without saving functions in m-files may be a complicated and messy endeavor, but here's one way I came up with...
First, make your anonymous functions and put their handles in a cell array:
fcn1 = #() ...;
fcn2 = #() ...;
fcn3 = #() ...;
fcnArray = {fcn1 fcn2 fcn3};
...or, if you have functions already defined (like in m-files), place the function handles in a cell array like so:
fcnArray = {#fcn1 #fcn2 #fcn3};
Then you can make a new anonymous function that calls each function in the array using the built-in functions cellfun and feval:
foo = #() cellfun(#feval,fcnArray);
Although funny-looking, it works.
EDIT: If the functions in fcnArray need to be called with input arguments, you would first have to make sure that ALL of the functions in the array require THE SAME number of inputs. In that case, the following example shows how to call the array of functions with one input argument each:
foo = #(x) cellfun(#feval,fcnArray,x);
inArgs = {1 'a' [1 2 3]};
foo(inArgs); %# Passes 1 to fcn1, 'a' to fcn2, and [1 2 3] to fcn3
WORD OF WARNING: The documentation for cellfun states that the order in which the output elements are computed is not specified and should not be relied upon. This means that there are no guarantees that fcn1 gets evaluated before fcn2 or fcn3. If order matters, the above solution shouldn't be used.
The anonymous function syntax in Matlab (like some other languages) only allows a single expression. Furthermore, it has different variable binding semantics (variables which are not in the argument list have their values lexically bound at function creation time, instead of references being bound). This simplicity allows Mathworks to do some optimizations behind the scenes and avoid a lot of messy scoping and object lifetime issues when using them in scripts.
If you are defining this anonymous function within a function (not a script), you can create named inner functions. Inner functions have normal lexical reference binding and allow arbitrary numbers of statements.
function F = createfcn(a,...)
F = #myfunc;
function b = myfunc(...)
a = a+1;
b = a;
end
end
Sometimes you can get away with tricks like gnovice's suggestion.
Be careful about using eval... it's very inefficient (it bypasses the JIT), and Matlab's optimizer can get confused between variables and functions from the outer scope that are used inside the eval expression. It's also hard to debug and/or extent code that uses eval.
Here is a method that will guarantee execution order and, (with modifications mentioned at the end) allows passing different arguments to different functions.
call1 = #(a,b) a();
call12 = #(a,b) call1(b,call1(a,b));
The key is call1 which calls its first argument and ignores its second. call12 calls its first argument and then its second, returning the value from the second. It works because a function cannot be evaluated before its arguments. To create your example, you would write:
foo = #() call12(functionCall1, functionCall2);
Test Code
Here is the test code I used:
>> print1=#()fprintf('1\n');
>> print2=#()fprintf('2\n');
>> call12(print1,print2)
1
2
Calling more functions
To call 3 functions, you could write
call1(print3, call1(print2, call1(print1,print2)));
4 functions:
call1(print4, call1(print3, call1(print2, call1(print1,print2))));
For more functions, continue the nesting pattern.
Passing Arguments
If you need to pass arguments, you can write a version of call1 that takes arguments and then make the obvious modification to call12.
call1arg1 = #(a,arg_a,b) a(arg_a);
call12arg1 = #(a, arg_a, b, arg_b) call1arg1(b, arg_b, call1arg1(a, arg_a, b))
You can also make versions of call1 that take multiple arguments and mix and match them as appropriate.
It is possible, using the curly function which is used to create a comma separated list.
curly = #(x, varargin) x{varargin{:}};
f=#(x)curly({exp(x),log(x)})
[a,b]=f(2)
If functionCall1() and functionCall2() return something and those somethings can be concatenated, then you can do this:
>> foo = #() [functionCall1(), functionCall2()]
or
>> foo = #() [functionCall1(); functionCall2()]
A side effect of this is that foo() will return the concatenation of whatever functionCall1() and functionCall2() return.
I don't know if the execution order of functionCall1() and functionCall2() is guaranteed.

When can I pass a function handle?

I have a function for cached evaluation. As one of the arguments, it takes a function handle. Under some circumstances, the function handle is unaccessible, and I don't quite understand why. The example below shows what got me stumped:
>> A.a = #plus; feval(#A.a, 1, 1)
ans =
2
>> clear A
>> A.a.a = #plus; feval(#A.a.a, 1, 1)
Error using feval
Undefined function 'A.a.a' for input arguments of type 'double'.
So, if I have a function handle stored as a structure member, I can pass it along fine if it's one level deep, but not if it's two levels deep. In my real use case, I have a structure D that holds many (117) instances of various classes, so I actually have stct.obj.meth, where stct is a structure, obj is a class instance/object, and meth is a method. Passing #stct.obj.meth fails, but if I assign A = stct.obj, then passing #A.meth succeeds.
Under what conditions can I pass a function handle as an argument, so that it's still accessible down the stack?
Edit: Although in the use case above, I could simply remove the # because #plus is already a function handle. However, consider the situation here:
>> type cltest.m
classdef cltest < handle
methods
function C = mymeth(self, a, b)
C = a + b;
end
end
end
>> A.a = cltest();
>> feval(#A.a.mymeth, 1, 1)
Error using feval
Undefined function 'A.a.mymeth' for input arguments of type 'double'.
>> b = A.a;
>> feval(#b.mymeth, 1, 1)
ans =
2
In this case, I need the # before A.a.mymeth...
Introducing classes was a big deal for MATLAB. So big, in fact, that they still do not work properly today. Your example shows that structure access and class method access conflict, because they had to overload the the meaning of dot '.' and didn't get it to work seamlessly. It all more or less works fine when you are calling class methods explicitly by their name on the MATLAB console, e.g. in your example >> A.a.mymeth(1,1). But when you have any type of indirection, it soon breaks.
You tried getting the function handle by >> #A.a.mymeth, which MATLAB cannot make sense of, probably because it gets confused by the mixed structure/class thing. Trying to work around using str2func doesn't work either. It works, again, only for explicit name access, as shown here. It breaks for your example, e.g. >> str2func('b.mymeth'). It does not even work inside the class. Try other indirections and watch them fail.
Additionally, MATLAB does not like giving you a class method's handles. There's no function for it. There's no way to get all function handles in one go, or even dynamically by a name string.
I see three options here. First, try changing your program, if possible. Do these functions need to sit in a classdef?
Second, follow your or nispio's workaround. They both create a temporary variable to hold a reference to the class instance in order to create a non-mixed access to its member methods. The problem is, they both require explicitly naming the function. You have to explicitly put this code for every function involved. No way to abstract that out.
Third, cheat by giving out your class' method handles from the inside. You can give them out in a structure.
classdef cltest < handle
methods
function C = mymeth(self, a, b)
C = a + b;
end
function hs = funhandles(self)
hs = struct('mymeth', #self.mymeth, ...
'mymeth2', #self.mymeth2);
end
end
end
You can then access the handles by name, even dynamically.
>> A.a = cltest;
>> feval(A.a.funhandles.mymeth, 1, 1);
>> feval(A.a.funhandles.('mymeth'), 1, 1)
ans =
2
But be careful, by using this you can access Access=private methods from outside.
Try this:
feval(#(varargin)A.a.mymeth(varargin{:}),1,1);
It is a little kludgy, but it should work.
EDIT:
The way it works is by creating an Anonymous Function that takes a variable number of arguments, and dumps those arguments into the method A.a.mymeth(). So you are not actually passing a pointer to the function A.a.mymeth, you are passing a pointer to a function that calls A.a.mymeth.
An alternative way of achieving the same thing without using varargin would be:
feval(#(x,y)A.a.mymeth(x,y),1,1);
This creates an anonymous function that accepts two arguments, and passes them along to A.a.mymeth.
<speculation> I think that it must be inherent in the way that the unary function handle operator # works. The Matlab parser probably looks at #token and decides whether token is a valid function. In the case of a.mymeth it is smart enough to decide that mymeth is a member of a, and then return the appropriate handle. However, when it sees A.a.mymeth it may discover that A is not a class, nor does A have a member named a.mymeth and therefore no valid function is found. This seems to be supported by the fact that this works:
A.a.a = #plus; feval(A.a.a,1,1)
and this doesn't:
A.a.a = #plus; feval(#A.a.a,1,1)
</speculation>
You can get around it by introducing a separate function that corrects what # operator is not doing:
function h=g(f)
x = functions(f);
if ~strcmp(x.type, 'anonymous')
h = evalin('caller', ['#(varargin)' x.function '(varargin{:})']);
else
h = f;
end
end
Now for your example:
>> feval(g(#A.a.mymeth), 1, 1)
ans =
2
>> feval(g(#b.mymeth), 1, 1)
ans =
2
I think this will have the smallest impact on your code. You can make it a bit more elegant but less robust and/or readable. The uplus method is not defined for function_handle class so you can create uplus.m in folder #function_handle somewhere in your path with this content:
function h=uplus(f)
x = functions(f);
if ~strcmp(x.type, 'anonymous')
h = evalin('caller', ['#(varargin)' x.function '(varargin{:})']);
else
h = f;
end
end
Now you just need to use +# instead of #. For your examples:
>> feval(+#A.a.mymeth, 1, 1)
ans =
2
>> feval(+#b.mymeth, 1, 1)
ans =
2

OOP Matlab inheritance issue with Matlab coder (Simulink MATLAB Function block)

I have defined an abstract base class measurementHandler < handle which defines the interface for all inherited classes. Two subclasses of this class are a < measurementHandler and b < measurementHandler.
I now have a function which should return a handle to an instance of either of these subclasses (depending on the function arguments) to it's caller. Consider something like this:
function returnValue = foobar(index)
if index == 0
returnValue = a();
else
returnValue = b();
end
end
This function is enclosed in a MATLAB Function block in Simulink (2013a). When I try to simulate the system, I get the following error:
Type name mismatch (a ~= b).
Can anybody suggest a workaround for this which still allows me to take advantage of OOP & inheritance when using Simulink?
This kind of pattern is possible in MATLAB Function block only if the "if" condition can be evaluated at compile time. The types cannot be switched at run-time. Can you make the index value a constant at the call site?
The main reason to use this pattern was to iterate over a measurementHandler Array, while these all can have custom implementations. I was able to do this by unrolling the loop with the coder.unroll directive. Example for the enclosing MTALAB Function block:
function result = handleAllTheMeasurements(someInputs)
%#codegen
for index = coder.unroll(1:2)
measurementHandler = foobar(index);
measurementHandler.handleMeasurement(someInputs);
end
result = something;
end
This way, the for loop gets unrolled at compile time and the return type of the function is well defined for each separate call.