0

Recently I have seen a few people telling others that if they need to cast they are doing something wrong. I have this code in C++

byte* pixel = (byte*)image->GetBits();

Here I cast to a byte* because GetBits() returns a void*. So how would I either

  • have pixel hold a byte* without casting
  • use void* (I have never used this type before)

To clarify, I then go on to use pixel similar to this.

*(pixel) += 20;
*(pixel + 1) += 20;
*(pixel + 2) += 20;
Ash Burlaczenko
  • 24,778
  • 15
  • 68
  • 99

4 Answers4

2

In your case, casting is justified, but in C++, a better way to cast is to use one of the C++-style cast, so here you can use static_cast as:

byte* pixels = static_cast<byte*>(image->GetBits());

To learn about various C++-style cast, and where to use which, read these topics:

Community
  • 1
  • 1
Nawaz
  • 353,942
  • 115
  • 666
  • 851
2

Using void * without a cast is impossible by definition, since a void * cannot be dereferenced/incremented/whatever. It just means "here's a pointer to some data, I don't know what kind".

GetBits() returns a void * because the best way to access the data depends on the kind of image (in particular from the color depth) and of elaboration you want to do; naturally you have to cast it to something to do something on such data.

Matteo Italia
  • 123,740
  • 17
  • 206
  • 299
1

Your question is clear. Casting doesn't always mean you're doing something wrong, but it's a code smell.

In your particular case, the code smell is returning a void *. Why do you need a function that returns void *?

Luchian Grigore
  • 253,575
  • 64
  • 457
  • 625
  • I don't define the function, it's part of the api of CImage, http://msdn.microsoft.com/en-us/library/zx1ex9b5(v=vs.80).aspx. – Ash Burlaczenko Apr 15 '12 at 18:55
  • @AshBurlaczenko so then MS did something wrong. :) Wouldn't be the first time. – Luchian Grigore Apr 15 '12 at 18:56
  • @LuchianGrigore: I don't know, there's no type that would be really correct for that return value. – Matteo Italia Apr 15 '12 at 19:04
  • @MatteoItalia maybe a new type? I'm sure there are equivalents in, Java or C# that don't return void*... So a different design could have been made. – Luchian Grigore Apr 15 '12 at 19:07
  • @LuchianGrigore, your probably right that equivalents exist in other languages, but they will include type checking, making them slower than c++'s implementation. – Ash Burlaczenko Apr 15 '12 at 19:13
  • @AshBurlaczenko I totally agree. When it comes to C++, there's a point when you reach a trade-off between a good design and something fast. A bloated design will probably decrease speed. But I thought that was the question, right? I was rash to say MS was wrong in this case (not saying they were right), scrape that, but a better design, at the cost of efficiency, would have been possible. – Luchian Grigore Apr 15 '12 at 19:16
1

You're not really asking a question anywhere, so let me comment a bit on when casting to something else than a byte* in cases as yours might be dangerous: if the returned pointer is cast to a pointer to a 2-byte type, 4-byte type, etc. and the value pointed at isn't correctly aligned for a type of that size, than a data misalignment error can occur, which on certain architectures will just flat out kill your process. For the byte* the cast is safe, since it points at the type of smallest alignment, i.e., it's always aligned correctly.

Johann Gerell
  • 24,991
  • 10
  • 72
  • 122