13 Replies Latest reply on Aug 24, 2016 11:32 PM by brucewilson

    if-then test does not appear to be working within loop

    macmesser

      Screen Shot 2016-08-22 at 3.47.55 PM.png

      I'm having trouble with the above script, which is supposed to break out discrete values from a field "Features" that contains variable length lists of values. The script works record by record and gets the count of the values, placing it in a global variable "$$lengthValList". It then loops through the list and retrieves all the values, one per iteration, by using a GetValue(Features; $$valIndex) expression, where $$valindex is starts at 1 and is incremented by one in each iteration until the loop is exited immediately after $$valIndex in incremented (SSlengthValList + 1). The looping through values is intended to find specific values with an if-then test (within the loop) and if present write these values in to specific fields. This is the part that is not working and it seems the test is simply ignored. The loop does cycle through the values in the input field "Features", is properly exited, and the steps following the loop are executed. I'm not all that familiar with scripting FMPro Advanced v. 12 so hopefully I'm just trying to do something the wrong way. Any insights appreciated and thanks in advance for help.

        • 1. Re: if-then test does not appear to be working within loop
          coherentkris

          First thing is if you don't need to use any of the variable you set outside the script then declare them as local $ not global $$.

           

          Second thing is that This will operate on the first record in the found set because their is no go to record next script step.

           

          You should really step through this with the script debugger on and the data viewer open and see exactly what it does.

           

          Thirdly my first set var would be to set $list to features:Features and then iterate through the variable contents instead of the field contents.

           

          Lastly without knowing exactly what is expected in features::Features I cant really diagnose the if statement but i suspect something is wrong with the left (...) part.

          1 of 1 people found this helpful
          • 2. Re: if-then test does not appear to be working within loop
            philmodjunk

            Also, make sure that you are on the correct layout when the script runs. If you are on a layout based on the "features" table occurrence, this script won't work.

            1 of 1 people found this helpful
            • 3. Re: if-then test does not appear to be working within loop
              macmesser

              Thanks for reply. I originally used local variables but changed them to global just to see if that might help. I figured it couldn't hurt. I know the script will only work on one record now. I will add a loop ending with a Go to next record  I get it to work on a single record. Right now I'm trying to get it to loop through the values on the list. The contents of Features field on one record is:

               

              SKU: T[26222]

              Brand: T[Aurora World, Inc.]

              Medium: T[Soft and cuddley plush bean filled]

              Height or Width: O[7]

               

              Carriage return delimited values (in this record's case 4) which Filemaker recognizes as a list of values and correctly determines the count. The values are accessible by an index ranging from 1 to the count of values. Initially the Features field values were delimited by ";" but I substituted carriage returns so the values could be accessed by Filemaker.

               

              I will do as you suggest and get everything into Filemaker variables. That should certainly make it easier to debug and I would think it will also just work better.

               

              The if-then statement is just looking for values like "Brand: T[Aurora World, Inc.]". Note that the nine chars starting from left are: "Brand: T ["

               

              So the expression:

               

              Left($$listItem; 9) = "Brand: T["

               

              will be true when the value is a Brand type as shown in red above. ( Where $$listItem is a variable containing a value from Features field. BTW, do you think the ":" and/or the "[" need to be escaped?

               

              I will try to start using the debugger as you suggest. It's a little counterintuitive. Once I start it will I need to manually step it through?

               

              Thanks again for the comments.

              • 4. Re: if-then test does not appear to be working within loop
                macmesser

                Thanks for reply Phil. I am working from a layout based on the "Features" table. Why will this not work? There are three tables in the database: Brands, Features, Test. They are all unrelated and I am using the layouts Filemaker just made in table view. Features is the second table I created. I'd have thought with no relationships the tables would be equal . Thanks again for your comment.

                • 5. Re: if-then test does not appear to be working within loop
                  philmodjunk

                  My mistake due to a typo. The script will not work if it is NOT based on that table occurrence.

                   

                  Sent from my iPhone

                  • 6. Re: if-then test does not appear to be working within loop
                    DrewTenenholz

                    Macmesser --

                     

                    If I understand what you are trying to do, it is to extract the 'Brand' from a return-delimited list of values in the field features::Features.  You don't know if there is a 'Brand', or where it might be in the list of values.

                     

                    I've developed a preference for a recursive way of doing this sort of thing:

                     

                    Set Variable ($remainingValues ; features::Features )

                     

                    Loop

                         Set Variable ($firstValue = GetValue ( $remainingValues ; 1 )

                         Set Variable ($remainingValues ; MiddleValues ( $remainingValues ; 2 ; ValueCount ( $remainingValues ) -1 ) )

                     

                         Exit Loop If ( IsEmpty ( $firstValue ) )  // you've run out of things to test

                     

                         Set Variable ( $result ; Case ( Left ( $firstValue ; 9 ) = "Brand T:[" ; $firstValue )  // you've found what you were looking for and captured it.  If not, $result will be empty, Case () allows you to do this

                     

                         Exit Loop If ( Not ( IsEmpty ( $result ) ) )  // you've have what you need, so quit NOW

                     

                    End Loop

                     

                    Set Field ( features::Brands ; Case ( IsEmpty ( $result ) ; "" ; $result ) // so you get nothing if there is no brand in the list, something labelled "Brand T:[..." if there is something found.  It would be trivial to trim off the "Brand T:[" with a substitute or a replace on $result.

                     

                    The last two lines of your script are puzzling.  Why do you want to set the features::Artists field to anything, and why do you set it first to one thing, and then immediately to something else?

                     

                    In the little recursion I've shown (and I hope I typed it right, this has not been copy/pasted, just hand-typed so excuse any finger slips), you could set up any number of $result -like variables to capture all the terms you are interested in with one pass (skipping the second exit loop [if you've found the one thing you are looking for]), then apply them to fields after capturing all of them. I hope that would prove to be efficient.

                     

                    -- Drew

                    1 of 1 people found this helpful
                    • 7. Re: if-then test does not appear to be working within loop
                      coherentkris

                      The script debugger and data viewer are vital tools in your tool box.

                      They are the screwdriver and crescent wrench when writing scripts.

                      Their are controls to step thru, step over and run to breakpoint or end..

                      Get familiar with it and you'll wonder how you ever wrote a script without it.

                      1 of 1 people found this helpful
                      • 8. Re: if-then test does not appear to be working within loop
                        macmesser

                        Thanks for reply, Drew. Your understanding of what I'm trying to do is correct. Not all products have all features and I need a way to flatten that Features field so I can make bulk edits as I clean things up. I will want to do this potentially with any "type" of value on the list. Your solution is just what I need and in fact you even anticipated what my further steps might be. It looks very solid and efficient, not to mention elegant, so I am eager to transplant it to my database. The fact that it is understandable means that I'll be able to adapt it with a minimum of frustration. This saves me hours of trial and error, thrashing around with unfamiliar expressions. Thank you!

                         

                        BTW, the last two lines of my first draft script were just so I could see a bit of what was working and what was not. I really need to get a little less down and dirty. As coherentkris pointed out, I need to start using the debugger, which I certainly will now that I have been getting back to db stuff.

                        • 9. Re: if-then test does not appear to be working within loop
                          macmesser

                          I intend to do just that. Under time pressure I didn't want to start with something I hadn't used before but that was a counterproductive mindset.

                          • 10. Re: if-then test does not appear to be working within loop
                            macmesser

                            After setting up a script  as shown, my script is still not performing boolean conditionals, whether they be in an IF block with a SET statement or in a CASE expression (as Drew wrote previously) that contains a value assigned by a SET statement. (I tried both ways.) The rest of the script works, it's just the part that assigns a value to $result that fails, no matter how the assignment is made. I also noted that when I step through the script in the debugger that the set statement in the IF block is seemingly skipped over. No value appears in the data viewer for $result when the script is stepped through. Is there some problem with performing a boolean test within a loop? This is the same thing that I was getting using my original less efficient script.  Any insights appreciated.

                            • 11. Re: if-then test does not appear to be working within loop
                              philipHPG

                              I wonder whether perhaps there are extra characters in the string that are not easily visible, either at the start of the line or where the space is. If you change your search to look just for "Brand", does it find anything? Otherwise you might want to step through with the Data Viewer and see if there are extra characters in the string that cause the comparison to fail.

                              1 of 1 people found this helpful
                              • 12. Re: if-then test does not appear to be working within loop
                                macmesser

                                Thanks philipHPG, and BINGO! My CSV data source had leading spaces which were not apparent until I looked at the file in TextWrangler, a capable and free text editor designed with programming in mind. Once seen the offending spaces were removed by a simple addition of Trim() to a few expressions.

                                • 13. Re: if-then test does not appear to be working within loop
                                  brucewilson

                                  How big can the list get? I try to avoid iteration.

                                   

                                  You could use something like this

                                   

                                  Set Field [ features::Brands ; Value: let ( [ features = ¶ & features::Features & ¶ ; start = Position ( features ; "¶Brand: T" ; 1 ; 1 ) ; end = Position ( features ; ¶ ; start ; 1 ) ] ; if ( start > 0 ; middle ( features ; start + 1 ; end - start - 2 ) ) ]

                                  1 of 1 people found this helpful