4

I'm trying to convert a simple C program into Python but as I don't know anything about C and a little about Python its just difficult for me..

I'm stuck at C pointers.

There is a function that takes an unsigned long int pointer and adds its values to some variables within a while-loop:

uint32_t somename(const uint32_t *z) {
    while(....) {
        a += z[0]
        b += z[1]
        c += z[2]
        z += 3
    }
}

Can someone please tell me how to accomplish the same thing in python? (The part that I didn't understand at all is " z += 3 ")

I'm aware that there aren't pointers in python. (at least not like C) But the problem is that I don't know what C pointers exactly do and therefor can't make this happen in python.

eymen
  • 628
  • 6
  • 17
  • The `....` is pretty important too. – tc. Apr 06 '11 at 23:29
  • 1
    A client calls that function by passing in the address (a pointer) to the first element of z. z+=3 moves past z[0], past z[1], past z[2], and on to z[3]. – Kirk Strauser Apr 06 '11 at 23:31
  • 2
    Also, `z= z[3:]` could be considered remotely equivalent, except for the fact that it takes a lot more time, moving memory around and there's no equivalent for `z-= 3` later on (the missing elements are not there anymore). – tzot Apr 30 '11 at 11:26

3 Answers3

10

A similar code snippet in Python might be:

def somename(z):
    i = 0
    while (....):
        a += z[i]
        b += z[i+1]
        c += z[i+2]
        i += 3

In C, z works sort of like an array index, except it starts at whatever the address of the start of the array is, rather than starting at 0. There is no analogous concept in Python, so you need to use a list index explicitly.

Whatever is inside (....) will need modification too. I'll leave that as an exercise for you, since it's unspecified in the question.

Greg Hewgill
  • 951,095
  • 183
  • 1,149
  • 1,285
1

What z += 3 means is basically advance the pointer 3 elements down. Say you have a pointer to an array in C called lst which contains [1, 2, 3, 4]. The pointer lst points to the first element such that *lst is equivalent to lst[0]. Furthermore, *(lst+1) is equivalent to lst[1].

nevets1219
  • 7,692
  • 4
  • 32
  • 47
0

Assuming z is passed as a list (in the corresponding python code). The z += 3 can be translated to del z[:3] which moves the element 3 to 0. However in python, you need to copy the array before doing that, because with the del-statement, the array gets modified.

In C you are able to access the elements before the pointed index through negative indices. This can be done with an "invisible" offset nested in a class. This offset is always added onto the index when the list is accessed. The following class demonstrates the behavior.

class pointer_like:
    def __init__(self, lst):
        self.lst = lst; self.offset = 0

    # self[index]
    def __getitem__(self, index):
        return self.lst[self.offset + index]

    # self += offset
    def __iadd__(self, offset):
        self.offset += offset

    # other member functions...

# as your example above
def somename(z):
    z = pointer_like(z)
    while (....):
        a += z[0]
        b += z[1]
        c += z[2]
        z += 3

>>> # other example
>>> z = pointer_like([0, 1, 2, 3, 4, 5])
>>> z[0]
0
>>> z += 3
>>> z[0]
3
>>>
>>> # with normal python lists, this would mean third last element
>>> z[-3]
0
>>> z += -5
>>> z[2]
0
>>>
>>> # this is special, because z.offset is negative (-2),
>>> # when a list item is accessed through a negative index,
>>> # it is counted from the end of the array in python.
>>> # In this case, it is -2, so the second last is accessed
>>> # In C this would cause undefined behavor, on most
>>> # platforms this causes an access violation
>>> z[0]
4

Note that pyhon also has a += operator for lists, but this allows to append another list at the end.

cmdLP
  • 1,658
  • 9
  • 19