c++ memory allocated at compile time - c++

I read that while dynamic memory is allocated on the heap during runtime, static memory is allocated on the stack during compile time since the compiler knows how much memory has to be allocated at compile time.
Consider the following code:
int n;
cin>>n;
int a[n];
How does the compiler possibly know how much memory to allocate for a[] at compile time if its actual size is read during the run only?

You won't be able to compile that, for the exact reason you specified. C++ needs to have a fixed number in there in order for compilation to be performed. If you want to do that, you have to use dynamic allocation.

Related

When an array is declared normally, is the memory allocated statically, dynamically or otherwise?

For example if an integer array is declared:
int ar[12];
And here a vector of integers:
vector<int> ar; //OR
vector<int> ar(12);
In either case, is memory allocated to the array at compile time or runtime? I know that vector class in C++ STL uses dynamic memory allocation but what about the ordinary array? Also:
int n;
cin >> n;
char ar[n];
If memory allocation is at compile time then how does this work? I can't find anything scavenging the net.
"Normal" arrays will have a size known at compile-time, which means the compiler can (and will) make sure that there's space for them. That space might not be allocated inside the executable program but allocated at run-time (like e.g. a local variable inside a function).
The size of a vector is unknown at compile-time, and its the vectors constructor that will allocate memory (if asked to, as in the case with vector<int> ar(12);). The memory for vectors will always be allocated dynamically of the heap.
Then there's also std::array which is a C++ standard container around a compile-time array. When it comes to size and allocations it acts like a "normal" array, but since it's also a standard container object it can be used with functions and algorithms designed for those.
And to confuse matter even more, something being "static" has a special meaning in C++, so saying than an array is "statically" allocated could mean different things depending one ones viewpoint. However, "statically allocated" seems to be commonly used for things like arrays, whose memory is allocated and handled by the compiler and its generated code.

Stack allocation of unknown size complexity

I know that stack allocation takes constant time. From what I understand, this happens because the allocation size can be determined in compile time. In this case the program knows how much memory is needed to run (for example) a function and the entire chunk of memory that is needed can be allocated at once.
What happens in cases where the allocation size is only known at run time?
Consider this code snippet,
void func(){
int n;
std::cin >> n;
// this is a static allocation and its size is only known at run time
int arr[n];
}
Edit: I'm using g++ 5.4 on linux and this code compiles and runs.
What happens in cases where the allocation size is only known at run time?
Then the program is ill-formed, and therefore compilers are not required to compile the program.
If a compiler does compile it, then it is up to the compiler to decide what happens (other than issuing a diagnostic message, as required by the standard). This is usually called a "language extension". What probably happens is: amount of memory is allocated for the array, determined by the runtime argument. More details may be available in the documentation of the compiler.
It is impossible (using standard C++ language) to allocate space on the stack without knowing how much space to allocate.
The line int arr[n]; is not a valid C++ code. It only compiles because the compiler you are using decided to let you do that, so for more information you should refer to your compiler documentation.
For GCC, you might take a look at this page: https://gcc.gnu.org/onlinedocs/gcc/Variable-Length.html
I'm using g++ 5.4 on linux and this code compiles and runs.
Yes, and this invalid code compiles under MSVC 2010:
int& u = 0;
The standard sais that this code is ill formed. Yet MSVC compiles it! This is because of a compiler extension.
GCC accepts it because it implements it as an extension.
When compiling with -pedantic-errors, GCC will reject the code correctly.
Likewise, MSVC has the /permissive- compiler argument to disable some of it's extensions.
The memory allocation procedure varies when the size to be allocated is determined at runtime. Instead of allocation on stack, memory is reserved on the heap when the size is not known at compile time. Now allocation of memory is possible on the heap until the main memory of the computer is completely used up. Also, in some languages like C,C++ the allocation is permanent and the user is required to deallocate the memory after use.
In the example given above, memory of size n*sizeof(int) is reserved on the heap and is garbage collected (in java or python) or manually deallocated if the memory is assigned a pointer. (in c/c++)

C/C++ Dynamic or Static memory allocation?

Dynamic memory allocation in C/C++ happens through malloc and the static memory allocation ex: int a[3]; its allocated after the code is executed.
But this code int x[y+1]; only can happen after a value is attributed to y and this happens in execution time, so its static, dynamic or both? does the compiler insert a malloc in the machine code automatically?
It is a Variable Length Array (VLA). Wikipedia: http://en.wikipedia.org/wiki/Variable-length_array
Technically, it is not legal in C++, but compilers often support it as an extension, but generate warnings when they are turned on. See
Why aren't variable-length arrays part of the C++ standard?
It is legal in C.
int[] is on the stack, while malloc'd or new'd things are on the heap.
VERY basically int[] gets allocated automatically when it is reached (where y is already known) and gets dropped when it gets out of scope. It is not everything already allocated at startup.
There are no hidden malloc calls or stuff, that is just how the stack memory works.
(I hope for an answer from someone who actually knows C/C++)

error creating a dynamic c++ array

