From 04:00 PM CDT – 08:00 PM CDT (09:00 PM UTC – 01:00 AM UTC) Tuesday, April 16, ni.com will undergo system upgrades that may result in temporary service interruption.

We appreciate your patience as we improve our online experience.

LabVIEW

cancel
Showing results for 
Search instead for 
Did you mean: 

Efficiently Update Object In Private Data Array

Hello,

 

I am working working with some more-than-basic objects/classes that I have create and would like to know the best (most efficient and least complicated) way to perform updates on these objects.

 

My scenario is as follows.  I have a Test class which contains an array of Test Trial objects in its private data.  Each test trial then has an array containing Test Result objects.  In my VI I pass a Test object into a state machine and use shift registers to move it from state to state.  Some of the states will need to create new trials, edit the data of these trials, add results to the trials, etc...

 

What I would like to know is how best to go about this in LabVIEW.  I would like to avoid what I think is that bad way of doing it where I have a member function in Test to get the array of trials (Read Test Trials), I have a member in Test Trial to get the array of results (Read Test Results), I add a new Test Result to the array, use another member of Test Trial to replace the array (Write Test Results), replace the old Test Trial with this new one, then use a method in Test to replace the array (Write Test Trials).  This (to me) would seem like an excessive amount of copies and would defeat some of the ideas behind OOP.

 

Any help is appreciated!

0 Kudos
Message 1 of 3
(2,118 Views)

A key component of LVOOP is encapsulation. All private data of a class can only be accessed by that class. You're basically describing creating Accessor methods, which seem like a pain at first but really aren't bad.

 

Once you've added your private data to the cluster, right click the class in the Project Explorer and select "Create vi for data member access" and it'll auto-create the accessor VI's for you. You can even tell them to create them for access via Property Node, which can be a much cleaner way to get to your data members than using a big list of accessor VI's.

 

In short, the way you're doing it is the right way, but I'd expand your thinking a bit. If each Test Result is written to a specific Test Trial, then why should the Test class be messing with it? Keep it all contained inside each class's member VI's. It will make your code more compartmentalized and scalable. It's also the same basic way it's handled in text based languages- "Test.TestTrials[n].TestResults = Test.TestTrials[n].NewTestResults" is basically a chain of accessors getting and setting data members of classes. LabVIEW is a bit different in that all data is private data, so you can't get at the data directly outside of a given class.

 

Also, as long as your wires aren't branching a ton, you won't be slinging around too many copies of your data.

0 Kudos
Message 2 of 3
(2,098 Views)

Based on the types of operations you described, I would suspect you could avoid most data copies by using the in-place element structure. You can keep the data private and build out all of the functions users will need to use which, under the hood, appropriately operate in place.

 

From just speculating on the requirements, you could do something like using "Array Index / Replace" to operate on a specific Test object in your Test Trial array and call an "Append Result" method of the test trial class which takes in a report object. That method could then use another in place element structure with the "Unbundle/Bundle Elements" node to get the array of test objects, append an additional object, and then output the new array.

Matt J | National Instruments | CLA
0 Kudos
Message 3 of 3
(2,096 Views)