09-07-2011 08:15 AM
Hello,
I am working on a small side project that will allow for a central shut-down or emergency stop button. Sadly I have a problem as I wanted to read in a queue reference, and this is different depending on the queue datatype...
My VIs use a reference containing a string, my example queue consists of a cluster of a string and a U32 - thus for LV the source and sink are different. How can I achieve the change behaviour of the NI VIs that change when wiring? Do I have to write a polymorph VI?
As a work around could I just pass the name of the queue and call it during runtime or would I get the same problems again?
I add pictures of the wiring (for users of older versions) and the lvlib for users of LV2010+
Thanks in advance for your time and your replies, as well as for random ideas for further improvement.
Solved! Go to Solution.
09-07-2011 08:45 AM
First question. Why don't you change the subVI to match the type of queue reference you are passing in? Why would you be trying to pass in more than one type of queue reference? It seems like a simple single purpose subVI. (Actually, I'm not sure how simple it is because it seems like a complicated interaction of two different notifiers with a queue.) If you have a subVI that is intended to do one thing like this seems it does, then you design the subVI to work for that particular situation.
A common way to have a queue be able to handle multiple kinds of data in one queue is to include a variant as one of the datatypes in the queue. Let's say you have a cluster of an enum (a typedef that defines the action you want to take) and a variant (a container that can hold any kind of data). You bundle the command with the data and have it coerce or cast into a variant. In the consumer of that queue, you read the command so you know what action to take, and based on that, you know how to convert the data in the variant bact to a datatype that you can use.
09-07-2011 08:49 AM
The approach I take when I need a queue to transmit different data types to different parts of the program is to configure the queue 'element datatype' as a cluster of Enum (or string) and Variant rather than String and Integer. I use the Enum (or string) to call a specific case. In each case the variant is converted back to whatever data type is typically expected by the case.
I can for instance trigger an Abort event and convert the abort code (integer) into variant and transmit that to the Abort Case in the consumer loop which will in turn always convert the variant to an integer. Other cases can convert the variant into whatever data types that case expects.
Please see my attached code for a working example.
Regards,
Dave.
09-07-2011 09:14 AM
Thanks for the answers, I will most probably use this VI with a Queue using a cluster from Enum and Variant, exactly as described by Ravens Fan and very similar to your example.
I want to use this VI to either shut down different VIs or call a global emergency stop. You can find my overall "design" concept in this post at the end. This would also be a possibility to end the consumer loops without injecting an error.
For the sake of reusability I wanted the VI to work with whatever queue I feed it. It is obvious that I could bash this VI to fit this quick and dirty example but I am not satisfied with that - I would rather like a more nice, reusable solution. The NI queue VIs also recognize what is wired to them and they change accordingly; can I also achieve this behaviour?
09-07-2011 09:30 AM
@Questionmarker wrote:
For the sake of reusability I wanted the VI to work with whatever queue I feed it. It is obvious that I could bash this VI to fit this quick and dirty example but I am not satisfied with that - I would rather like a more nice, reusable solution. The NI queue VIs also recognize what is wired to them and they change accordingly; can I also achieve this behavior?
Probably only through polymorphism like you suggested. The reason is that the queue reference has the datatype of the data it carries inherently in it. It wouldn't know how to adapt to any given queue because it would ultimately break the underlying subVI at the dequeue element function where it needs to decode the queue datatype and figure out how to distribute the data.
09-07-2011 09:34 AM
Ok, then its once again bash to fit, paint to cover (;
Thanks for your time!
09-07-2011 09:47 AM
maybe having all queues formated to the same datatype (a wide spread method is to have a cluster with an enum to describe message type, a variant to cary the data and a timestamp) could do the job?
We have two ears and one mouth so that we can listen twice as much as we speak.
Epictetus
09-07-2011 09:48 AM
@TiTou wrote:
maybe having all queues formated to the same datatype (a wide spread method is to have a cluster with an enum to describe message type, a variant to cary the data and a timestamp) could do the job?
thats exactly what Ravens and Dave suggested in the first place
09-07-2011 10:25 AM
Sure, I saw that... what I meant is that to me it's elegant enough to not be refered to as "paint to cover"
We have two ears and one mouth so that we can listen twice as much as we speak.
Epictetus
10-25-2011 10:27 AM
Why is it traditionally taught to use an Enum with a variant as opposed to an Enum with a flattened string? Seems like both implmentations would work identically.