在MATLAB中模拟C ++模板 [英] Simulate C++ template in MATLAB

查看:95
本文介绍了在MATLAB中模拟C ++模板的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试找出创建C ++模板或Java通用对象的替代方法的最佳方法.过去,由于几种不同的原因,我曾经想这样做,但是现在我想做的事情与为多个相关类创建saveobj和loadobj函数有关.我的想法是,我希望有一组通用的例程来创建默认结构,然后再进行一些操作以使结构以我想要的方式获得.

I am trying to figure out the best way to create an alternative to the C++ template or the Java generic objects. I have wanted to do this several times in the past for several different reasons, however right now what I want to do is related to creating the saveobj and loadobj functions for several related classes. The idea is that I want to have a generic set of routines to create a default struct and then manipulate that a little bit farther to get the structs the way I want them.

我不能简单地使用外部函数,因为我需要访问对象的所有公共(不是问题)和受保护的(问题)非瞬态属性,以便创建loadobj和saveobj.

I cannot simply use an external function because I need access to all the public (not a problem) and protected (problem) non-transient properties of an object in order to create the loadobj and saveobj.

然后我考虑使用抽象接口.但是,使用抽象接口给我带来了同样的问题.相同,复制粘贴在我所有目标文件中的代码.因此,我想到了结合使用某种完全爆炸的对象和多重继承(我的大多数对象已经从接口的基本构想继承而来).我以为使用超类将允许我公开受子类保护的属性,但是它似乎无法正常工作.有什么建议吗?

Then I considered using an abstract interface. However, using an abstract interface leaves me with the same problem; identical, copy an pasted code floating around in all of my object files. So then I thought of using some sort of full blown object combined with multiple inheritance (Most of my objects are already inheriting from a basic concretion of interfaces). I thought using a superclass would allow me to expose the subclass protected properties, but it doesn't seem to work that way. Any suggestions?

这里是save obj方法的多重继承方法(到目前为止,我有史以来最接近的方法)的示例.

Here is a sample of the multiple inheritance approach (the closest thing I have so far) for the save obj approach.

Serializer.m

Serializer.m

% Serializer.m
classdef Serializer 

  methods
    function [saveObj] = saveobj( obj )

      % Get metadata about the Object
      meta = metaclass( obj );
      meta = meta.PropertyList;

      for p = meta'
        if p.Transient | p.Dependent
          continue; % Only serialize the correct fields
        end

        saveobj.(p.Name) = { obj.(p.Name) }; % Serialize
      end % for ( property )
    end % function ( saveobj )
  end % methods
end % classdef ( Serializer )

TestSerializerA.m

TestSerializerA.m

% TestSerializerA.m
classdef TestSerializerA < Serializer
  properties
    PropA = 'a';
  end % properties ( public )

  properties( Access = protected )
    HiddenA = 'ha'
  end % properties ( protected )
end % classdef ( TestSerializerA )

TestSerializerB.m

TestSerializerB.m

% TestSerializerB.m
classdef TestSerializerB < TestSerializerA & Serializer

  properties
    PropB = 'b'
  end

  properties( Access = protected )
    HiddenB = 'hb';
  end % properties ( protected )

end % classdef ( TestSerializerB )  

推荐答案

解决方案

您可以使用访问列表.您可以允许Serializer类访问您想要序列化的任何受保护/私有类成员.这允许每个类自行确定要序列化的成员.由于您允许访问Serializer,因此您不想从其继承.如果您这样做,则继承关系中的所有类都将有权访问这些成员.这是重写的Serializer类:

Solution

You can accomplish what you are looking to do by using Access lists. You can allow the Serializer class access to any protected/private class members you would like to be serialized. This allows each class to determine on its own which of its members are serialized. Since you are allowing access to Serializer, you do not want to inherit from it. If you do, all classes in the heirarchy will have access to those members. Here is the rewritten Serializer class:

classdef Serializer

    methods
        function SerializedObj = serialize(~, Obj)
            % Get metadata about the Object
            meta = metaclass(Obj);
            meta = meta.PropertyList;

            for p = meta' %'
                if p.Transient || p.Dependent
                    continue; % Only serialize the correct fields
                end
                try
                    SerializedObj.(p.Name) = { Obj.(p.Name) }; % Serialize
                catch Me
                    % the class has chosen not to allow this property to be
                    % serialized. decide how to handle it.
                    if ~strcmp(Me.identifier, 'MATLAB:class:GetProhibited')
                        Me.rethrow()
                    end
                end
            end
        end 

    end 

end

请注意,您可以决定如何处理访问限制.在上面的示例中,我什么也不做.但是您可以发出警告,引发错误等....

Note that you can decide how you want to handle the access restrictions. In the above example, I do nothing. But you could issue a warning, throw an error, etc... .

现在,创建一个抽象的Serializable类,而不是从Serializer继承,该类将启用序列化.

Now, instead of inheriting from Serializer, create an abstract Serializable class, which will enable serialization.

classdef (Abstract) Serializable

    properties (Access = private)
        Serializer_ = Serializer()
    end

    methods        
        function savedObj = saveobj(This)
            savedObj = This.Serializer_.serialize(This);
        end 

    end

end

现在,您希望启用序列化的任何类都将另外继承自Serializable.您可以指定Serializer有权访问哪些受保护/私有成员.

Now any class you wish to enable serialization on will additionally inherit from Serializable. You can specify which protected/private members the Serializer has access to.

以下类具有两个可序列化的属性,以及一个隐藏(不可序列化)的属性.

The following class has two serializable properties, and one hidden (not serializable) property.

classdef TestSerializerA < Serializable
  properties
    PropA = 'a';
  end

  properties( Access = {?TestSerializerA, ?Serializer} )
      % This property is protected and serializable
      SerializableA = 'sa'
  end 

  properties (Access = private)
      % This property is private and not serializable
      HiddenA = 'ha';
  end
end

这是MATLAB的结果:

This is the result from MATLAB:

>> Test = TestSerializerA

Test = 

  TestSerializerA with properties:

    PropA: 'a'

>> b = saveobj(Test)

b = 

            PropA: {'a'}
    SerializableA: {'sa'}

下一个示例继承自TestSerializerA,并具有另外两个可序列化的属性和一个隐藏的属性.

The next example inherits from TestSerializerA, and has an additional two serializable properties, and one hidden property.

classdef TestSerializerB < TestSerializerA & Serializable

    properties
        PropB = 'b';
    end

    properties (Access = {?TestSerializerB, ?Serializer})
        % This property is protected and serializable.
        SerializableB = 'sb';
    end

    properties (Access = protected)
        % This property is protected and not serializable.
        HiddenPropB = 'hb';
    end

end

请注意,从Serializable重新继承是不必要的,但会使代码更易于阅读.

Note here that re-inheriting from Serializable is unnecessary, but makes for easier to read code.

最后,来自MATLAB的结果:

Lastly, the result from MATLAB:

>> Test = TestSerializerB

Test = 

  TestSerializerB with properties:

    PropB: 'b'
    PropA: 'a'

>> b = saveobj(Test)

b = 

            PropB: {'b'}
    SerializableB: {'sb'}
            PropA: {'a'}
    SerializableA: {'sa'}

我希望这会有所帮助!

这篇关于在MATLAB中模拟C ++模板的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