List.ReplaceItemAtIndex between lists

Hi guys. I hope you’re ok and that someone finds some time to help me.

I’m having problems with the List.ReplaceItemAtIndex. I have two lists, one with indexes and another with points I got from a feature line. I would like to place the points in my new list depending on the index but what I always get is something like this (see image)
The result I get

It places the 75 points at the first index. I have tried using the @levels, but it just does another thing completely different from what I expected.

The final result that would be ok for me is to have my final list with 142 items, the points placed at the right index, and the zeros filling the rest of the indexes as they are already.

Can someone please help me find out what I am doing wrong?
Please let me know if you need more info…
PD:*I tried to upload the .dyn file, but It wasn’t possible because I’m a new user.

Hi
Share dyn file on any download site

Hi!! You’re right. I didn’t think of that… here it is:

:grinning:

Sounds like you’re trying to replace multiple items at once. The core node only replaces one item per list. You’ll have to use a custom node (there are a couple out there from some of the common custom packages) or python in order to replace multiple items at once.

Hi @Nick_Boyts that’s right, I’m trying to replace many items. I’m trying to place a list within a list. Can you show me how to navigate both lists with a loop while evaluating the index to determine if the item must or must not be placed?

You’re going to have to provide more information. If you have a specific condition that determines whether an item gets replaced or not then you’re probably better off with an IF statement.

I’ll try to explain. I’m trying to build a point-coordinates report in Excel.

I got the points from the feature lines of my corridor and poured the data into an excel file. However, I realized something was missing. As I had my dynamo canvas, it got the data and placed it one point after the other without minding the station. You know, there will be some places along the corridor where I won’t have daylight. So when I create the final report, there will be some gaps where I don’t have data, and I need it to be this way to fill those gaps later manually with notes.

Something like this
image

Then, I got the station of my points, compared them with the baseline stations, and found out what the index was of every point depending on the baseline stations list. As a result, I now know where each of my points must be located in a new list just for those stations that apply. But here, the problem came when I tried to create a new list that would have points and zeros where daylight is not present.
I hope I was clear. Any help is appreciated.

Maybe I don’t understand the issue.
The data you pulled from excel should contain blank values at the points without daylight. There shouldn’t be any issues there. If you’re going back to fill those blanks with notes now then I would use an IF statement instead of replacing each of the items. The IF statement would be very simple, if the item is blank ("") then return the note value, otherwise return the original item:
item=="" ? note : item;

Hi @Nick_Boyts, I think I wasn’t clear enough. The image of the excel is the final result. I mean. I have the corridors, and I have to get the coordinates of certain points to place them there in excel. I want dynamo realizes the stations where a certain code is not present and reports nothing to fill at those stations (these are the gaps).

Gotcha. What does your data look like now?

Hi @Nick_Boyts thanks for your interest.
Here I post a screenshot. You can see my spreadsheet to the left, and the points in dynamo to the right. As you can see in this example, there are stations where I didn’t have “hinge” or “daylight.” However, the way I’ve managed to get the point coordinates from the feature lines of my corridor and pour the data within the spreadsheet hasn’t allowed me to place the info where it truly belongs depending on the station, which would also be reported and placed in the first column.


e

Today we can get a similar report with the out-of-the-box tool FeatureLineReport of C3D. However, It doesn’t allow me to get the coordinates at geometry points and superelevation points. That’s why I’m trying to build this canvas. The out-of-the-box report lets the blank cells at the stations where there is nothing to report from that specific code (see the second image)

My background is not in Civil so I’m afraid I’m a little lost on the specifics here, but it seems like this in an issue with your data collection before you even get to Dynamo.

If I’m following correctly, the original spreadsheet (first image) has the location data for the stations without hinge or daylight, but the ootb report (second image) does not. It seems like the ootb report would not be a viable option then, or would have to be used in combination with the original spreadsheet.

Is the spreadsheet data the data that you’re using in your graph currently? If so, we’d need to see how you’re filtering your data for point creation, as it seems you need a second condition to handle these missing stations.

Hi @Nick_Boyts. Thanks for your kind effort in helping me. Thanks for letting me know that your background is not Civil 3D. I’ll try to explain it again since I’ve been a little blurry.

I have a corridor in Civil 3D. Like any corridor in Civil 3D, this one is made of assemblies that control the creation of “feature lines” along the alignment of the road depending on previously assigned “codes.” For instance, if a code for the Edge-Of-Pavement is set, then I’ll have a feature line along the corridor that represents it in 3D. The assemblies are inserted at a specific frequency along the alignment (every 5m, 10m, etc.). At every assembly placement, a point for every “feature line” is created if the conditions at that station are those that allow it to happen.

An important output of our design as highway engineers is the report that allows surveyors to stake out the design on the field. Therefore, we extract the coordinates from the model to create such a report.

Now, what I’m doing is getting the point coordinates of my desired feature lines at the assembly placement that is present in the Civil 3D corridor. When I get those coordinates, everything is ok until I’m working with feature lines that are not continuous along the corridor. Let’s say those that appear just at some parts of the model but not from the beginning to the end.

See the previous image. When I get the list of points, Dynamo gets all the available points, but they appear one after the other without considering the gap that is present in the middle. The gap is important because when I’m creating the report, I have to indicate in those blank spaces the reason why there is no data (In the case of the image, there is a retaining wall), and not having those empty spaces would implicate to reorganize the data on the spreadsheet. I’m trying to automate this because, even though I can have the information I need with the out-of-the-box tools that Civil gives me, I always have to reorganize it later in Excel, and this is time-consuming.