I was trying to make a dynamic array in this form :
int x;
cin>>x;
int ar[x];
My g++ (gcc) compiler on Linux refused to create an array without a fixed size. However using the same code on windows on dev-cpp, it was complied and executed, also it allows me to create and use the dynamic array, i thought it was a compiler bug, however when i restarted and returned to g++ it compiled and executed the code although it refused to do it before I tried the code on windows, how can that be and is it dangerous?
C++ requires the size of an automatic storage array to be known at compile time, otherwise the array must be dynamically allocated (unless with compiler extension).
You should use
int *ar = new int[x];
...
delete []ar; // free the memory after use
or
vector<int> ar;
As the other answerers point out, if you don't know the size of the array at compile time then you should dynamically allocate using new. But (somehwat shamefully) they fail to tell you that you will be responsible for deallocating this memory with delete : details here
This responsibility (making sure you always release memory you have allocated) is the biggest source of problems in C++. A technique like RAII can make this easier (put simply : wrap the memory in an object, new in the constructor and delete in the destructor, then the language makes sure the destructor is always called)

What exactly is dynamic memory? [duplicate]

This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
Differences between dynamic memory and “ordinary” memory
I was reading the C++ tutorial and I don't understand why I need to declare dynamic memory, this is what the tutorial says:
Until now, in all our programs, we have only had as much memory available as we declared for our variables, having the size of all of them to be determined in the source code, before the execution of the program.
And then it says that we have to use new and delete operators to use dynamic memory.
However, I seem to be using dynamic memory when declare a pointer, e.g. char* p, for which I have not specified the length of the array of characters. In fact, I thought that when you use a pointer you are always using dynamic memory. Isn't it true?
I just don't see the difference between declaring a variable using new operator and not. I don't really understand what dynamic memory is. Can anyone explain me this?
I thought that when you use a pointer you are always using dynamic
memory. Isn't it true?
No it's not true, for example
int i;
int *p = &i; // uses a pointer to static memory, no dynamic memory.
However, I seem to be using dynamic memory when declare a pointer,
e.g. char* p, for which I have not specified the length of the array
of characters
char[100] string;
char* p = &(string[0]); // Same as above, no dynamic memory.
You need dynamic memory when you can't tell how big the data structure needs to be.
Say you've to read some ints from a file and store them in memory. You have no idea how many ints you need. You could pick a figure of 100, but then your program breaks if there are 101. You could pick 100,000 hoping that's enough, but it's waste of resources if there's only 10 in the file, and again, it breaks if there's 100,001 ints in the file.
In this scenario your program could iterate through the file, count the number of ints, then dynamically create an array of the correct size. Then you pass over the file a second time reading the ints into your new array.
Static v's Dynamic Memory
Static memory is static because once the program is compiled it can't be changed, it is static. Variables you declare in functions, and members declared on classes / structs are static. The compiler calculates exactly how many of each its going to need as each method gets called.
Dynamic memory is a "pool" of memory that can be made available to your program on demand, at run time.
The compiler only knows it needs to allocate some (probably unknown) amount of that memory, and to release that memory back to the dynamic memory pool.
Hope this helps.
P.S. Yes, there are more efficient ways to get an unknown number of items into memory, but this is the simplest to explain
When you have:
char* p;
p is variable of type pointer to char and p is stored on the stack and you haven't allocated any dynamic memory.
But when you do:
p = new char[100];
you have allocated a part of dynamic memory (heap) of the size 100*sizeof(char).
You are responsible to free allocated memory on the heap:
delete[] p;
You don't need to clean variables from the stack - they will be removed automatically after variable goes out of scope. In this example, p will be removed from the stack when it goes out of its scope.
Dynamic memory is memory which the programmer has to explicity request, as an oppose to have automatically allocated on the stack.
There are many advantages to dynamic memory such being persistent between stack frames (function calls) and can be of varying size.
On the stack an array much be of a certain size:
int ar[5];
However if you 10 element then you can't do it, the solution is to dynamically allocate the memory;
size_t sz;
std::cin >> sz;
int *i_p=new int[sz];
That said everything dynamically allocated must be freed (in C++ using delete)
delete i_p;
However it is generally better where possible to use wrappers to dynamic arrays such as the std::vector
size_t sz;
std::cin >> sz;
std::vector<int> vect(sz);
This will automatically manage the memory and provide a useful interface to the array.
Let's say you want to read an unknown number of integers from a user. You could, for example, declare int numbers[100], ask the user how many numbers there are (let's say this is store in variable n) and if he enters a number larger than 100, you would have no choice but to report an error. Alternatively, you could write int *numbers = new int[n] and allocate just enough space for all the numbers.
Dynamic memory in c++ is a memory allocated in a heap of operation system by using new operator. You need the dynamic memory when you need to allocate the objects which are too large and cannot be allocated in the stack, or when you have a multithreaded environment and need to share the memory allocated in one of the threads between the different threads. Pointer doesn't mean that you use the dynamic memory pointers also can contain the a stack address related with the object in the stack.
In fact, I thought that when you use a pointer you are always using dynamic memory. Isn't it true?
No. Here's a pointer to stack-allocated ("automatic") memory:
{
int i;
int *p = &i;
}