Locating Value in a List

Clovertech Forums Read Only Archives Cloverleaf Cloverleaf Locating Value in a List

  • Creator
    Topic
  • #53869
    Jon Melin
    Participant

      Hello!

      I am just looking to see if anyone has any thoughts on a better way of doing this. I have a system that sends me a bunch of selected fields in a non-ordered list like this below:

      2(1).1(0).0(0).OBR(0).#14(0).[0]  :  >Signs and Symptoms: ignore; Pacemaker: No; Aneurysm Clips: No; Implanted Defibrillator: No; Insulin Pump: No; Bullets, Shrapnel, BB’s: No; Any Hx of Metal Fragments in the eye?  (welding, hobbies, job related?): No; < I need certain answers from these selected fields, sometimes all of them, sometimes just one, but they are not in the same order all the time. Also sometimes the labels and questions are completely different depending on the test coming in. Right now I am using string first to find a word (such as Aneurysm Clips: ) and then grabbing the answer (yes/no/etc) by getting what is in between the ending “;” and the end of the label word “:”. The problem with this is I have to do it for every word I want, and if two “answers” contain the word Symptoms: (as an example) – I could get the wrong value because first would obviously only get the first one even if one said Symptoms: and the other said Additional Symptoms: Not sure there is a perfect way. My setup: 1) Find the word: set location [string first “Insulin Pump:” $xlateInVals] set xlateOutVals $location 2) Grab what’s after the label word I just found: set something [crange $xlateInVals [string first “:” $xlateInVals $location] [string first “;” $xlateInVals $location]]        set something [crange $something 2 end-1]        set something [regsub -all ” ” $something “”]  — Only because it doesn’t work if I don’t remove the spaces (see question 2) Like I said, this works fine but it seems inefficient. Any ideas? #2 Question: When I copy something with a space (exp: Clean Catch) into a variable, I can echo that variable and it shows just fine, but when I try to place that variable into another field somewhere it only ever does the first word (Clean  only). Any ideas on this? Thank you in advance, Jon

    Viewing 14 reply threads
    • Author
      Replies
      • #79311
        Jim Kosloskey
        Participant

          Jon,

          For your last question is the field somewhere you are referring to as the target a target field in an Xlate?

          If so I suspect your problem is you are not treating xlateOutVals as a list (possibly not xlateInVals either). So the space in the variable is treated as a liste lement terminator. The Xlate treats xlateOutVlas (and the other xlateInxxxx, xlateOutxxxx data items) as lists and if you don’t then the Xlate will not behave the way you want.

          email: jim.kosloskey@jim-kosloskey.com 30+ years Cloverleaf, 60 years IT – old fart.

        • #79312
          Jim Kosloskey
          Participant

            Jon,

            As for your first question.

            The field is not a list in itself but it appears you could split on ; to create a list of the individual categories.

            Then I think you can use lsearch with a -glob option to get the specific terms you are looking for. If you also use the -all option you will get a list of all of the indices of the original list which matched your glob search.

            If you want to be really sure you only search the left hand side of the : then using split I believe there is a way to get a compund list by specifying multiple ( :; ) split characters. Then using a combination of list commands (including the lsearch described above) you can only search the terms to the left of the :.

            You can also populate a list of the terms you want to search on and use list commands to drive your search. However if that changes frequently you might find maintaing the list in Tcl a bit of a chore.

            Another option is to use a Lookup Table to contain your terms. You can make the left side of the table entry something like term1, term2, etc with the right side the actual term. Then using a loop routine and Cloverleaf provided Tcl Table lookup command build the key (the left side of the Table) adding the counter to the end and incrementing it until you receive the default (means you have exhausted the Table and thus your terms). So now you can update your termis to search for via the Table Configurator. Then do a purge caches and your Tcl proc will get the updfated verion of table of terms.

            If you want to discuss this further, contact me via email off line.

            email: jim.kosloskey@jim-kosloskey.com 30+ years Cloverleaf, 60 years IT – old fart.

          • #79313
            Charlie Bursell
            Participant

              To expand on what Jim said:

              Assume the string is in variable fld

              # Make sure array is clear

              array unset fldArray

              foreach el [split $fld ;] {

                 lassign [split $el :]  tag data

                 set fldArray($tag) $data

              }

              Now you can simply access the array by tag name for what you want

              Also, heed Jim’s warning about treating xlateIn and out vals as a list

              For example assume the field contains:  “Jack and Jill went up the hill”

              If you echo $xlateInVals you would see {Jack and Jill went up the hill} because of the spaces.  Note the braces

              If you assigned to xlateOutVals and you only had one address you would see just “Jack”

            • #79314
              Jon Melin
              Participant

                Thank you both for the responses.

                I will try out the array, that seems like a great idea.

                I tried to treat it as a string but it doesn’t appear to be working, I’ve tried putting the “list” in quotes, how do I force it to output to $xlateOutVals as the whole string?

                Thank you,

                Jon

              • #79315
                James Cobane
                Participant

                  set xlateOutVals

                • #79316
                  Jon Melin
                  Participant

                    Thanks James, that is more obvious than I thought, I thought I was trying to not treat it as a list but I see what you did.

                    Charlie,

                    How do you go about calling this array inside the XLATE?

                    I created it, do I save it to a destination variable or just call it from within the next line in the Xlate such as:

                    array get fldArray “Insulin Pump: “

                    When I tried this it didn’t work, I used the array @fldArray as the Source side.

                    Thank you,

                    Jon

                  • #79317
                    Chris Williams
                    Participant

                      This behaved differently on our system . With [split $fld ;] it returned each word as a separate list element. But parsed as desired when adding quotes around the semicolon [split $fld “;”]. I didn’t expect it to make a difference, but it did. Perhaps it saw the semicolon as the end of the split statement and reverted to the default of whitespace. Charlie, any insight?

                      Jon, depending on your needs you may also want to [string trim] the variables before setting them in the array if you find the whitespace messing with you.

                      Cheers.

                    • #79318
                      Charlie Bursell
                      Participant

                        yeah, forgot you may have to quote the ; since it is a special character in Tcl

                        As for the array it is nothing special.  Treat as you would any other Tcl variable

                      • #79319
                        Jon Melin
                        Participant

                          Hello. I have this array setup but I am still having issues. I can’t seem to find anything online for it and haven’t used Arrays within an Xlate ever.

                          Am I building the array incorrectly? When I tried to echo array statistics it said it wasn’t an array and showed all the labels I was searching for.

                          Here (screenshot) is what I have setup. I know I am doing something incorrectly that will be very simple and evident once you point it out. Any suggestions? I still can’t get it to work.

                          Thank you in advance

                        • #79320
                          Chris Williams
                          Participant

                            Jon,

                            First, if you want to see the contents of the array use parray which will display the data on its own. You don’t have to echo its return value:

                            Code:

                            parray labelArray


                            Don’t forget that xlateInVals and xlateOutVals ARE LISTS. If you want to read the contents of xlateInVals you have to index the value you want:

                            Code:

                            [lindex $xlateInVals 0]


                            When writing to xlateOutVals, you are building a list. Make sure you make your output data into a list element first. Depending on the logic you’re using you can do

                            Code:

                            set xlateOutVals [list $ex]
                            or
                            lappend xlateOutVals “$ex”


                            The offset values, by definition, are zero-based and for xlateInVals and xlateOutVals refer to the rows of items in the Source and Destination boxes. If you want to refer to the second row of Source values you would use [lindex $xlateInVals 1]. If you are writing Tcl code, that is the only way you can access those Source/Destination values.

                          • #79321
                            Jon Melin
                            Participant

                              Chris,

                              Thank you for this information. Printing it should be fine but once I populate the array do I place it in a varibale using xlateOutVals (build a list)?

                              Essentially from what I was understand I could make the array and then use the array get command to do a string match on the label (i.e. Insulin Pimp:   Interval:  etc) use that to get the taged element that lies between the “;” and the “:” and save it to a variable I can use –

                              So I’d assume I am building the array correctly but I can’t get the elements back out, and I’d like to do it by the label because the labels are never in the same order so index won’t help.

                              Do I put the “list” in the destination side in the XLate and then put that variable into the source on the next line and search for array elements by index, or can I use the label?

                              I may just have to go back to my original method.

                              Thank you,

                              Jon

                            • #79322
                              Chris Williams
                              Participant

                                It’s difficult to say. It would be helpful to know a bit more about what you are trying to accomplish. e.g., are you trying to create a separate OBX for each of these array items? Do you know ahead of time which elements in the array you want to use if they appear? Do you just want to assign the array values to specific @variables?

                              • #79323
                                Chris Williams
                                Participant

                                  It might be helpful to note that your xlate is a single Tcl instance. If you write a bit of code in the first line of an xlate that sets a Tcl variable, that variable exists until the end of that xlate, not just for the life of the single xlate action. If you want to manipulate that variable throughout your xlate, it’s not necessary to pass it from one line to another via @variables.

                                  I’m sure that some people will disagree, but sometimes it’s just easier, cleaner and faster to manipulate data in a Tcl snipped rather than trying to do it all with xlate actions.

                                  As with all of this, there are many ways to accomplish your task. It’s your choice of which is best for you and your circumstances.

                                • #79324
                                  Jon Melin
                                  Participant

                                    Chris,

                                    The ancillary system is dictating which labels they will want, so I still don’t know. This OBR14 field you see coming in with the format [ Field1: something; Field2: something; ] is a series of questions that the person putting an order in answers. (where the something word is what I want and Field is the label for the question) They can come in any order and vary every time. Depending on the test, for instance a general lab, or a micro lab, I need to look for different words inside that OBR14 and extract them. It depends on the word, where I will place it for the outbound system. Some run through a table, some go to other OBR locations, some I create an OBX with.

                                    Right now I know I will always want the text (so between the colon and semi colon) for Interval/Occurrences:   Pattern:  and Site: —  so if I was looking for a field/label (example above) Field1, I’d want to get “something” as the value and put it somewhere that is dictacted by the destination system. For Interval/Occurrences: id want what is after that, usually i’d want Weekly or something similar in an example like this:

                                    Interval/Occurrences: Weekly;  — I’d want the word weekly, but I’d have to search through that OBR14 to make sure I am grabbing weekly from the field/label that says Interval/Occurrences:

                                    Hope this helps. Please let me know.

                                  • #79325
                                    Chris Williams
                                    Participant

                                      Sorry for being so chatty today. To get back to your question about getting the info out of the array. You don’t need to use those array commands. Assuming your array is named labelArray and the array element is “Interval/Occurrences”, just treat it like any other variable except that it has a subscript.

                                      Code:

                                      set xlateOutVals [list $labelArray(Interval/Occurrences)]

                                      Just make sure the bit in parens matches exactly what was loaded into the array. You can use parray as a diagnostic tool to verify the spelling and any punctuation that may be there.

                                  Viewing 14 reply threads
                                  • The forum ‘Cloverleaf’ is closed to new topics and replies.