Search code examples
pythonnumpydynamically-generatedindices

Is there a way to generate a list of indices using numpy


Can I use numpy to generate repeating patterns of indices for example.

0, 1, 2, 3, 4, 5, 0, 6, 7, 8, 9, 10, 0, 11, 12, 13, 14, 15

or

0,1,2,1,2,3,4,5,6,5,6,7

Is there a method in numpy i can use to generate these lists between a range ?

currently I am doing this using lists in python but I was curious if I could use numpy to speed things up.

I am not sure what methods to even look into other than numpy.arange.

Just to further clarify I am generating indices to triangles in opengl in various patterns.

so for traingles in a circle I have some code like this.

    for fan_set in range(0, len(self.vertices) / vertex_length, triangle_count):
        for i in range(fan_set + 1, fan_set + 8):
            self.indices.append(fan_set)
            self.indices.append(i)
            self.indices.append(i + 1)

Solution

  • Your first example can be produced via numpy methods as:

    In [860]: np.concatenate((np.zeros((3,1),int),np.arange(1,16).reshape(3,5)),axis=1).ravel()
    Out[860]: 
    array([ 0,  1,  2,  3,  4,  5,  0,  6,  7,  8,  9, 10,  0, 11, 12, 13, 14,
           15])
    

    That's because I see this 2d repeated pattern

    array([[ 0,  1,  2,  3,  4,  5],
           [ 0,  6,  7,  8,  9, 10],
           [ 0, 11, 12, 13, 14, 15]])
    

    The second pattern can be produced by ravel of this 2d array (produced by broadcasting 2 arrays):

    In [863]: np.array([0,1,4,5])[:,None]+np.arange(3)
    Out[863]: 
    array([[0, 1, 2],
           [1, 2, 3],
           [4, 5, 6],
           [5, 6, 7]])
    

    I can produce the 1st pattern with a variation on the 2nd (the initial column of 0s disrupts the pattern)

    I=np.array([0,5,10])[:,None]+np.arange(0,6)
    I[:,0]=0
    

    I think your double loop can be expressed as a list comprehension as

    In [872]: np.array([ [k,i,i+1] for k in range(0,1,1) for i in range(k+1,k+8)]).ravel()
    Out[872]: array([0, 1, 2, 0, 2, 3, 0, 3, 4, 0, 4, 5, 0, 5, 6, 0, 6, 7, 0, 7, 8])
    

    or without the ravel:

    array([[0, 1, 2],
           [0, 2, 3],
           [0, 3, 4],
           [0, 4, 5],
           [0, 5, 6],
           [0, 6, 7],
           [0, 7, 8]])
    

    though I don't know what parameters produce your examples.