Matlab: 静态类成员

3
我将尝试在Matlab中实现一个列表,它可以作为实例计数器。我希望这个列表是静态的。
目前,在Matlab中没有静态关键字,但是他们提供了一个几乎可以完成任务的模式:
声明一个继承自handle的类List:
classdef List < handle

   properties (Access = private)
      cellRepresentingAList = {};
   end

   ..... %Implement any functions

end

那么您可以按照以下方式使用它:

classdef MyClassUsingAList < handle

    properties (Constant, Access = private)
       myListOfStuff = List();
    end

    .....

 end

我们使用一个句柄对象作为常量导致每个 MyClassUsingAList 实例都将使用相同的对象句柄,也就是说我有一个静态列表。

一切都完美运行,直到出现异常。或者我通过“停止调试”按钮进行调试,或者保存。此时,列表被清除为空。

这不是我可以投入生产的东西。

Matlab 提供了持久性变量,用于在函数中起到静态变量的作用,但无法在类中使用(除非您在使用该列表的每个方法中使用关键字“persistent”)。

是否有可靠的方法来实现这个目标?

谢谢


精度:每次我保存包含静态列表的类的文件时,似乎都会发生这种情况。这比我最初预期的要好一些。然而,如果有更好的解决方案,将不胜感激。 - Milan
1个回答

1
使用persistent关键字,如此处所述。 (你采用了第二种方法,我认为你需要的是这种方法)。 您可以使用mlock命令锁定函数,以防止意外清除它们,例如您描述的情况。
请注意,您无需在每个方法中定义一个持久变量,如您所说!(实际上,那可能会产生与您想要相反的效果,因为持久变量对每个函数都是唯一的,而不是整个类)。 只需创建一个具有静态访问权限的单个方法,其唯一目的是保留该持久变量的副本,并在任何其他非静态方法中引用该方法以获取或设置它。
例如。
classdef myclass

  properties
    Prop1;
    Prop2;
  end

  methods(Static, Access='public')
    function Out = StaticVar1(In)   % first static "variable"
      mlock
      persistent var;
      if isempty(var); var = 0; end          % initial value
      if nargin < 1; Out = var; return; end  % get value
      var = In;                              % set value
    end
    function Out = StaticVar2(In)   % second static "variable"
      mlock
      persistent var;
      if isempty(var); var = 0; end          % initial value
      if nargin < 1; Out = var; return; end  % get value
      var = In;                              % set value
    end
  end

  methods
    function Out = addStaticVars(o)
      Out = o.StaticVar1 + o.StaticVar2;
    end
  end
end

使用示例:

>> a = myclass();
>> myclass.StaticVar1       % access the first static "variable"
ans =
     0
>> myclass.StaticVar2       % access the second static "variable"
ans =
     0
>> myclass.StaticVar1(10)   % set static "variable" to 10
>> myclass.StaticVar2(20)   % set static "variable" to 20
>> a.addStaticVars()        
ans =
    30
>> b = myclass();
>> b.addStaticVars()
ans =
    30

>> clear all;               % inneffective as functions are "locked"
>> myclass.StaticVar1
ans =
    10

>> munlock myclass.StaticVar1
>> clear all;        % this will now succeed in clearing the static "variable"
>> myclass.StaticVar1
ans =
     0

嗨,谢谢你的回答。然而,如果持久变量对于函数是静态的(这比我最初预期的要好),那么我如何确保协同数据?我需要静态数据在整个类中都是静态的。我可以在一个函数中声明变量,并确保该函数在整个类中被调用。但是,由于没有办法保护数据,这似乎是一个错误和维护问题的巢穴。我认为最后,第二种方法“静态数据对象”更适合我的需求。 - Milan
抱歉,请问您所说的“内聚数据”和“保护数据”的意思是什么? - Tasos Papastylianou
一个静态对象不够安全,因为它会在“清除”事件的情况下被清除——也就是说,如果对句柄的引用消失了,那么你的数据也会消失;而一个锁定的持久函数保证会一直存在,直到会话结束或手动重置。如果你不喜欢这种范式,那就由你决定,我只是在回答问题;这就是你防止“静态”变量被清除的方法。 :) - Tasos Papastylianou
我的观点是该对象在类中的多个方法中被使用。因此,我担心项目中的任何新开发人员会以非静态方式在某些方法中使用它。不过,我会查看这个实现。目前,SharedObject设计最终运行良好,即使该对象可以被清除(到目前为止,我遇到的唯一情况是保存文件,这使得调试更加困难,但在运行时并不会出现问题)。 - Milan

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接