-2

In the answers to the question Do I cast the result of malloc? was covered that I do not need and should not cast the returned void pointer of malloc() in C.

But how is it about the new operator in C++?


Is there an explicit reason to only do:

int *p_rt = new int;

instead of

int *p_tr = (int*) new int;

Or can I do the cast?

YSC
  • 34,418
  • 7
  • 80
  • 129
  • Why would you cast? Also, the use of `new` is taught in every C++ tutorial, what does it say there? That said, two notes: There is a "new operator" and something called "operator new". The distinction is very advanced C++ though, don't bother with that now. Secondly, avoid using C-style casts, as in above code! They are dangerous and usually bad. – Ulrich Eckhardt Jan 27 '20 at 11:15
  • Why do you ask for a reason to use the shorter syntax? I kind of expected the opposite question. – HolyBlackCat Jan 27 '20 at 11:15
  • I believe the whole point of `new` was to avoid the need for an explicit cast in a language that then didn't have templates. Casts defeat type safety. C++ has aimed to be a more type-safe C. – PSkocik Jan 27 '20 at 11:16
  • 1
    No there's no reason to cast. The result of `new any_type` is `any_type*`. Doing an explicit cast to `any_type*` is just useless. – Some programmer dude Jan 27 '20 at 11:16
  • `new int` returns an `int*`. Why would you cast an `int*` to an `int*` before assigning it to an `int*` variable? – Blaze Jan 27 '20 at 11:17
  • @Someprogrammerdude I was confused about it and thought `new` would return `void*` after I´ve read: `void* operator new (std::size_t size);` here: http://www.cplusplus.com/reference/new/operator%20new/ – RobertS supports Monica Cellio Jan 27 '20 at 11:38
  • 1
    Ah but that's *different*! The `operator new` function is *called* by the `new` operator. They do different things though: The `new` operator (as in `new int`) will call `operator new` to allocate memory, then if the type is one that have a constructor it will be called, and then it results in a pointer to the allocated object with the correct type. You can call the `operator new` function yourself if you want, but then you need to cast the result to the correct type, and remember that like `malloc`, the function call will only allocate memory, not construct objects. – Some programmer dude Jan 27 '20 at 11:44
  • 1
    OP: do not answer in the question. You can answer your own question. I've [done it for you](https://stackoverflow.com/a/59930767/5470596). – YSC Jan 27 '20 at 12:01
  • 1
    There are basically three kinds of `new` in C++. The `new` _expression_ (1), which you use, allocates memory by _operator_ `new` (2) and construct the object by _placement new_ (3). – Daniel Langr Jan 27 '20 at 12:11
  • not sure if it was already mentioned, another reason not to cast the result of `new` is not to use `new` in the first place ;) https://stackoverflow.com/questions/6500313/why-should-c-programmers-minimize-use-of-new – 463035818_is_not_a_number Jan 27 '20 at 12:39
  • @downvoters I don't undertand the downvotes. Can anyone please explain it? – Zheng Qu Jan 27 '20 at 12:39
  • 1
    @Maverobot Thanks for your support. Well, I made a mistake by myself in the distinction between `new` and `operator new`. All blame on me. But I think, too, that the downvotes wouldn´t be that necessary. If the question may be based on confusion, just explain how the things really are in a kind way and everything is fine. – RobertS supports Monica Cellio Jan 27 '20 at 13:00

5 Answers5

6

new T returns T*, thus there is no need to cast it:

T* p = new T;

The return type of malloc on the other hand, is void*, so it must be cast to T* in C++:

T* p = static_cast<T*>(malloc(sizeof(T));

Also note that as pointed in a comment, new T not only allocates the memory for the new object, but also constructs the object in that memory. malloc doesn't do it, so you must construct the object manually with placement new.

Ayxan Haqverdili
  • 17,764
  • 5
  • 27
  • 57
  • 2
    It should be noted that `new T` does *more* than just the plain allocation that `malloc` does. With `new T` the object is also constructed (the constructor is called). – Some programmer dude Jan 27 '20 at 11:19
2

Is there an explicit reason to do:

int *p_rt = new int;

instead of

int *p_rt = (*int) new int;

Yes, there are reasons to use the first. Reinterpret casts disable type diagnostics, and often result in bugs. You should avoid them if at all possible. Casting a pointer to the same type has no advantages.

P.S. Your attempted cast is syntactically wrong.

eerorika
  • 181,943
  • 10
  • 144
  • 256
1

Edit made to the question transformed into an answer

Edit: My confusion was made because I´ve read void* operator new (std::size_t size); at http://www.cplusplus.com/reference/new/operator%20new/ and thought new would return void*.

Thanks to the comments of @Someprogrammerdude and @UlrichEckhardt I´ve faced that the new operator and operator new are two different things and that new as opposed to malloc() explicitly returns a pointer of the respective type.

For everyone who encounters this question in the future, I would like to provide a link to the question where the difference between them two is described explicitly: Difference between 'new operator' and 'operator new'?

Community
  • 1
  • 1
YSC
  • 34,418
  • 7
  • 80
  • 129
0

unlike malloc() the new operator in c++ does already return a pointer of the allocated type. So there is no need to cast. In c the typechecking isnt as strict so you dont have to cast void* to the type you want. The data will automatically be interpretet as the type you have specified. If you are allocating in C++ with malloc on the other hand you should cast (else you might get compiler warnings).

Erarnitox
  • 36
  • 3
0

C allows the compiler to perform an implicit conversion from a void* pointer to another pointer type, so the return value of malloc() does not need to be type-casted explicitly in C.

C++ does not allow the compiler to perform such an implicit conversion, so the return value of malloc() must be type-casted explicitly in C++.

No type-cast is needed for the return value of new in C++, because it returns a pointer of the type that it creates, it does not return a void* pointer.

Remy Lebeau
  • 454,445
  • 28
  • 366
  • 620