I was testing the new operator in C++ as the following:
#include <iostream>
using namespace std;
int main()
{
int *Q = new int[5];
Q[0] = 0;
Q[1] = 1;
Q[2] = 2;
Q[3] = 3;
Q[4] = 4;
for (int i = 0; i < 7; i++)
{
cout << "Q[" << i << "] = " << Q[i] << endl;
}
return 0;
}
If you notice, in the for loop I am exceeding the limit of the pointer and I was expecting an stack over flow type of error; but instead of that it just printed what ever these two extra locations have.
Does any one have explanation about this ?
Yes, what is happening is that your program is "walking off" the end of an array, and is printing out garbage. "Garbage" in this context can be anything in the computer (memory, etc.). It does not have protections against this like Java or Python does.
Related
I just started using c ++. I am trying to run a forward Euler, where I use a for loop and pointers. But I don't understand what's wrong?
#include <iostream>
using namespace std;
void euler(){
int n = 10;
double dt = 0.1;
double *a=new double[n];
double *v=new double[n];
double *t = new double[n];
int vr = 5;
for (int i=0;i<n; i++){
a[i+1] = vr + i;
v[i+1] = v[i] + a[i+1]*dt;
t[i+1] = t[i] + dt;
}
cout << v << endl;
}
int main(int argc, char const *argv[]) {
euler();
return 0;
}
The terminal gives me this "0x7fce7cc017d0"
You are printing out the pointer itself, instead of the value to which it is pointing. Try one of these:
cout << *v << endl;
or
for (int i=0;i<n; i++)
cout << v[i] << endl;
Also, as mentioned in a commment, no need for the +1 in your array indexing. By the way, this is not a good use of pointers in C++. In general, you don't want to use pointers unless you really need to. With code as simple as yours, you can simply declare arrays.
double *v=new double[n];
...
cout << v << endl;
V is a pointer to an array of n doubles.
When you are printing you are printing the value of the pointer.
Which is why you get results like "0x7fce7cc017d0" because that's the value of the pointer.
If you want to print out the values of the array you must index into it properly.
std::cout << v[0] << "\n"
You can make your original code print the content of vector v if you implement operator << for vecotor, for example like here:
Overloading output stream operator for vector<T>
Hey so below is the code that i came up with can some explain me what is wrong its reverse of an array
#include <iostream>
using namespace std;
int main() {
int arr[4] = {1,4,3,2};
int size = sizeof(arr)/sizeof(arr[0]);
int n = size - 1;
cout << size << endl;
cout << n << endl;
for (int i = 0; i<size; i++)
{
arr[i] = arr[n - i];
cout << arr[i] << endl;
}
return 0;
}
You've answered your own question. But effectively, instead of swapping the values from opposite ends of the array, you're overwriting the values at the beginning with those at the end, and once you reached the mid point, you start to copy those back into the second half.
As you wrote:
arr[0] = arr[3];
but later
arr[3] = arr[0];
which is just a long winded way of reversing the second half of the array twice.
Closed. This question needs debugging details. It is not currently accepting answers.
Edit the question to include desired behavior, a specific problem or error, and the shortest code necessary to reproduce the problem. This will help others answer the question.
Closed 6 years ago.
Improve this question
I am running below code and i am getting output as 8 0 4, rather 8 9 4. Can you please help me understand the problem with this code-
#include <cstdlib>
#include <iostream>
using namespace std;
int main() {
int *p;
p = (int*)calloc(2, sizeof(int));
*(p + 0) = 8;
*(p + 1) = 9;
p = (int*)realloc(p, 3);
*(p + 2) = 4;
for (int i = 0; i < 3; i++)
cout << p[i] << " ";
free(p);
p = NULL;
}
The realloc function needs the size on bytes and not elements.
You need to do
int *temp = realloc(p, 3 * sizeof(*temp));
if (temp == NULL)
{
// Handle error...
}
p = temp;
Note that I use a temporary variable for the result of realloc. This is because if realloc fails it will return NULL and reassigning the result back to the pointer you pass as the first argument then you will lose the original pointer.
The size specified as an argument to realloc() must be computed as a number of bytes. As you found out yourself, the simple fix is
p = (int*)realloc(p, 3 * sizeof(int));
Incidentally, you could use the type of *p instead of int to avoid potential inconsistencies if the type of p changes later:
p = (int*)realloc(p, 3 * sizeof(*p));
But since the cast is needed in C++, the inconsistency at least be visible.
You should also test whether calloc() and realloc() succeeded. They do not throw exception but return NULL when out of memory.
Note that you should decide whether you program in C or C++. These languages have a common ancestry but have diverged notably and some idioms used in one are considered bad style in the other, as more appropriate and safer constructs are available.
Here is a corrected version of your program in C:
#include <assert.h>
#include <stdio.h>
#include <stdlib.h>
int main(void) {
int *p = calloc(2, sizeof(*p));
assert(p != NULL);
*(p + 0) = 8;
*(p + 1) = 9;
p = realloc(p, 3 * sizeof(*p));
assert(p != NULL);
*(p + 2) = 4;
for (int i = 0; i < 3; i++) {
printf("%d ", p[i]);
}
putchar('\n');
free(p);
return 0;
}
While here is C++ program by PaulMcKenzie that implements the same thing, although the use of pointer p is still frowned upon:
#include <vector>
#include <iostream>
using namespace std;
int main() {
std::vector<int> pV(2);
int *p = pV.data();
*(p + 0) = 8;
*(p + 1) = 9;
pV.resize(3);
p = pV.data();
*(p + 2) = 4;
for (int i = 0; i < 3; i++) {
cout << p[i] << " ";
}
}
As you can see, std::vector<int>::resize() takes the number of elements, no need to compute byte counts.
Using pointers and especially pointer arithmetic is not good practice in C++, a much simpler version is:
#include <vector>
#include <iostream>
using namespace std;
int main() {
std::vector<int> v(2);
v[0] = 8;
v[1] = 9;
v.resize(3);
v[2] = 4;
for (int i = 0; i < 3; i++) {
cout << v[i] << " ";
}
}
You could also use an enumerator for the printout.
Ok, I got the problem:
p = (int*)realloc(p, 3);
the size value I had specified was 3, it should have been 3 * sizeof(int)
I'm trying to learn more about malloc() and need help clarifying the output. I want to reserve 10 bytes of memory and be able to access them individually but they must be in one block. Here is the code:
#include<iostream>
using namespace std;
#include<stdio.h>
#include<stdlib.h>
int main()
{
char neededbytes = 10;
char *p;
p = (char *)malloc(neededbytes * sizeof(char));
if(p==NULL)
{
cout<<"Error! memory not allocated.";
exit(0);
}
else
{
for (int i = 0; i < neededbytes; i++)
{
p[i] = 0;
}
for (int i = 0; i < neededbytes; i++)
{
cout<<"Address at index " << i << " is ";
cout<<&p+i<<endl;
}
}
free(p);
}
The output of the program shows that all addresses are 8 bytes apart. Shouldn't they be only one byte apart? Is there a way for me to know if char consumes 8 bytes on my architecture?
&p+i is the same as (&p)+(i), and since p has type char*, &p has type char**. As a result, adding i will actually add i * sizeof(char *) bytes to the address denoted by &p.
What you want is p + i, which will add i * sizeof(char) bytes to the address stored in p. In other words, you already have a pointer to contiguous data when you use malloc(). Of course, this is C++, so char * is handled specially by std::cout, std::cerr, and the std::ostream class in general. You'd need to do something like static_cast<void *>(p + i) rather than just p + i as you would use in C.
As others have stated, you should avoid using malloc() and free() in C++ when possible; C++ has the new[] and delete[] operators for your purpose.
cout<<&p+i<<endl; should just be cout<<static_cast<void*>(p+i)<<endl;
It's because you are using the address of operator, the offset will be i * sizeof(char *) in that case which on your system is apparently 8 * i bytes.
Try this instead
#include <iostream>
#include <stdio.h>
#include <stdlib.h>
using namespace std;
int main()
{
char neededbytes = 10;
char *p;
p = static_cast<char *>(malloc(neededbytes));
if (p == NULL)
{
cout << "Error! memory not allocated.";
exit(-1);
}
for (int i = 0; i < neededbytes; i++)
p[i] = 0;
for (int i = 0; i < neededbytes; i++)
{
cout << "Address at index " << i << " is ";
cout << static_cast<void *>(p + i) << endl;
}
free(p);
}
You could look at the byte alignment of char in your compiler output settings but I bet char is always 1 byte. Try a few changes like this (I think you are accessing the wrong array element at &p+i) :
int main()
{
int neededbytes = 10;
char *p=NULL;
p = malloc(neededbytes * sizeof(char));
if(p==NULL)
{
cout<<"Error! memory not allocated.";
exit(0);
}
else
{
for (int i = 0; i < neededbytes; i++)
{
p[i] = 0;
}
for (int i = 0; i < neededbytes; i++)
{
cout<<"Address at index " << i << " is ";
// Dave cout<<p+i<<endl;
cout<<&(p+i)<<endl;
}
}
free(p);
}
NB: Dave shared the correct syntax of p+i. Thanks Dave
Change cout<<&p+i<<endl; to cout<<static_cast<void*>(p+i)<<endl;.
Here's a site that talks about memory alignment on GNU systems. It will always be 8(16 for 64 bit systems) byte aligned. There are some libc (stdlib.h) functions that can force alignment for you listed there though.
http://www.gnu.org/software/libc/manual/html_node/Aligned-Memory-Blocks.html
I'm in the process of teaching myself C++ and am currently learning about dynamically allocating memory. Here's the code that I'm currently working with:
#include <iostream>
using namespace std;
int *memAdd(int* dyn_Point, int *lenPoint){
int *new_Dyn_Point = new int[*lenPoint * 2];
*lenPoint = *lenPoint * 2;
for(int i = 0; i < *lenPoint; i++){
new_Dyn_Point[i] = dyn_Point[i];
}
delete lenPoint;
delete[] dyn_Point;
return new_Dyn_Point;
}
int main(){
int len = 2;
int *lenPoint = &len;
int current = 0;
int val;
int *dyn_Point = new int[len];
cout << "Input a value for point 1: ";
cin >> val;
dyn_Point[current] = val;
while(val > 0){
current++;
cout << "Input a value for point " << current+1 <<" (0 to exit): ";
cin >> val;
if(current+1 == len){
*dyn_Point = *memAdd(dyn_Point, lenPoint);
cout << len;
}
dyn_Point[current] = val;
}
for(int i = 0; i < len; i++){
cout << &dyn_Point[i] << "\n";
cout << dyn_Point[i] << "\n\n";
}
delete[] dyn_Point;
}
My Question: When adding more memory does it have to increment by a certain value?
Whenever I start with a value in my "len" variable that's not 2 my program will crash either as soon as I try and allocate more memory or after more memory has been allocated and even more has to be added a second time.
Is this how it's supposed to be or am I missing something entirely here?
Your while loop need a break
while() {
//do your steps
break;
}
In function memAdd following changes required :
// *lenPoint = *lenPoint * 2;
// above line need to be commented else it will trouble the loop condition by causing over flow:
for(int i = 0; i < (*lenPoint-1); i++){
// for loop is corrected to resolve the over flow
Below delete is unnecessary since you didn't allocate memory
using this variable
// delete lenPoint;
For your question: When adding more memory does it have to increment by a certain value?
There is no hard and hard fast rule on this regard. std::vector<> double its size( memory allocation) whenever it is needed more memory. It is slightly different than your approach. You are doubling memory before reaching the allocated upper limit.
**Edit**
Compiled full code as OPs request
#include <iostream>
using namespace std;
int *memAdd(int* dyn_Point, int *lenPoint){
int *new_Dyn_Point = new int[*lenPoint * 2];
// *lenPoint = *lenPoint * 2;
for(int i = 0; i < (*lenPoint-1); i++){
new_Dyn_Point[i] = dyn_Point[i];
}
//delete lenPoint;
delete[] dyn_Point;
return new_Dyn_Point;
}
int main(){
int len = 2;
int *lenPoint = &len;
int current = 0;
int val;
int *dyn_Point = new int[len];
cout << "Input a value for point 1: ";
cin >> val;
dyn_Point[current] = val;
while(val > 0){
current++;
cout << "Input a value for point " << current+1 <<" (0 to exit): ";
cin >> val;
if(current+1 == len){
*dyn_Point = *memAdd(dyn_Point, lenPoint);
cout << len<<"\n";
}
dyn_Point[current] = val;
break;
}
for(int i = 0; i < len; i++){
cout << dyn_Point[i] << "\n";
cout << &dyn_Point[i] << "\n\n";
}
delete[] dyn_Point;
}
"My Question: When adding more memory does it have to increment by a certain value?"
Of course you have to manage your memory allocations using a design like this.
In particular you should obey the Rule of Three (Five), and to copy all of the existing elements, when reallocating memory to increase to the necessary amount.
The much better choice than doing it all yourself (which is likely to be error prone), is to use a
std::vector<int> dyn_point;
and/or alike in your class.
Memory management is taken care of in the container implementations, and you don't need to bother about it.