0. 概述
加速 Simulink 仿真是個老生常談的問題,尤其是系統(tǒng)比較復(fù)雜或規(guī)模較大的時候,大家都不希望時間耗費(fèi)在等待上,也正因此,其實(shí)已經(jīng)有很多答案散落在各種地方;考慮到老朽本人玩 Simulink 不多甚至可以說很少,所以這篇以搬磚為主,整理編撰的時候會盡量注明出處,也盡量對各種方法分門別類讓大家可以一目了然。當(dāng)然,本著嚴(yán)謹(jǐn)?shù)募夹g(shù)態(tài)度,老朽還會盡量做一些驗(yàn)證,確保拿出來的東西都是能用得上的。(由于本文涉及的外部鏈接較多,我將一一列在文末,方便大家獲取。)
首先,有必要澄清一下,這里的 Simulink 其實(shí)不只是 Simulink,而仿真耗時也不只是模型求解慢。
從模型本身來講,它可能由以下一種或多種情形組合(甚至是全部):
1Simulink(數(shù)學(xué))模型
2Simscape(物理)模型
3Stateflow(狀態(tài)機(jī))模型
4SimEvents(事件)模型
5MATLAB(腳本)模型
6其它第三方模型(以源代碼或動態(tài)庫等方式集成)
其中物理模型可能是 Driveline,Multibody,Electrical,F(xiàn)luids 以及 Powertain 和 Vehicle Dynamics 中的一種或多種組合。
MATLAB 腳本可能只是一個簡單的計算,一個傳遞函數(shù)或狀態(tài)方程,也可能是機(jī)器學(xué)習(xí)或深度學(xué)習(xí)的推斷,亦或是強(qiáng)化學(xué)習(xí)智能體。
本文重點(diǎn)討論 Simulink 與 Simscape,也會提及其它的方面,對于復(fù)雜的情況,建議還是找 MathWorks 官方提供技術(shù)支持(版本在更新,技術(shù)在發(fā)展,過去沒有改善的不表示現(xiàn)在不能改善)。
從仿真耗時來講,它可能會涉及以下時間成本:
1模型編譯/鏈接
2循環(huán)初始化
3循環(huán)迭代
4輸出/日志(在循環(huán)迭代過程中)
5仿真終止(在循環(huán)迭代結(jié)束時)
列舉完這些方方面面,大概就能有一個概念——仿真加速要針對具體的情況具體分析。
盡管老朽有理由相信來讀這篇文章的大都是有經(jīng)驗(yàn)的 Simulink 用戶,但穩(wěn)妥起見,我們還是從基礎(chǔ)開始——其實(shí),經(jīng)驗(yàn)也常常教育我們,涉及到性能的問題,確實(shí)有不少情況都是基礎(chǔ)沒打好。
1. 基礎(chǔ):性能優(yōu)化相關(guān)知識
基礎(chǔ)部分的知識點(diǎn)來自 MATLAB產(chǎn) 品文檔,著急直接上手優(yōu)化仿真性能的觀眾,可以直接去看這個:優(yōu)化性能 - MathWorks 官網(wǎng)文檔[1]。但俗話講得好,心急吃不到熱豆腐,耐心點(diǎn)往下看,我相信會有更多收獲。
在看這部分之前,無論你是 Simulink 老用戶還是新用戶,我都要墻裂建議你看一下幫助文檔里仿真原理的相關(guān)章節(jié),MathWorks已經(jīng)提供部分中文化的pdf版本了,其中 Simulink 的工作原理一章已經(jīng)有中文版了,給懶人們直接上鏈接吧:Simulink 用戶指南 (僅已翻譯的部分 R2021b)[2],翻到第99頁,從這里開始,看完第三章的29頁即可。
如果你的模型里還有 Simscape 或 Stateflow 或 SimEvent 等等,我還要建議你更進(jìn)一步,把它們的 User's Guide 里有關(guān)原理的章節(jié)都看一下:
● Simulink 用戶指南 (僅已翻譯的部分 R2021b)[3],第3章 Simulink 的工作原理,共29頁
● Simscape User's Guide:[4]第7章 Model Simulation,共69頁
● Stateflow 用戶指南 (僅已翻譯的部分 R2021b):[5]第3章 Stateflow語義,共24頁
● SimEvents User's Guide:[6]這個有點(diǎn)分散,沒用到就先放放吧,講真老朽也沒看過
關(guān)于基礎(chǔ)知識,大家看 MATLAB 幫助文檔學(xué)習(xí)的話,老朽建議一定要看 PDF 版本的 User's Guide 也就是用戶指南,相比去官網(wǎng)上看或者在幫助界面上看,PDF 版本的用戶指南都要好看的多。
言歸正傳,回到加速 Simulink 仿真的問題,在 Simulink 用戶指南(R2021b 中文版)的動態(tài)仿真部分,分別在第31章和第35章,給出了“如何提高仿真性能”以及“加速模型”兩章較為全面的闡述,大家把這些看完看懂的話,老朽相信大家對于自己的仿真為什么會慢,以及怎樣改進(jìn)模型使仿真能快一些,就已經(jīng)有譜了。
鑒于以上提到的方方面面,顯然不合適把重點(diǎn)全抄下來,而老朽又想大家即使只看完本文也能做些工作,因此就挑重點(diǎn)半抄半寫吧。
基礎(chǔ)方面,我打算羅列6個要點(diǎn),考慮到內(nèi)容真的有點(diǎn)多,沒法具體展開,要細(xì)節(jié)的話還是去看文檔吧。
1.1 動態(tài)系統(tǒng)仿真的3個階段
編譯階段
鏈接階段
仿真環(huán)階段
所謂3個階段,就是從你按下綠色的運(yùn)行按鈕,到仿真跑出結(jié)果,Simulink 要干的三件事情。看名字就很好理解它們都是什么,為了讓偷懶的也能看看,就把文檔內(nèi)容拷貝到本節(jié)后面吧。
大多數(shù)有關(guān)仿真提速的內(nèi)容都是針對第三階段的,即仿真的循環(huán)初始化和循環(huán)迭代兩個部分,但作為開篇,我想重點(diǎn)先說說模型編譯。經(jīng)常有人在大型建模上耗費(fèi)了大把時間等待模型編譯,加快超大模型的編譯,有幾點(diǎn)知識和經(jīng)驗(yàn)需要了解:
01模型的編譯跟 C/C++ 文件的編譯類似,其實(shí)是可以支持多 CPU 核(多進(jìn)程)同時編譯的,前提是你得遵循“基于組件的建模規(guī)范”,即在你的模型中合理使用子系統(tǒng)、鏈接子系統(tǒng)、模型引用和子系統(tǒng)引用。具體我們在1.3模型架構(gòu)里講。
02Simulink 支持增量式加載/編譯,在滿足前一條的情況下,可以通過共享 Simulink Cache 文件來降低編譯耗時,具體參見:共享 Simulink 緩存文件以加快仿真速度[7]。
03如果不是采用普通模式,而是用加速或快速加速模式,則 Simulink 不僅會經(jīng)歷模型編譯,還會調(diào)用 Simulink Coder 的代碼生成功能(雖然不需要為此購買和安裝 Simulink Coder),生成 C/C++ 代碼并調(diào)用 C/C++ 編譯器將其編譯為可執(zhí)行文件,這種情況的模型編譯耗時更長,對架構(gòu)做的差的超大模型而言,甚至?xí)ㄋ馈_@一點(diǎn)在1.5仿真模式中還會再提到。
04通過 Simulink Cache文件(.slxc)來減少模型編譯時間這一功能,到 R2019b 才健全(支持代碼生成和 Stateflow),以此為例,談性能真的不能離開 MATLAB 最新版(后面關(guān)于求解器、多處理器和 GPU 都會提到)。
· 模型編譯
當(dāng)系統(tǒng)的模型處于打開狀態(tài),并且您對模型進(jìn)行仿真時,將進(jìn)行仿真的第一個階段。在 Simulink 編輯器中,點(diǎn)擊運(yùn)行。運(yùn)行仿真會導(dǎo)致 Simulink 引擎調(diào)用模型編譯器。模型編譯器會將模型轉(zhuǎn)換為可執(zhí)行形式,這個過程稱為編譯。具體說就是,編譯器會:
? 計算模型的模塊參數(shù)表達(dá)式,以確定它們的值。
? 確定模型沒有顯式指定的信號屬性,例如,名稱、數(shù)據(jù)類型、數(shù)值類型和維度,并檢查每個模塊是否都接受連接到其輸入的信號。
? 將源信號的屬性傳播到它所驅(qū)動的模塊的輸入,以便計算模塊中先前未指定的屬性。
? 執(zhí)行模塊簡化優(yōu)化。
? 通過將虛擬子系統(tǒng)替換為它們所包含的模塊,將模型層次結(jié)構(gòu)扁平化。
? 通過基于任務(wù)的排序確定模塊執(zhí)行順序。
? 確定模型中您未顯式指定其采樣時間的所有模塊的采樣時間。
這些事件本質(zhì)上與您更新模塊圖時發(fā)生的情況相同。差別在于 Simulink 軟件作為模型仿真的一部分啟動模型編譯,編譯會直接進(jìn)入鏈接階段,如“鏈接階段”中所述。而顯式模型更新是針對模型的獨(dú)立操作。
編譯模型或模型層次結(jié)構(gòu)時,可以通過點(diǎn)擊進(jìn)度條旁邊的取消按鈕來取消模型編譯。
· 鏈接階段
在此階段,Simulink 引擎為工作區(qū)域(信號、狀態(tài)和運(yùn)行時參數(shù))分配執(zhí)行模塊圖所需的內(nèi)存。它還為用于存儲每個模塊的運(yùn)行時信息的數(shù)據(jù)結(jié)構(gòu)體分配和初始化內(nèi)存。對于內(nèi)置模塊,模塊的主要運(yùn)行時數(shù)據(jù)結(jié)構(gòu)體稱為 SimBlock。它存儲指向模塊的輸入和輸出緩沖區(qū)以及狀態(tài)和工作向量的指針。
方法執(zhí)行列表
在鏈接階段,Simulink 引擎還會創(chuàng)建方法執(zhí)行列表。這些列表列出了調(diào)用模型的模塊方法以計算其輸出的最有效順序。在模型編譯階段生成的模塊執(zhí)行順序列表用于構(gòu)造方法執(zhí)行列表。
模塊優(yōu)先級
您可以向模塊分配更新優(yōu)先級。較高優(yōu)先級模塊的輸出方法在較低優(yōu)先級模塊的輸出方法之前執(zhí)行。僅當(dāng)這些優(yōu)先級與其模塊執(zhí)行順序一致時,才會遵循它們。
· 仿真環(huán)階段
鏈接階段完成后,仿真會進(jìn)入仿真環(huán)階段。在此階段,Simulink 引擎使用該模型提供的信息,從仿真開始到完成的時間段內(nèi)以固定間隔連續(xù)計算系統(tǒng)的狀態(tài)和輸出。計算狀態(tài)和輸出的連續(xù)時間點(diǎn)稱為時間步。時間步之間的時間長度稱為步長。步長取決于用來計算系統(tǒng)連續(xù)狀態(tài)、系統(tǒng)基礎(chǔ)采樣時間以及系統(tǒng)的連續(xù)狀態(tài)是否具有不連續(xù)性。
仿真環(huán)階段有兩個子階段:循環(huán)初始化階段和循環(huán)迭代階段。初始化階段在循環(huán)開始時出現(xiàn)一次。迭代階段在從仿真開始到仿真停止的時間段內(nèi)的每個時間步重復(fù)一次。在仿真開始時,模型將指定要仿真的系統(tǒng)的初始狀態(tài)和輸出。在每個時間步中,將計算系統(tǒng)的輸入、狀態(tài)和輸出的新值,并且將更新該模型以反映計算的值。仿真結(jié)束時,該模型將反映系統(tǒng)的輸入、狀態(tài)和輸出的最終值。Simulink 軟件會提供數(shù)據(jù)顯示和日志記錄模塊。您可以通過在模型中包含這些模塊來顯示和/或記錄中間結(jié)果。
仿真環(huán)階段的速度提升,除了建模本身的影響,在選擇求解器和發(fā)揮硬件性能(多核、GPU、超算)方面是相輔相成的,這個也跟 MATLAB 的版本更新有著密切的聯(lián)系,除了求解器會在1.4中提到,后面在第2、3、4里都是跟這兩相關(guān)的。
1.2 建模方法
假設(shè)我們要仿真一個閉環(huán)的自動駕駛系統(tǒng)模型。
在這里,用什么方法分別對傳感(Sensors)、感知(Perception)、規(guī)劃(Planning)、控制(Control)以及被控對象(Plant model, Passenger Vehicle)和環(huán)境/場景(Environment/Scenario)建模,以及如何連接各子系統(tǒng),對整體上的仿真速度顯然有很大的影響。
從場景建模來說,現(xiàn)在 MATLAB 支持 Unreal Engine,以及 RoadRunner 工具鏈,這一塊已經(jīng)可以單獨(dú)跑了(單機(jī)多進(jìn)程,或者干脆雙機(jī)分開跑),你可以看作是一種聯(lián)合仿真,在考慮仿真性能優(yōu)化的時候基本可以忽略它們,堆硬件(GPU)是最直接靠譜的出路——對于多體動力學(xué)的仿真,你如果從 UG 或 Solidworks 等軟件導(dǎo)入 3D 模型,在 Simulink 的仿真過程中展示 3D 動態(tài)效果,配置一塊獨(dú)立顯卡也是非常有必要的。
被控對象建模則有不同的方法。過去我們往往在模型的保真度和計算性能上做取舍,或者結(jié)合更抽象高效的數(shù)學(xué)模型與查表來避免對機(jī)電液物理模型的求解并同時達(dá)到合適的仿真精度要求,但這對于要考慮整車眾多性能(諸如電池充電狀態(tài)、速度曲線、續(xù)航能力、熱管理水平等)的系統(tǒng)級仿真而言,模型大了跑起來就很慢,因此借用深度學(xué)習(xí)和實(shí)驗(yàn)數(shù)據(jù)構(gòu)建降階的替代模型就成了一種可能的優(yōu)雅的選擇。
關(guān)于用深度學(xué)習(xí)來實(shí)現(xiàn)模型降階,這里給一篇文章供大家參考:
至于數(shù)學(xué)模型的構(gòu)建,更多還是要看我們建模的經(jīng)驗(yàn)和水平,Simulink 用戶指南第15章,建模最佳實(shí)踐中給出的對串聯(lián) RLC 電路建模求解的例子,就很好的闡釋了什么是“最佳形式的數(shù)學(xué)模型”,雖然過于簡單了點(diǎn),但很有參考意義。
關(guān)于采用什么樣的方法建模,歸納起來有以下幾點(diǎn)供參考:
· 對于數(shù)學(xué)模型,嘗試找到它的最佳形式
· 對于多域物理系統(tǒng),建議優(yōu)先考慮 Simscape。在必要的情況下(Simscape 不滿足需求)或者對數(shù)學(xué)方法構(gòu)建被控對象模型很熟悉的情況下可以用數(shù)學(xué)方式建模,但自己造輪子要求總歸是比較高的。
使用 Simscape 將跨越機(jī)械、電氣、液壓和其他物理領(lǐng)域的系統(tǒng)建模為物理網(wǎng)絡(luò)。Simscape 構(gòu)造描述模型行為的 DAE。軟件將這些方程與模型的其余部分集成,然后直接解算 DAE。Simulink 同時對不同物理領(lǐng)域中的組件變量求解,從而避免代數(shù)環(huán)問題。
· 對于大型物理網(wǎng)絡(luò),如果所有子系統(tǒng)都是建的詳細(xì)模型,則很難讓仿真跑得快,建議充分利用變體,對于分析目標(biāo)影響不大的子系統(tǒng),使用諸如查表的方法表達(dá)外特性或者抽象的物理模型替代(如用理想開關(guān)替代 IGBT,甚至用等效電路替代開關(guān)從而進(jìn)一步提高仿真效率),更進(jìn)一步,還可以用數(shù)據(jù)驅(qū)動+深度學(xué)習(xí)的方法來建模。
· 以上基本都是宏觀方向上的,細(xì)節(jié)在哪里?看這個:Simulink 用戶指南 (僅已翻譯的部分 R2021b)[8],第31章 動態(tài)系統(tǒng)仿真 -> 提高仿真性能和準(zhǔn)確性 -> 提高性能的建模方法,內(nèi)容較多,涵蓋“加速初始化階段”、“降低模型交互性”、“降低模型的復(fù)雜度”、“選擇和配置求解器”、“保存仿真狀態(tài)”各個方面,后面的章節(jié)只有求解器會重復(fù),建議細(xì)看一下(4頁文檔)。
1.3 模型架構(gòu)
一個好的模型,跟一份好的代碼,有一個最重要的共同點(diǎn)就是架構(gòu)都要好。相較于寫代碼不管架構(gòu)只堆功能(有點(diǎn)難),在 Simulink 里畫模型不看架構(gòu)顯然更容易過得下去,而且很多情況甚至過得還不錯,但跟代碼一樣,一旦整體規(guī)模上去了,就成了災(zāi)難——好在 Simulink 模型重構(gòu)還是要比代碼來得簡單些。
一個好的模型架構(gòu),不僅意味著易于維護(hù)、易于擴(kuò)展,也意味著易于測試(確保單元測試覆蓋率),更是有效提高仿真性能的基礎(chǔ)。有關(guān)模型架構(gòu),可以參考 Simulink 用戶指南 (僅已翻譯的部分 R2021b)[9],第22章“大型建模”中的“基于組件的建模規(guī)范”和“比較模型組件的功能”,這里抄錄性能相關(guān)的部分供參考。事實(shí)上,有關(guān)建模規(guī)范,尤其是在滿足高可靠高完整性的要求方面,有更完備的內(nèi)容,但這不在本文探討范圍內(nèi),有興趣的可以去MathWorks 官網(wǎng)查詢或者聯(lián)系 MathWorks 銷售以便跟他們的工程師直接交流。
組件建模要求考慮事項(xiàng)——“性能要求”
? 增量模型加載
? 編譯工件重用
? 降低大型模型的內(nèi)存使用量
? 消除人為代數(shù)環(huán)
對于不太想了解這么多細(xì)節(jié)的人來說,我們簡單歸納幾點(diǎn)在下面,作為大家建模時在仿真性能方面的參考:
· 模型引用!模型引用!模型引用!重要的事情說4遍,多用模型引用(Model Reference)。模型引用對于仿真性能的四個方面均有重要影響
· 子系統(tǒng)引用是 R2019b 版本才出來的,子系統(tǒng)引用的輸入輸出端口支持 Simscape 物理連接
· 模型引用雖然出來很早,但其端口至今仍不支持 Simscape 物理連接(R2022a),因此如果想用模型引用對物理網(wǎng)絡(luò)進(jìn)行分割封裝,需要將端口等效轉(zhuǎn)換為 Simulink 信號(自行分解物理網(wǎng)絡(luò)有難度,可以向 MathWorks 咨詢)
· 子系統(tǒng)引用雖然不支持編譯工件重用,但它支持增量方式加載;換句話說,使用引用子系統(tǒng)不能帶來模型編譯上的效率提升,但對維護(hù)超大物理網(wǎng)絡(luò)還是有用的
三種組件化技術(shù)
在模型架構(gòu)的最后部分,要提一下利用多 CPU 核提速單一模型仿真的問題,換句話說,就是多線程協(xié)同仿真的問題,這個問題重點(diǎn)會在第二章的進(jìn)階部分講,這里提一下,是因?yàn)樗P鸵妹芮邢嚓P(guān)。
1.4 求解器的選擇
求解器的選擇是一個很經(jīng)典又富有挑戰(zhàn)的話題,說很經(jīng)典,是因?yàn)榍蠼馄?a target="_blank">算法本身大都?xì)q月悠久了,譬如龍格-庫塔(Runge-Kutta)迭代求解非線性常微分方程的方法于 1900 年左右被提出,歐拉方法則更早;而挑戰(zhàn)呢,似乎是 Simulink 不像一些特定領(lǐng)域的專業(yè)軟件有默認(rèn)的甚至固定的求解器(它們往往只需求解某一類問題),在 Simulink 上,你還得自己選求解器(當(dāng)然,從 R2015b 開始你可以選 auto solver 讓它自動給你選),可選項(xiàng)還挺多,常常不知道該選啥才能跑的快(還得結(jié)合模型的特性、精度要求與采樣時間的要求等)。
另一個方面,因?yàn)橛衅渌鼘I(yè)軟件在仿真速度方面的比較,也常常有人(包括我自己)會質(zhì)疑是不是 MATLAB 的求解器不行,而忽略了在建模方法上的差異,這就很容易引錯方向。
考慮到求解器的這些個情況,我就不拷貝黏貼了細(xì)節(jié)了,去下面兩個鏈接自己看吧:
? 比較求解器[10](參見 Simulink 用戶指南 第3章 Simulink 簡介 -> Simulink 工作原理 -> 比較求解器)
? 選擇求解器[11](參見 Simulink 用戶指南 第3章 Simulink 簡介 -> Simulink 工作原理 -> 比較求解器)
求解器的選擇
當(dāng)然,關(guān)于求解器,老朽也有幾點(diǎn)額外說明:
· 從 R2015b 開始,你可以使用 auto solver(自動求解器),讓 Simulink 自動選擇一個求解器與步長進(jìn)行仿真。自動求解器根據(jù)模型的動態(tài)特性,推薦一個固定步長或可變步長求解器,自動確定最大步長值。R2016a 開始自動求解器能計算模型剛度,對于剛性模型會選擇 ode15s 求解。
· 從 R2019a 開始,支持 odeN solver,能快速求解有過零檢測的系統(tǒng)。“Simulink 提供了一個變步長求解器,允許您使用變步長(無誤差控制)積分來求解動態(tài)模型,同時保持過零點(diǎn)的精度”
odeN (Nonadaptive)
? 從 R2018a 在 Simscape 中引入 Partitioning Solver[12] 后(限制較多不太好用),MathWorks Advisory Board(MAB)就在講 Local solver,然后到 R2022a 才真正發(fā)布對 Local solver 的支持。通過 Local solver,可以為模型的不同部分(模型引用!)選擇不同的求解器,從而來提高仿真速度。這個新特性允許我們?yōu)檩^慢的模型選擇計算成本更低的求解器。請注意:模型引用模塊上 Local Solver 選項(xiàng)默認(rèn)是關(guān)著的,你得自己打開它。
Local Solver Basics[13]
Use local solver when referencing model[14]
? 從 R2022a 開始,使用固定步長的求解器也可以很好地應(yīng)對過零檢測了。這對時間步長偏大的情況很有用。給張圖大家自己看看吧~~
定步長求解器的過零檢測
? 看到這里,是不是要說:你看,還是求解器的水平問題嘛~~呃,好吧,求解器確實(shí)重要,但更重要的是建模的方法,不然你就得自己造輪子實(shí)踐了。
? 無論是 odeN(R2019a)、ode1be(R2020a),還是對 local solver(R2022a)的支持,都未必能解決你的問題,現(xiàn)實(shí)的約束常常讓人頭疼,但是很抱歉,關(guān)于求解器老朽也只能到這里了,而且具體選哪個,參數(shù)怎么設(shè),還是得 case by case 來看,實(shí)在搞不定,還是找 MathWorks 直接問吧~~
1.5 仿真模式
前面幾個部分寫得真的是太費(fèi)力了,這部分還是拷貝粘貼吧。以下內(nèi)容出自 Simulink 用戶指南第35章加速模型。
加速和快速加速模式使用 Simulink Coder 產(chǎn)品的部分內(nèi)容創(chuàng)建可執(zhí)行文件。加速和快速加速模式會替換 Simulink 仿真中常用的解釋代碼,從而縮短模型的運(yùn)行時間。雖然加速模式會使用一些 Simulink Coder 代碼生成技術(shù),但您不需要安裝 Simulink Coder 軟件即可為您的模型加速。
· 普通模式
在普通模式下,MATLAB 技術(shù)計算環(huán)境是 Simulink 軟件的基礎(chǔ)環(huán)境。Simulink 控制仿真過程中使用的求解器和模型方法。模型方法包括模型輸出的計算等內(nèi)容。普通模式在一個進(jìn)程中運(yùn)行。
普通模式
· 加速模式
默認(rèn)情況下,加速模式采用即時 (JIT) 加速方式在內(nèi)存中生成執(zhí)行引擎,而不是生成 C 代碼或 MEX 文件。您還可以將模型回退到經(jīng)典加速模式,在這種模式下,Simulink 將生成代碼并將代碼鏈接到 C-MEX SFunction。在加速模式下,模型方法與 Simulink 軟件相分離,它們將作為之后進(jìn)行仿真時使用的加速目標(biāo)代碼的一部分。Simulink 會在重用加速目標(biāo)代碼之前檢查代碼是否為最新版本。有關(guān)詳細(xì)信息,請參閱“Code Regeneration in Accelerated Models”。在加速模式下,有兩種操作模式。即時加速模式 在此默認(rèn)模式下,Simulink 在內(nèi)存中只為頂級模型(而不為引用模型)生成執(zhí)行引擎。因此,仿真過程中不需要使用 C 編譯器。由于加速目標(biāo)代碼在內(nèi)存中,因此只要模型處于打開狀態(tài),就可以重用這些代碼。Simulink 還會序列化加速目標(biāo)代碼,因此當(dāng)模型處于打開狀態(tài)時,不需要重新構(gòu)建模型。
即時加速模式
經(jīng)典加速模式
要使用生成 C 代碼的經(jīng)典加速模式對您的模型進(jìn)行仿真,請運(yùn)行以下命令:
set_param(0, 'GlobalUseClassicAccelMode', 'on');
在此模式下,Simulink 會生成代碼并將代碼鏈接到與 Simulink 軟件進(jìn)行通信的共享庫。MATLAB 與Simulink 的目標(biāo)代碼執(zhí)行過程相同。
經(jīng)典加速模式
· 快速加速模式
快速加速模式從您的模型中創(chuàng)建一個快速加速獨(dú)立可執(zhí)行文件。這個可執(zhí)行文件包含求解器和模型方法,但位于 MATLAB 和 Simulink 的外部。它使用外部模式(請參閱“External Mode Communication”(Simulink Coder))與 Simulink 通信。MATLAB 和 Simulink 在一個進(jìn)程中運(yùn)行,如果有第二個處理內(nèi)核可用,獨(dú)立可執(zhí)行文件將在該內(nèi)核中運(yùn)行。
快速加速模式
關(guān)于如何選擇仿真模式,大家看文檔吧,中文的:選擇仿真模式[15]。提煉幾句話放下面供參考:
· 普通模式在調(diào)整模型和顯示結(jié)果方面提供了最大的靈活性,但運(yùn)行速度最慢。
· 加速模式在性能以及與模型的交互方面介于普通和快速加速模式之間。加速模式不支持大多數(shù)運(yùn)行時診斷。
· 快速加速模式的運(yùn)行速度最快,但此模式不支持調(diào)試器或探查器,而且僅適用于模型中的所有模塊可生成 C/C++ 代碼或編譯為 MEX 文件的模型。
另外,快速加速模式支持仿真目標(biāo)語言為C++也是最近版本才有的功能(似乎文檔里甚至都沒公開),這個主要解決了深度學(xué)習(xí)不支持C語言代碼生成的問題~~舊版本的話,折中的辦法是先生成 C++,再用 C 封裝,編譯成 dll 或 mex 后再集成進(jìn)來,道路有點(diǎn)曲折,好在現(xiàn)在不需要這么干了。
1.6 性能問題分析
其實(shí)這節(jié)應(yīng)該放到最前面,但考慮到如果不了解基礎(chǔ)光靠工具分析也很難解決根本問題,所以放到這還是更合適些。
Simulink 里其實(shí)提供了兩個分析性能的手段,但性能分析要結(jié)合前面的建模與求解器一起來做,給張圖:
加速仿真需要關(guān)注每個階段
具體的分析收到要落實(shí)到兩個工具上,分別是 Performance Advisor 和 Solver Profiler,具體這里就不描述了,大家看文檔更靠譜(這兩部分在 Simulink User's Guide 英文版pdf里才有,因?yàn)榻刂?R2022a 還沒中文化):
· Improve Simulation Performance Using Performance Advisor[16](英文 Simulink User's Guide 第34章)
· Examine Model Dynamics Using Solver Profiler[17](英文 Simulink User's Guide 第35章)
這里,我們來舉一個實(shí)戰(zhàn)小栗子,嘗試用 Performance Advisor 找到原因并修改模型使它跑的快起來(如果很熟悉 Simulink,就不用廢那么大功夫了)。
源頭是我這篇文章里提到的問題:老朽筆記:MATLAB 強(qiáng)化學(xué)習(xí)入門(1+)[18],把強(qiáng)化學(xué)習(xí)智能體替換成只有推理模型后,仿真變慢了 N 倍,當(dāng)時沒找到原因。
那么,我們打開模型,然后切換到“調(diào)試”菜單,點(diǎn)擊“性能顧問”,打開性能顧問(performance advisor)的界面。
點(diǎn)擊“運(yùn)行所選檢查”,經(jīng)過漫長等待,得到報告:
所有問題項(xiàng)看下來,其它都改了,沒有效果,剩下這項(xiàng):檢查驅(qū)動導(dǎo)數(shù)端口的離散信號!我們再打開兩個模型,將信號的全部屬性召喚出來(點(diǎn)擊左邊工具條上的雙箭頭圖標(biāo),選“全部”即可),很顯然,區(qū)別就在 Calculate Observation 模塊的輸出原本是采樣時間為 0.025 的離散信號,變成了連續(xù)信號(FiM固定子步),這導(dǎo)致后面的 MATLAB function(evaluatePolicy)以及機(jī)器人物理模型的計算量急劇增加。
我們要做的就是修改 Calculate Observation 模塊中最右邊一個模塊 RateTransition 的采樣時間,強(qiáng)制它為 0.025,如此就能得到跟原模型一樣的仿真速度(和精度)了。
至于 Simulink 默認(rèn)行為為何會變,還是等老朽問完專家再來探討吧。
審核編輯:湯梓紅
-
仿真
+關(guān)注
關(guān)注
50文章
4048瀏覽量
133431 -
Simulink
+關(guān)注
關(guān)注
22文章
522瀏覽量
62312
原文標(biāo)題:如何加速 Simulink 仿真?(上)
文章出處:【微信號:MATLAB,微信公眾號:MATLAB】歡迎添加關(guān)注!文章轉(zhuǎn)載請注明出處。
發(fā)布評論請先 登錄
相關(guān)推薦
評論