Python: store the original pointindex in list - insert() wrong usage ?



  • Hello again,

    I am trying to store the original index (pointindex) of an object in a new list with inserting it at the original position with this

    nearestPoints.insert(point['i'], op.GetPoint(point['i']) * op.GetMg())

    but i guess I am using the wrong python solution hence python "minimizes" the list to only its content (in this case 1+n items, most of the time just one)

    is there a sane solution, googling didn't get me far

    I want somthing like this:

    # what i want
    index:37 Vector(-39.182, 97.869, 277.787)
    # what i get is
    index:0 Vector(-39.182, 97.869, 277.787)
    

    thank you for your time.
    mogh



  • Hi,

    The index in the list.insert() method is the local index of the list and therefor not identical to your point index. Assuming you want to store key value pairs, a hash map should be your data type of choice, which could be a dict in Python. The task of building key-value pairs is something Python's comprehension feature lends itself very well to. Something like this:

    local_points = op.GetAllPoints()
    global_points = { i: p * ~op.GetMg()
                      for i, p in enumerate(local_points)
    }
    
    for index, point in global_points.items():
        print index, point
    

    Cheers,
    zipit



  • Thanks Zipit,
    still trying to understand it. Need to look for a comprehension tutorial.

    hm ... this gives me all points ... ah ok this kinda works

    local_points = op.GetAllPoints()
    point = vpSelect.GetNearestPoint(op, x, y, radius)
    
    global_points = { point['i']: op.GetPoint(point['i']) * ~op.GetMg()
                                          for i, p in enumerate(local_points)
                        }
    

    Is global_points a dict or a tuple ? not a plain list anymore I guess.
    I am sorry this is pulling the rug under my feet. :-P

    Thank you for your time.
    mogh



  • Hi,

    global_points ist a dict. The comprehension was just a more compact way to write this:

    global_points = {}
    for i, p in enumerate(local_points):
        global_points[i] = p * ~op.GetMg()
    

    Comprehensions are meant to build data in one go, but given your second example, you probably want to contiously store some proximity data obtained from a ViewportSelect. You cannot do that with a comprehension, you have to build you data structure the old fahsioned way then.

    Cheers,
    zipit



  • I don't have too much to add, @zipit already said everything needed.

    Just a side note to retrieve the global position you should do LocalPointPostion * op.GetMg() and not LocalPointPostion * ~op.GetMg().

    local_points = {}
    global_points = {}
    
    for i, p in enumerate(local_points):
        local_points[i] = p
        global_points[i] = p * op.GetMg()
    

    And finally, keep in mind coping data is expensive even more if your PolygonObject is pretty heavy, its recommended to use PointObject.GetAllPoints that will return a list of all points in local position. Since its build-in C++ it will be way more performant on a huge mesh.

    Cheers,
    Maxime.



  • Thanks Both of you @zipit @m_adam ,

    Quote: "keep in mind coping data is expensive"

    I had the feeling that the very nice example I am building on has some limitations (speed) as you mentioned.
    I guess I have to re organice this section (selecting points) and clean up.

    My aproach as a beginner is more or less like this.

    • try get it to work anyhow
    • try to understand it by cleaning
    • try to make a compact function so it doesn't break my code everytime i touch it ...

    I have an old C++ code as an cheat sheet to get a general idea how a perfomant code could look like (selecting & working just inside one big point object list, as far as I understand it) ,
    but at this stage I can't combine them jet hence the different selecting aproach.

    Anyway I try to get somethingmore robust ...

    Thank you for your time.
    mogh


Log in to reply