在matlab中覆盖抽象类的empty()方法

hoo*_*one 5 oop matlab

我多次遇到过这个问题,我希望最终解决这个问题.

上下文

在MATLAB中创建异构类层次结构时,会调用一个受保护的静态方法getDefaultScalarElement,它允许您定义用于创建数组的默认标量对象.如果层次结构的元素是抽象的,则可以覆盖该方法以使用其他类.

例如

classdef (Abstract) AbstractRoot < matlab.mixin.Heterogeneous

    methods (Static, Access = protected)
        function DefaultObj = getDefaultScalarElement()
            DefaultObj = ConcreteSubclass1();
        end
    end

end

classdef ConcreteSubclass1 < AbstractRoot

end

classdef ConcreteSubclass2 < AbstractRoot

end
Run Code Online (Sandbox Code Playgroud)

matlab中的每个具体类都有一个名为的公共静态隐藏方法empty,它创建该对象的空数组.我想为抽象类创建一个空方法,它的功能与getDefaultScalarObject方法类似.这将允许我调用AbstractRoot.empty()和接收默认类型的空数组.

例如:

classdef (Abstract) AbstractRoot < matlab.mixin.Heterogeneous

    methods (Static, Hidden)
        function EmptyObj = empty()
            EmptyObj = ConcreteSubclass1.empty();
        end
    end

    methods (Static, Access = protected)
        function DefaultObj = getDefaultScalarElement()
            DefaultObj = ConcreteSubclass1();
        end
    end

end
Run Code Online (Sandbox Code Playgroud)

不幸的是,这不起作用(无限递归).我遇到的主要问题是我不知道如何覆盖empty,并且仍然能够从子类调用它的内置版本,因为empty它不是从任何地方继承的

问题

  1. 是否可以调用内置版本的空?如果是这样,怎么样?
  2. 是否有一种在抽象基类中重写空的方法,以便子类仍然可以调用内置版本的空.同样,我可以从方法内部检查调用哪个版本的静态方法(例如'AbstractRoot.empty'或'ConcreteSubclass1.empty'),所以我可以根据具体情况处理它?

RTL*_*RTL 1

迟到总比不到好...

据我所知,它完全没有记录:(只能验证 2013a)

  • 对任何类的 1x1 数组进行索引
  • 具有任何可能大小的空双精度数组(至少 1 维为 0)
  • 将为给定类创建一个具有给定大小的空数组。

有了这个,我们可以为任何类重新创建与empty的内置版本等效的内容。

然后可以使用它来覆盖内置版本。因此,可以为子类单独定义它,这将防止调用定义的超类方法(并避免递归)。

因此,有 3 个 classdef m 文件首先是问题中的第二个 AbstractRoot 定义;然后两个子类的empty方法定义如下(Obj变量创建为所需的类)

classdef ConcreteSubclass1 < AbstractRoot 

    methods (Static, Hidden)
        function EmptyObj = empty( varargin )
            if isempty( varargin )   
                ind = double.empty;  %// as calling double.empty([]) errors
            else
                ind = double.empty( [varargin{:}] );  
            end
            Obj = ConcreteSubclass1();  %// or Obj = ConcreteSubclass2();
            EmptyObj = Obj(ind);
        end
    end

end
Run Code Online (Sandbox Code Playgroud)

我们现在可以调用所有 3 个 class.empty 方法

a = AbstractRoot.empty
b = ConcreteSubclass2.empty
c = ConcreteSubclass1.empty

a = 

  0x0 ConcreteSubclass1 array with no properties.


b = 

  0x0 ConcreteSubclass2 array with no properties.


c = 

  0x0 ConcreteSubclass1 array with no properties.
Run Code Online (Sandbox Code Playgroud)

最后,如果emptyAbstractRoot 的子类中省略了定义,则将调用抽象根的重载版本,从而生成 ConcreteSubclass1 数组

 d = ConcreteSubclass3.empty

d = 

  0x0 ConcreteSubclass1 array with no properties.
Run Code Online (Sandbox Code Playgroud)