Why do I have to use free() when I declare a pointer such as:
int *temp = (int*)malloc(sizeof(int))
*temp = 3;
but not when I do:
The need to free() doesn't depend on whether or not you've declared a pointer, but rather whether or not you've malloc()ed memory.
Like Brian Bondy said before, variables ("int number", "char string[10]", "float your_boat", etc.) go away when then fall out of scope, like when your code leaves a function block. So the pointer in your question ("temp") doesn't go away when you call free() -- rather, whatever your code allocated when it called malloc() goes away. Your pointer still stays there, i.e. immediately after your example code you could say "temp = &some_other_variable" without having to say (again) "int *temp;".
If somebody ever implemented a function, that they also happened to call malloc(), that would claim memory for your program, and that did not require you to release that data, then you would be able to say
int * temp = (int*)malloc(sizeof(int));
without later saying
free(temp);
But that's not the way malloc() is implemented.