Jack Pilowsky
Jack Pilowsky

Reputation: 2303

What's the right way to get the number of variable variables

Let's say I have a form with an undetermined number of values with names such as follows:

PARAM1VCHRNAME
PARAM2VCHRNAME
PARAM3VCHRNAME
...

And I want to loop through these using quoted naming as described in this article: http://www.bennadel.com/blog/152-dynamic-coldfusion-variables-via-quoted-naming.htm

But in order to do so I need to find how many of these items exist in order to set up my loop.

I have ran across this situation in the past and the only way I could think to do it was to write some javascript to into a hidden field into the form with how many items there were. But this was a messy solution because it would screw things up if the user clicked the back button. I'm sure there has to be a way to do this on the server side.

Thank you

@kevin

Ok, I wrote a thing to loop though the form field names and filter them. Not the prettiest code I have ever written. But it works. Thanks for your help.

<cfset totalParams = 0>
<cfloop index="i" list="#Form.FieldNames#" delimiters=",">
     <cfif LEFT(i,5) eq 'PARAM' AND 
           RIGHT(i,8) eq 'VCHRNAME' AND 
           LSParseNumber(Replace(Replace(i, 'PARAM',''),'VCHRNAME','')) gt totalParams>
           <cfset totalParams = LSParseNumber(Replace(Replace(i, 'PARAM',''),'VCHRNAME',''))>
     </cfif>
</cfloop>

Upvotes: 0

Views: 79

Answers (1)

Henry
Henry

Reputation: 32915

If the pattern is PARAM#i#VCHRNAME and the sequence always starts with 1 and it's continuous, you can try looping continuously until you cannot find the field name anymore from the FORM scope:

function findLastVchrname()
{
  var i=1;
  while (structKeyExists(FORM, 'PARAM#i#VCHRNAME'))
    i++;

  return i;
}

If the series is not continuous, then you need to loop through the form.fieldnames and count how many of them passes regex "^PARAM(\d)+VCHRNAME$" with reFind()

Or if you want to be fancy, try listFilter() on form.fieldNames, use a filter function with determine if it matches the pattern, then do a listLen() on the result.

If you use CF11 and also want to be Extra fancy, try to refactor the logic above into ListReduce()

Upvotes: 1

Related Questions