Dereference operator gives different results than array offset operator with void*

Go To StackoverFlow.com

0

The following C++ Win32 console program assigns an array to a pointer to void, and prints the results in two different ways:

// Foo.cpp : A Win32 console application.
//
#include "stdafx.h"

typedef unsigned char elem_type;
#define ELEM_COUNT 4

int _tmain(int argc, _TCHAR* argv[])
{
    elem_type *ary = new elem_type[ELEM_COUNT];
    for (int i = 0; i < ELEM_COUNT; i++)
    {
        ary[i] = ((i + 1) * 5); // multiples of 5
    }
    void *void_ary = ary;

    for (int i = 0; i < ELEM_COUNT; i++)
    {
        printf("void_ary[%d] is %u\t", i, ((elem_type*)void_ary)[i]);
        printf("*(void_ary+%d) is %u\n", i, *((elem_type*)(void_ary))+i);
    }

    void *allocd_ary;
    return 0;
}

Here is the output:

void_ary[0] is 5        *(void_ary+0) is 5
void_ary[1] is 10       *(void_ary+1) is 6
void_ary[2] is 15       *(void_ary+2) is 7
void_ary[3] is 20       *(void_ary+3) is 8

Using square brackets prints the result that I expected. But dereferencing pointer offsets does not, even though the array is being typecast.

Why the discrepancy?

2012-04-05 18:02
by Buggieboy


3

Well that is because you are dereferencing the value then adding 'i' to the result. You need some more parenthesis around the pointer cast or using static_cast which is more obvious.

As in:

*(static_cast<elem_type*>(void_ary)+i)

2012-04-05 18:04
by tyranid
Okay, my bad. The second printf is just taking the first element's value and adding 1 to it. Should be printf("(void_ary+%d) is %u\n", i, *(((elem_type)(void_ary))+i)) - Buggieboy 2012-04-05 18:11
Correct, therefore it's not really the four different elements, but the same one that is being added with i four times and printed out, with i starting at 0. It's slippery sometimes, don't worry about it - NoName 2012-04-05 18:41


1

printf("*(void_ary+%d) is %u\n", i, *((elem_type*)(void_ary))+i);

Here it seems that you are dereferencing the value BEFORE adding i to it. This will cause to get always the first element of the array (since you are dereferencing the same pointer 5 times) and add i to it.

Try with:

*((elem_type*)(void_ary)+i)
2012-04-05 18:05
by Jack


1

Your expression don't mean the same thing. What you write as

*(void_ary+i)

Is not actually that. In fact it is

void_ary[0]+i

according to your printf notation.


If you write

*((elem_type*)(void_ary))+i

as

*((elem_type*)(void_ary)) + i

then I think it becomes more clear. You are looking for:

*((elem_type*)(void_ary)+i)
2012-04-05 18:06
by David Heffernan
Ads