从 Matlab 中的超类中获取对象的 Class

Get Class of an Object From Superclass in Matlab

与许多其他 OOP 语言一样,常量属性在 Matlab 中是静态属性(属于 classes,而不是实例)。访问它们的自然方式是 ClassName.PropName,如 Matlab documentation.

但是,在这样的情况下,我找不到从超级class 执行 ClassName.PropName 的方法:

classdef (Abstract) Superclass < handle
    properties(Dependent)
        dependentProperty
    end

    properties (Abstract, Constant)
        constantProperty
    end

    methods
        function result = get.dependentProperty(obj)
            c = class(obj); % Here I have to get class of obj
            result = length(c.constantProperty); % to use here as `ClassName.PropName`
        end
    end
end



classdef Subclass < Superclass
    properties (Constant) 
        constantProperty  = [cellstr('a'); cellstr('b')];
    end
end

以便以下命令产生以下输出:(预期输出

>> subclassInstance = Subclass()

subclassInstance = 

  Subclass with properties:

     constantProperty: {2×1 cell}
    dependentProperty: 2

>> subclassInstance.dependentProperty

ans =

     2

>> 

但是,我得到的是以下内容:(实际输出)

>> subclassInstance = Subclass()

subclassInstance = 

  Subclass with properties:

    constantProperty: {2×1 cell}

>> subclassInstance.dependentProperty
Struct contents reference from a non-struct array object.

Error in Superclass/get.dependentProperty (line 13)
            result = length(c.constantProperty);

>> 

也试过:c = metaclass(obj) 给出“没有合适的方法,属性,或字段 'constantProperty' class 'meta.class'."

问题:有什么方法可以从superclass获取一个对象的class,从而能够写出像[=15=这样的语句]?


编辑:

我知道我可以像这样从对象引用中获取:

function result = get.dependentProperty(obj)
    result = length(obj.constantProperty); 
end

但这不是我想要的,因为它让 reader 认为 constantProperty 是一个实例 属性。这也没有在 Matlab 中记录,而是文档说 ClassName.PropName 这让我觉得一定有办法。

在 matlab 中 正确的 方法是通过实例,根据我之前回答的部分,您现在已将其纳入问题中。这是因为 matlab 的面向对象模型是基于 "instance" 的。

常量属性一个实例属性;它恰好在所有情况下都是相同的(即常数)。据推测,这就是为什么它被称为 "constant" 而不是 "static" 的原因:它不像在 c 中那样引用内存中的单个静态项;相反,每个实例都使用相同的常量值实例化。

通过 "class reference" 特意调用它,您一无所获(顺便说一句,不存在这样的东西;与 python 和 julia 不同,class 原型不是对象可以参考,他们自己也没有类型)。

但是,如果您坚持, 恰好是一种使用 metaclasses 来做到这一点的方法,因为常量 属性 从在构造函数中将有一个在其 metaclass profile

中命名的默认值
subclassInstance = Subclass();
m = metaclass(subclassInstance);
mp = findobj (m.PropertyList, 'Name', 'constantProperty');
mp.DefaultValue

此外,为了解决为什么 class(subclassInstance).constantProperty 不起作用,这仅仅是因为 class(subclassInstance) 的结果是一个 字符串 (其值恰好是 classname),而不是 "reference" 到 class(就像我说的,matlab 中不存在这样的东西)。

但是,如果你愿意,显然你可以在 eval 语句中使用这样的 classname string 来评估它,就好像你直接输入它一样在终端中访问常量 属性。所以这是实现您所追求的目标的另一种方式:

eval([class(subclassInstance) '.constantProperty'])

但理论上 eval 语句通常应避免,除非别无选择。


简短说明:

in Java this is possible by this.getClass()

在 java 中,这称为 reflection,它是 java 自己的 'inspecting' 对象机制。当您执行类似 myObject.getClass() 的操作时,您返回的是 仍然 而不是 "reference to a class prototype"。它是类型 Class 实例 。 IE。即使在 java,你也做不到 myObject.getClass().aStaticProperty。但是你可以使用Classclass提供的getFields方法获取Field个对象,并检查它们相对于具体对象实例;对于静态字段,此实例只是成为 null 对象。