簡體   English   中英

如何在matlab包中使用靜態工廠方法?

[英]How do I use static factory method in matlab package?

我在 +mypackage\\MyClass.m 下有以下類定義

classdef MyClass  
    properties
        num
    end
    
    methods (Static)
        function obj = with_five()
            obj = MyClass(5);
        end
    end
    
    methods
        function obj = MyClass(num)
            obj.num = num;
        end
    end
end

我使用 with_five() 作為靜態工廠方法。
以下腳本應創建兩個對象。

import mypackage.MyClass
class_test1 = MyClass(5);
class_test2 = MyClass.with_five();

class_test1 已創建。
對於 class_test2 它說:

Error using MyClass.with_five
Method 'with_five' is not defined for class 'MyClass' or is removed from MATLAB's search path.
Error in Testpackage (line 4)
class_test2 = MyClass.with_five();

當我將 MyClass.m 放在包文件夾之外並刪除“import”語句時,它可以工作。
我究竟做錯了什么?

MATLAB 中有一些帶有包和靜態方法的奇怪的東西。

首先,包內的函數必須使用包名來引用同一包內的其他函數或類(請參閱此處)。 所以靜態方法mypackage.MyClass.with_five()必須聲明如下:

    methods (Static)
        function obj = with_five()
            obj = mypackage.MyClass(5);
        end
    end

沒有這個,我看到:

>> mypackage.MyClass.with_five
Undefined function or variable 'MyClass'.

Error in mypackage.MyClass.with_five (line 8)
            obj = MyClass(5);

其次,靜態類方法(至少是包內類的方法)在類的對象被創建之前不會被加載。 所以我們需要先調用類構造函數:

>> clear classes
>> mypackage.MyClass.with_five
Undefined variable "mypackage" or class "mypackage.MyClass.with_five".
 
>> mypackage.MyClass(1);
>> mypackage.MyClass.with_five

ans = 

  MyClass with properties:

    num: 5

如果我們導入類也是如此:

>> clear classes
>> import mypackage.MyClass
>> MyClass.with_five
Undefined variable "mypackage" or class "mypackage.MyClass.with_five".
 
>> MyClass(3);
>> MyClass.with_five

ans = 

  MyClass with properties:

    num: 5

第二點在 R2017a(生成上述輸出的地方)中是正確的,但在 R2021a 中不再正確。 我不知道這是在哪個 MATLAB 版本中修復的,但在 R2021a 中,不再需要創建類的對象來使用其靜態方法。

我認為您缺少的是,當您導入靜態方法時,您必須導入類名和方法名https://au.mathworks.com/help/matlab/matlab_oop/importing-classes.html )

這有效:

classdef MyClass  
    properties
        num
    end
    
    methods (Static)
        function obj = with_five()
            obj = MyClass(5);
        end
    end
    
    methods
        function obj = MyClass(num)
            obj.num = num;
        end
    end
end

然后執行以下操作:

>> import MyClass.with_five
>> x = with_five

輸出:

x = 

  MyClass with properties:

    num: 5

話雖如此:不要在它自己的類的成員函數中創建一個對象! 正如您所建議的,更好的選擇是將工廠轉移到不同的班級。 如果你想制作一堆鏈鋸,你永遠不會試圖設計一個上面有一個按鈕來構建鏈鋸的鏈鋸。 您寧願設計一家可以生產用於砍伐樹木的鏈鋸的工廠。

“靜態工廠”並不是一件壞事。 這實際上是一種非常常見的模式,尤其是在 C# 中。 但是,工廠始終是它自己的類。 從繼承或擴展該類的另一個對象調用該方法(我不確定你甚至可以在 Matlab 中做到這一點......)如果不是致命的,肯定會令人困惑。 我也想不出你需要這樣做的任何理由。 事實上我不明白為什么with_five()應該是靜態的

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM