Programozás kategória bejegyzései

Szimulációk automatizált futtatása

Gyakori eset, hogy egy tudományos kérdés vizsgálatára számos szimulációt kell futtatni különböző paraméterekkel. A szimulációk egyenkénti futtatása nem a legkényelmesebb, hiszen egy-egy szimuláció órákig is eltarthat, és figyelni kell, mikor indíthatjuk a következőt. Jobb megoldás az automatizált végrehajtás, ekkor a szimulációk paraméterezését nem feltétlenül triviális úgy végrehajtani, hogy közben karbantartható maradjon a kód. Éppen ezért fejlesztettem ki egy olyan környezetet szimulációk automatizált futtatására, mely a korábban ismertetett paraméterezésen alapul.

Az egymás után futtatandó szimulációkat egyszerűen, egy táblázatban lehet paraméterezni, ahol az egymás utáni oszlopok tartalmazzák az egymás utáni paramétereket. A szimulációt végrehajtó VI-t dinamikusan lehet betölteni. A VI-nak megadott be és kimenetekkel (is) kell rendelkeznie ahhoz, hogy a rendszerbe integrálható legyen, a szimulációt végrehajtó kódba viszont csak néhány subVI-t kell beilleszteni. Ezzel a megoldással könnyű olyan szimulációkat írni, melyek futtatását a keretprogrammal kényelmesen végre lehet hajtani.

A környezet a következő fő funkciókkal rendelkezik:

  • Szimulációk egyszerű konfigurálhatósága
  • Munkakönyvtár meghatározása
  • Szimulációk dinamikus betöltése (a VI front panelje is követhető)
  • Hátralévő iterációk és idő előrejelzése
  • Félbehagyott szimulációk folytatása

A környezet továbbfejlesztését is tervezem többek között a következő funkciókkal:

  • Egy futtatás során különböző szimulációs VI-ok betöltése
  • Konfigurációs fájlok betöltése az egyes iterációkhoz
  • Szimulációk futtatása több gépen, párhuhamosan

A következő képeken bemutatok néhány képernyőképet és a feladatok végrehajtását VI-t.

Feladatok végrehajtása

Feladatok végrehajtása

A szimulációt végrehajtó VI front panelje futtatás közben

A szimulációt végrehajtó VI front panelje futtatás közben

A keretprogram diagramja

A keretprogram diagramja

A program még fejlesztés alatt áll, de kérésre bárkinek elküldöm a forrásokat.

Szimulációk paraméterezése LabVIEW-ban, karbantartható módon

LabVIEW szimulációk késztésekor gyakori probléma, hogy az egyes programokat, illetve subVI-kat folyamatosan bővítjük új funkciókkal, így nehéz egy olyan szimulációs környezetet létrehozni az adott problémára, mely jól átlátható és jól karbantartható.

Amennyiben nem használunk subVI-okat, akkor minden egyes új funkció hozzáadásával programunk egyre inkább hasonlítani fog egy spagetti VI-ra. Ezen a problémán a subVI-ok bevezetése sem fog önmagában segíteni, ugyanis egyre több paraméter kell az egyes subVI-okba bekötni. A paraméterek számának növekedését jól lehet kezelni clusterekkel. Amennyiben várható, hogy egy-egy ilyen clustert egynél több helyen használunk, azonnal célszerű belőle típusdefiníciót készíteni. Így a kódot később is jól karban tudjuk majd tartani, az egyes típusdefiníciókat ugyanis később át tudjuk szerkeszteni, a változást pedig a projekt összes VI-a köveni fogja.

A típusdefiníciók használata általában egy jól követhető és karbantartható kódot eredményez. Azonban, főleg szimulációk kötegelt futtatásánál, rengeteg paramétert kell jól kézben tarthatóan kezelni, erre pedig a sok-sok, beálltásokat tartalmazó cluster nem feltétlenül a legjobb megoldás. Számos próbálkozás után arra jutottam, hogy a legtöbb feladatot jól meg lehet oldani, hogy ha a paramétereket egy 2D táblázatban tárolom el. A táblázat első oszlopa tartalmazza a paraméterek nevét. A második oszloptól kezdve pedig az egyes iterációkban felhasználandó paraméterértékek vannak. Ha egy paraméter értéke nem változik, akkor annak értékét elég a második oszlopban feltűntetni. A következő ábrán egy példa látható a paraméterekre. A LoopCount határozza meg az iterációk számát. Az éppen változtatott paraméter az R-Wire, a többi paraméter állandó a szimuláció során.

Minta konfigurációs táblázatra

Minta konfigurációs táblázatra

A következő ábrákon a szimulációs program blokkdiagramja látható. Minden egyes iterációban egy-egy oszlop van kiválasztva a konfigurációs táblázatból, ez van átadva a szimulációt végző VI-nak. A konfigurációs beálltások minden egyes subVI-hoz eljutnak. Amennyiben egy új funkcióval bővül a szimuláció, elegendő csak a táblázatot módosítani, valamint az éppen érintett subVI-t.

Szimulációs program mely oszloponként olvassa ki a konfigurációs paramétereket

Szimulációs program mely oszloponként olvassa ki a konfigurációs paramétereket

Szimulációt végrehajtó subVI - 1 szint

Szimulációt végrehajtó subVI - 1. szint

Szimulációt végrehajtó subVI 2. szint

Szimulációt végrehajtó subVI 2. szint

Szimulációt végrehajtó subVI 3. szint

Szimulációt végrehajtó subVI 3. szint

A konfigurációs fájlok kezelésére egy saját függvénykönyvtárat késztettem, kérés esetén ezt szívesen rendelkezésre bocsájtom (jelenleg még szerkesztés alatt van). A konfigurációs adatok mentésére és betöltésére két lehetőség is van: maga a fő VI is felkészthető az adatok betöltésére és mentésére (főleg, ha egyéb ok miatt eleve szükség van eseményvezérelt programozásra), de egy külső VI-n keresztül is elérhetjük a konfigurációs táblázatot.

Konfigurációs táblázat szerkeztése

Segédprogram a konfigurációs táblázat szerkeztésére

Rekurzív függvényhívások LabVIEW-ban

A 2009-es LabVIEW verziótól kezdődően már egyszerűen megvalósítható a függvények (subVI-ok) rekurzív hívása. Ha külön beállítások nélkül helyezzük el a VI-t saját magában, akkor hibát kapunk:

Recursive-Bad

A hibát az okozza, hogy LabVIEW-ban alapbeállítások mellett egy VI csak egy példányban futhat. Viszont ezt a viselkedést megváltoztathatjuk a VI Properties Execution pontjában:

 

SharedCloneReentrant

A Shared clone reentrant execution opciót választva a VI már több példányban is futhat, minden egyes meghíváskor a LabVIEW klónokat készít az adott VI-ról. Ezzel a beállítással a rekurzív függvényhívás már nem fog hibát adni, és helyesen is működik:

Recursive-Good.png

 

További olvasnivaló: National Instruments: Creating Recursive VIs

DAQmx - mintavételezéses mérések

Hardware-timed mérések esetén a mintavételezés vezérlését nem a számítógép, hanem maga a mérőhardver végzi el. Az aktuális hardver képességei határozzák meg, hogy az egyszerre hány mérési feladat (Task) végrehajtására képes, mekkora memória áll rendelkezésre az adatok ideiglenes tárolására, illetve, hogy milyen adatátviteli sebességgel rendelkezik. A legtöbb mérőeszköz mindössze egyetlen SW vagy HW timed feladat végrehajtására alkalmas. STC3 vezérlőt tartalmazó eszközök esetén (pl cDAQ) már három feladatot is használhatunk párhuzamosan, különböző időzítések mellett, azonban egy-egy modulhoz csak egy-egy feladat rendelhető.

Mintavételezéses méréseknek két fő típusát különböztetjük meg: véges hosszúságú mérés, és folytonos mérések. Előbbiek esetén a megadott mennyiségű adat mérését követően befejezzük a mintavételezést, esetleg a mérést később megismételjük (pl. egy ciklusban). Egy egyszerű mintaprogram a következő ábrán látható:

DAQmx HW-Timed A In

A csatorna kiválasztását követően megadjuk a mintavételi sebességet, valamint azt is, hogy hány pontot szeretnénk mérni egy-egy mérés során. A ciklusban mindig újraindítjuk a mérést, majd pedig beolvassuk a mintavételezett adatokat. Több csatorna mérése esetén az NChan NSamp opciót kell kiválasszuk. Folytonos mérések esetén a DAQmx Timing.vi sample mode bemenetére a Continuous Samples opciót kell bekössük, ezt követően a cikluson kívül (egyszer) indítjuk a mérést, a ciklusban pedig beolvassuk a szükséges adatmennyiséget:

DAQmx - Continuous A In

A mintavételi sebesség megadásakor a driver felülbírálhatja kérésünket, és a hardver képességeihez igazodó mintavételi sebességet fog beállítani. Amennyiben kíváncsiak vagyunk a végeredményre, a DAQmx Timing Property Node.vi segítségével kérdezhetjük le:

 DAQmx  -Actual Sample Clock

DAQmx - Analóg bemenet mérése

A National Instruments által gyártott USB műszerek nagy része a DAQmx driver segítségével programozhatók. A LabVIEW programozásról valamint a műszerek kezelésének alapjairól a hamarosan megjelenő „Mérés és adatgyűjtés laboratóriumi jegyzet” című jegyzetben írok részletesebben. A most elkezdett post-sorozatban néhány, ott nem szereplő módszert és valamint hasznos javaslatokat mutatok be.

Műszerek egyszerű kezelésére a DAQ assistant nevű eszközt is használhatjuk, mely segítségével, egyszerűen, varázslószerűen tudjuk konfigurálni a mérési vagy vezérlési feladatot. Összetettebb mérési feladatok esetén viszont a DAQ assistant használata már nem kézenfekvő, célszerű magunknak megírni az adatgyűjtésre használható kódot.

A driver használata során a következő alapfogalmak ismeretére van szükségünk:

  • Physical channel: az eszközön lévő bemenet vagy kimenet
  • Virtual channel: a fizikai csatorna reprezentációja
  • Task: egy mérési feladat, mely több virtuális csatornát tartalmaz
  • On demand/ Software timed: a mintavételezést a PC szoftver frissítési rátája dönti el. Nem determinisztikus, alacsony sebességnél használható
  • Hardware timed: maga a hardver végzi a mintavételezés vezérlését, determinisztikus

A következő egyszerű programban egy csatorna mérését mutatom be.

DAQmx Software Timed Analog Input 1 Ch

A program elején konfiguráljuk a kiválasztott csatornát. Az input terminal configuration bemenet esetén a következő fő választási lehetőségeink vannak:

  • RSE (referenced single ended): a bemenő feszültséget a műszer földjéhez képest mérjük
  • NRSE (non referenced single ended): a bemenő feszültséget a műszer az AI-sense bemenethez képest méri
  • Differential: két (általában szomszédos) bemenet közötti feszültségkülönbséget méri
  • Default: az adott csatorna alapértelmezett beállítását használja. Ez általában differenciális beállítást takar, kivéve a magasabb sorszámú csatornák esetén amennyiben azok valamely bemenet negatív párja lennének differenciális mérés esetén.

A DAQmx Start Task.vi indítja el magát a mérést, ezt követően a DAQmx Read.vi segítségével olvashatjuk ki az adatokat. A vi alatt lévő Polymorphic VI Selector segítségével választhatjuk ki az adatok típusát, egyetlen csatorna és egyetlen mért minta esetén választhatunk DBL (egyetlen skalár) valamint a Waveform között. A Waveform a minta mellett tartalmazni fogja a csatorna időzítési értékeit is (pl. mérés ideje).

A mérés egy ciklusban történik, ennek frissítési gyakorisága 100 ms. Az adatok egy Waveform Chart-on kerülnek megjelenítésre. A ciklus a Stop gomb megnyomásakor, vagy hiba esetén leáll. A program végén az erőforrások felszabadítása zajlik.

Szükség esetén egyszerre több csatornát is mérhetünk. Ekkor a physical channels mező Browse opcióját használhatjuk egyszerre több, azonos tulajdonságokkal rendelkező bemenet kiválasztására. A DAQmx Read.vi esetén ki kell válasszuk az NChan1Samp opciót.

DAQmx Software Timed Analog Input n Ch

Amennyiben különböző beállításokkal rendelkező csatornákat szeretnénk hozzárendelni egy-egy mérési feladathoz, akkor több DAQmx Start Task.vi-t kell meghívnunk a következő ábrának megfelelően:

 DAQmx multiple physical channels

Megjegyzés: csak azonos típusú csatornákat (pl. analóg bemenet) tudunk egy feladathoz hozzárendelni.