Let’s go to Dynamo:

This is my list of points; as you can see, there are just 75 points.
image
Every single point on that list is placed at a different station along the alignment of my road at the given frequency I was talking about previously. In this case, my frequency is 10m.

According to the frequency (and having some particular additional points I needed), there are 143 stations where I can get data, considering the length of my alignment.
These are the stations where there is data to get from my corridor (my alignment starts at the k3+950 station, that’s the first number you see there):

As you can see, there are 143 stations where the data can be extracted. If you compare the list sizes, you immediately notice that the feature line from which I got my points is not present from the beginning to the end of the alignment. That’s why I created another list to determine which station every point belonged to.
This is the list with the stations of the points from the first list:

Notice the list size again and the highlighted in blue. You can notice that there is no “hinge” feature line in this case for stations ranging from 4340 to 4390, and there is data again in 4400.

Now, what I’m trying to do, is to accommodate my points (first image) in a new list that not only will have the size of the whole available stations’ list (the second image) but also will respect the stations each point belong to. This means that when there are stations where my feature line is not present, I will fill the point for that station with a (0,0,0) or (“”,“”,“”) to create the blank space I need to see in Excel when I pour the data there. In Excel I’ll have some rows (X,Y,Z coordinates) with data and others with zeros or empty.

I have created a block with a nested “for loop” to solve this, but I haven’t been able to make it work. I’m completely new at doing this, and I could have many errors:
image

Lista1= The big list with all the stations available in my corridor.
Lista2= The list with the stations of my points
Lista3= The points I want to organize in a new list depending on their corresponding stations.
Lista4= The new list with my points and the (0,0,0) points at the stations where there was no data.

This was too long to explain, but I sincerely hope I made myself clear and you can understand to see if you can provide me with some insights.
Have a good day. Any help is appreciated.
Best regards!

1 Like

That was very helpful. Thank you.

So you essentially want to fill in the “gaps” that don’t have coordinates/hinges. You could certainly write something in python to walk the data and fill in anywhere you don’t have an expected station at every 10’, but I think you can actually do it pretty easily with a few nodes.

Rather than using the actual data with missing locations, I’d start by creating an expected station list. You can either do this by manually specifying the known start and stop values, or by reading them from the report. Either way, you’d just create a list of values; something like 3950..6700..10;

You can then compare the list of expected stations to those that show up in the report. The additional locations (like 4327.31 in your image) would have to be added to the list, but that should be easy enough. That should give you a list of all stations/locations only. You can then compare those values against the report to pull in all the additional data (like x, y, z coordinates) for all the matching values, and fill in blanks for all the missing ones.

Does that make any sense?

1 Like

Hi @ecfernandez,

Something like this? Just using dummy values here.

I typically use a couple of lines of Python when needing to replace multiple items at multiple indices.

lst = IN[0]
ind = IN[1]
rep = IN[2]
for i,x in zip(ind,rep):
	lst[i]=x
OUT = lst
2 Likes

Hi, I believe that is what I’m trying to do but with one difference. I’m getting the stations directly from my model. The idea is that the spreadsheet is used just to pour data but not to read it from it since my corridors may vary a lot, and the specific stations that are not every 10m are placed differently in every corridor since they depend on geometric points like the beginning of a curve or so.

I would like just to create the list with the stations and pull the data from the model at those stations, having coordinates X,Y,Z when data is available and 0,0,0 or empty when it’s not, but I haven’t been able to find nodes that execute this action.

I get the stations from my model like this:

As you can notice, this is another corridor, and now the stations are different, the specific points are different, and so on.
Thanks again for your time and willingness to help!

Hi @mzjensen, I’ll give it a try. @david_licona suggested me something similar, but I continued looking for help since I couldn’t achieve the desired result. I don’t understand pretty much the zip() function, and that’s why I didn’t manage to solve it.
I’ll let you know If I can do it.
Kind regards! And thanks for your help!

zip() allows us to iterate through several collections at the same time. The syntax is like this:

for iterator1, iterator2 in zip(collection1,collection2):
    # loop instructions

iterator1 and iterator2 can be any name, I just put it up like that so its easier to understand. We can have as many collections as we like. What it does is that it takes the values at the same index from each of the collections through the loop. If you have collections of different length, zip will stop at the end of the shortest one (like the shortest lacing option in Dynamo).

So I’ll try to sum it up:

  • We have several lists (eg. collection1, collection2…) and we take the values that are at the same index

  • We give them some names (eg iterator1, iterator2…) and we do something with them (inside the loop) - so it allows us to combine different lists at the same time

  • Then we will go to the next index and so on and so on until one of the collection ends

1 Like

to explain zachri’s solution and it is exactly the same as what I suggested - what the for loop is doing is:

  • going throught the list of indexes (ind in zachri's solution) and the list of values (rep) at the same time

  • placing the value (iterator x in rep) at the correct index (iterator i in ind) of a list with empty values (lst)

2 Likes

Hi again guys! I came back here to say thank you! :grinning: your help was really useful. Finally, thanks to you all, I managed to create the tool I wanted.
There are still some details to improve, but it works. I’ll open another thread to post my comments regarding this later.
Best regards to all!