For Loop Error

loop
#1

Hello,

I’m struggling a bit with a for loop, could you please assist?

The below code works perfectly:

paramNames = DSCore.List.GetItemAtIndex(parameterList, 0);

profile0 = DSCore.List.GetItemAtIndex(profileList, 0);
paramVals0 = DSCore.List.GetItemAtIndex(parameterList, 1);
paramValsStr0 = DSCore.String.ToNumber(paramVals0);
element0 = profile0.SetParameterByName(paramNames, paramValsStr0);

profile1 = DSCore.List.GetItemAtIndex(profileList, 1);
paramVals1 = DSCore.List.GetItemAtIndex(parameterList, 2);
paramValsStr1 = DSCore.String.ToNumber(paramVals1);
element1 = profile1.SetParameterByName(paramNames, paramValsStr1);

profile2 = DSCore.List.GetItemAtIndex(profileList, 2);
paramVals2 = DSCore.List.GetItemAtIndex(parameterList, 3);
paramValsStr2 = DSCore.String.ToNumber(paramVals2);
element2 = profile2.SetParameterByName(paramNames, paramValsStr2);

Now I am trying to put it into a for loop, which isn’t working:

profile = [Imperative]
{
	paramNames = DSCore.List.GetItemAtIndex(parameterList, 0);
	noProfiles = 0..9;
	profile = {};
	paramVals = {};
	paramValsStr = {};
	element = {};

	for (i in noProfiles)
	{
		profile[i] = DSCore.List.GetItemAtIndex(profile, {});
		paramVals[i+1] = DSCore.List.GetItemAtIndex(parameterList,{});
		paramValsStr[i] = DSCore.String.ToNumber(paramVals,{});
		element = profile.SetParameterByName(paramNames, paramValsStr);
	}

	return = element;
};

Please assist with what I’m doing wrong in my conversion of the initial code to the for loop.

(I’ll be honest I don’t know what [Imperative] does. I initially had profile = {}, which wouldn’t work. I saw the [Imperative] in a loop on the forums and used it :see_no_evil:

Kind regards,
Connor

0 Likes

#2

Hi,

A few things here :

  • The arguments that you give to the List.GetItemAtIndex nodes are wrong. You should give a List and an int : you are giving two lists, one of them being an empty list.
  • You should not need a loop for those operations : Dynamo permits you to compute several results in parallel : just create the lists you need and use the correct list levels. I’ll try to upload an example if I can here.

Edit : (for the sake of better understanding, I chose arbitrary inputs. Just change the inputs in your graph accordingly).

In the first example, I’m doing as you were doing : get the element first element of each list, and operating of those elements to get the result I want for the first iteration.

In the second half of my graph, I’m not getting those elements, and I’m still using the same syntax to compute my result. Yet, Dynamo get what I was trying to saying to it, i.e. compute for each the result for each set of input.

1 Like

#3

Thanks for the assistance @mellouze!

I mostly understand your logic, but am struggling a bit to apply it fully.

profileList;
paramList;
parameterNames = List.DropItems(paramList,-10);
paramVals = List.DropItems(paramList,1);
paramValsStr = String.ToNumber(paramVals);
element = profileList.SetParameterByName(parameterNames, paramValsStr);

Looking at the watch nodes furthest to the right in the image below, all seems in order. However, my parameter values in my family aren’t changing (as they did in the original code from my first post), which leaves me to believe that there is something wrong with this line:

element = profileList.SetParameterByName(parameterNames, paramValsStr);

Could you please advise on where I’ve gone wrong here?

0 Likes

#4

Hi again,

This is much better at first glance :slight_smile:
First, change the nodes circled in red by A[0..9], that will be much more efficient.

Second, I don’t truly get what you are trying to do in your graph and why it is not working. Could you show us a simpler example and/or write down the expected output ? That way, it would be simpler to help you too :wink:

1 Like

#5

I don’t completely follow either, but I suspect it’s a lacing issue.
He’s got 10 elements (profiles), with 47 parameters each, which he wants to set, but instead ends up with a list of 10x the same element (and it being unclear if the parameters even got set as intended at all).
So something like…
profileList<1>.SetParameterByName(parameterNames<1>, paramValsStr<1><2>);

Or something along those lines… I’m still not too at home with the lacing syntax :flushed:

1 Like

#6

Oh right, i see, thanks ! :slight_smile:
The best way would certainely be to use the nodes rather then DesignScript and eventually, when everything is set, to turn back to DesignScript through Node to Code :slight_smile:
I cannot help more that that as I do not know how those items should be laced in the first place…

2 Likes

#7

Ah okay, thank you kindly to the both of your for your friendly assistance! Resultantly I figured it out.

This coding stuff is really fun.

@mellouze I felt pretty stoked when you acknowledged my previous improvement. :sunglasses:

Below, the lacing that was required for it to work:

element = profileList<2>.SetParameterByName(paramNames<1>, paramValsStr<2>);

Why though?

I presume its because paramNames remains constant throughout the iterations, whereas profileList & paramValsStr reiterate?

So something along the lines of:
For the function SetParameterByName:
Iterate the element identity {counter+} and parameter values {counter+}, while keeping parameter names constant.

Therefore the line above is essentially a type of loop?

I don’t know if I understand or whether I am explaining myself properly. :see_no_evil: Some clarification would be great!

There doesn’t seem to be much material to read up on on Replication Guides?
I found this:
http://dynamobim.org/cbns-for-dummies/

And post #3 here (which I must still read through :D):
https://www.revitforum.org/dynamo-bim/27485-introduction-designscript.html

2 Likes

#8

Glad you figured this out !

From my undestanding of Dynamo, there is no iterations here, only parallel computation : you could have done each operation seperatly, without taking the other into considerations. It is like if you had two lists ( say [1,2,3] and [4,5,6]) and asked a team of smart guys and gals (metaphor for Dynamo) to compute the sum of the two lists. This team would work in parallel and three people would have done the calculation : a first person would compute 1 + 4, and second one 2 + 5, and a third one 3 + 6. Ultimately they would gather to form the result ([5,7,9]), but no one had any access to the inputs of his or her buddies.

To be honest, I never got the thing with<1>, <2>, etc, but it definitely has something to do with lacing haha :stuck_out_tongue:

1 Like

Looping logic through sublists
#9

Sublists. Dynamo can’t magically figure out (well, not always…) which lists you want to perform a particular operation on or with. Your first list is 1-dimensional, while the other two are 2-dimensional, and it just tries to work something out.
I’ve actually struggled a lot with this before and in the recent past actually written convoluted loops in imperative blocks to get the lacing right because I couldn’t wrap my head around the replication guide syntax(and still haven’t fully)… Fixing that yielded huge performance gains, though.
Point being, you have to explicitly tell Dynamo you want to match this list at such level with that list at so level. It can just be complicated (and infuriating) to figure out how to tell Dynamo that. :slight_smile:

There’s a bit more information on replication guides here as well:
http://primer.dynamobim.org/en/07_Code-Block/7-2_Design-Script-syntax.html

1 Like

#10

@mellouze that makes a lot of sense, thank you!

@Avz sweet.

Ja, my script runs at least 5x faster now that I wrote it this way, as opposed to my initial script using independent nodes!

Its currently a case of do - then learn :stuck_out_tongue:

Now I just need to integrate this logic to my Revit families :sweat_smile:

1 Like