I have a book that says the following:
The malloc() allocation still has one slight problem. We still have to explain the left portion of the temperature malloc(). What is the (int *) for?
The (int *) is a typecast. You’ve seen other kinds of typecasts in this book. To convert a float >value to an int, you place (int) before the floating-point value, like this:
aVal = (int)salary;
The * inside a typecast means that the typecast is a pointer typecast. malloc() always returns a character pointer. If you want to use malloc() to allocate integers, floating points, or any kind of data other than char, you have to typecast the malloc() so that the pointer variable that receives the allocation (such as temps) receives the correct pointer data type. temps is an integer pointer; you should not assign temps to malloc()’s allocated memory unless you typecast malloc() into an integer pointer. Therefore, the left side of the previous malloc() simply tells malloc() that an integer pointer, not the default character pointer, will point to the first of the allocated values.
temps:
int * temps; /* Will point to the first heap value */
temps = (int *) malloc(10 * sizeof(int)); /* Yikes! */
After reading similar threads, it's said that malloc()
returns a pointer of type void, not of type character. Am I missing something? I'm aware that it's not needed to typecast malloc()
in C.
CodePudding user response:
As user207421 mentioned in the comments, your book is most likely pretty old. Originally, C didn't have a generic pointer type (i.e., void*
). I forget when this was added. The closest thing back then was char*
since every pointer, no matter its type, can be safely cast to and from a char*
(sort of).
CodePudding user response:
Prior to the 1989 standard, C did not have a "generic" pointer type; pointer types were not compatible, so to assign a char *
value to an int *
variable (or vice versa) you needed to explicitly cast the value to the target type.
Also prior to the 1989 standard all the memory allocation functions (malloc/calloc/realloc
) returned char *
, so if you were assigning the result to a different pointer type, you had to use a cast:
int *ptr = (int *) malloc( some_size );
This, frankly, was a pain in the ass. It was recognized that C could use some kind of a "generic" pointer type, so the void *
type was introduced, along with the rule that void *
values could be converted to other pointer types (and vice versa) without needing a cast. The memory allocation functions were changed to return void *
, so a cast is no longer necessary:
int *ptr = malloc( some_size );
You cannot dereference a void *
- the result would be a void
type, which has no values and no size. For the same reason, you can’t do pointer arithmetic or use the subscript operator on a void *
.