Confusing error when deleting dynamically allocated array in C++ - c++

I am trying to implement a simple merge sort algorithm. What I am very confusing is that
I keep getting the following error message right after the "array2" is deleted.
"
free(): invalid next size (fast)
"
Please advise. Thank you very much!
#include <iostream>
#include <limits.h>
using namespace std;
void merge_sort(int*,int,int);
int main(){
//cout << "Max int: " << INT_MAX <<endl;
int n;
cin >> n;
int* array = new int(n+1);
for (int i=1; i<=n; i++)
cin >> array[i];
merge_sort(array,1,n);
cout << "--------------------------------------------" <<endl;
for (int i=1; i<=n; i++)
cout << array[i] <<endl;
}
void merge_sort(int* array,int p,int r){
cout << p << ' ' << r <<endl;
if (p == r)
return;
int q = int((p+r)/2);
merge_sort(array,p,q);
merge_sort(array,q+1,r);
//(p..q) and (q+1 .. r) sorted, then merge this two sorted array
int n1 = q-p+1;
int n2 = r-q;
cout << "Mark1 " <<n1<<' '<<n2<<endl;
int *array1;
array1 = new int(n1+1);
int *array2;
array2 = new int(n2+1);
for (int i=p; i<=q; i++)
array1[i-p] = array[i];
for (int i=q+1; i<=r; i++)
array2[i-q-1] = array[i];
array1[n1] = INT_MAX;
array2[n2] = INT_MAX; //CONSTANT, serve as sentinel
int p1 = 0;
int p2 = 0;
cout << "Mark2" << endl;
for (int i=p; i<=r; i++){
if (array1[p1]<array2[p2]){
array[i] = array1[p1];
p1++;
}else{
array[i] = array2[p2];
p2++;`enter code here`
}
}
cout << "Mark3" << endl;
delete [] array2;
cout << "Delete array2 " << endl;
delete [] array1;
cout << "Delete array1 " << endl;
}

The syntax
new int(n+1)
Creates a single int on the free-store and initialises it with n+1, and right away you access it out of bounds with array[1]. You want brackets:
new int[n + 1]
Which will create an array. The same goes for every other place like that in the program.
Also, since you are starting your loop at 1, the object array[0] is uninitialised and you get undefined behaviour if you access it, which you do. This is wasting an array element for nothing and setting up traps for yourself, I recommend you don't add 1 to the array size and start your indices from 0.

Related

How to properly insert and display data in an dynamically allocated arrays in C++?

I've been having trouble trying to properly display the correct memory address so I don't know in which memory address I'm inputting data.
#include <iostream>
using namespace std;
int main() {
system("cls");
int *p = new int[2];
for(int i = 0; i < 2; i++) {
cout << "Enter value for address " << p << ": ";
cin >> p[i];
}
for(int i = 0; i < 2; i++) {
cout << *p << " " << p << endl;
p++;
}
}
Here is the output when inputting data:
Here is the output when displaying them:
My concern is it doesn't output the correct memory address when inputting data.
But when displaying them it seems to have no problem displaying the correct memory address.
Your input loop is displaying the p pointer as-is (ie, the base address of the array) on every iteration. It is not adjusting the pointer on each iteration, unlike your output loop which does.
You are also leaking the array, as you are not delete[]'ing it when you are done using it.
Try this instead:
#include <iostream>
#include <cstdlib>
using namespace std;
int main() {
system("cls");
int *p = new int[2];
for(int i = 0; i < 2; i++) {
cout << "Enter value for address " << &p[i] << ": ";
cin >> p[i];
}
for(int i = 0; i < 2; i++) {
cout << p[i] << " " << &p[i] << endl;
}
delete[] p;
return 0;
}
Alternatively:
#include <iostream>
#include <cstdlib>
using namespace std;
int main() {
system("cls");
int *p = new int[2];
int *elem = p;
for(int i = 0; i < 2; i++) {
cout << "Enter value for address " << elem << ": ";
cin >> *elem;
++elem;
}
elem = p;
for(int i = 0; i < 2; i++) {
cout << *elem << " " << elem << endl;
++elem;
}
delete[] p;
return 0;
}

New to C++, Please help identify issue with code pointer code

Having issues with my getPosNums3 function.....all the others work as I need them to. I'm having issues in general understanding pointers, but I am sure that will pass. The aforementioned function spits out the size and address as I need it to, but when I print the newly modified array, it prints out long identical negative integers akin to this: -5476891, -5476891. It'll put out the right amount of integers, which tells me it is a small adjustment that is hanging up my code.....all these functions modify an array down to only its positive values; they just do so via different methods. I appreciate the help
#include <iostream>
using namespace std;
typedef int* IntArrayPtr;
int* getPosNums1(int* arr, int arrSize, int& outPosArrSize);
int* getPosNums2(int* arr, int arrSize, int* outPosArrSizePtr);
void getPosNums3(int* arr, int arrSize, int*& outPosArr, int& outPosArrSize);
void getPosNums4(int* arr, int arrSize, int** outPosArrPtr, int* outPosArrSizePtr);
void printNewArray(int* arr, int arrSize);
void fillArray(int a[], int size);
int main() {
cout << "Fuction 1: " << endl;
int array_size;
cout << "What is the size of the array? ";
cin >> array_size;
IntArrayPtr a;
a = new int[array_size];
fillArray(a, array_size);
int posArraySize;
int* posNums1 = getPosNums1(a, array_size, posArraySize);
cout << "Original array is: ";
printNewArray(a, array_size);
cout << "The new address is " << posNums1 << " and the new size is " << posArraySize << " " << endl;
cout << "New array is: ";
printNewArray(posNums1, posArraySize);
delete[] a;
cout << endl;
cout << "Function 2: " << endl;
int array_size2;
cout << "What is the size of the array? ";
cin >> array_size2;
a = new int[array_size2];
fillArray(a, array_size2);
cout << "Original array is: ";
printNewArray(a, array_size2);
int* posArraySize2 = &array_size2;
int* posNums2 = getPosNums2(a, array_size2, posArraySize2);
cout << "The new address is " << posNums2 << " and the new size is " << *posArraySize2 << " " << endl;
cout << "New array is: ";
printNewArray(posNums2, *posArraySize2);
delete[] a;
cout << endl;
cout << "Function 3: " << endl;
int array_size3;
cout << "What is the size of the array? ";
cin >> array_size3;
a = new int[array_size3];
fillArray(a, array_size3);
cout << "Original array is: ";
printNewArray(a, array_size3);
int* posNums3 = new int[array_size3];
int posArraySize3 = array_size3;
getPosNums3(a, array_size3, posNums3, posArraySize3);
cout << "The new address is " << posNums3 << " and the new size is " << posArraySize3 << endl;
cout << "New array is: ";
printNewArray(posNums3, posArraySize3);
delete[] a;
cout << endl;
cout << "Function 4: " << endl;
int array_size4;
cout << "What is the size of the array? ";
cin >> array_size4;
a = new int[array_size4];
fillArray(a, array_size4);
cout << "Original array is: ";
printNewArray(a, array_size4);
int* posNums4ptr = &array_size4;
int* posNums4 = new int[array_size4];
int** posNums4ptrptr = &posNums4;
getPosNums4(a, array_size4, posNums4ptrptr, posNums4ptr);
cout << "The new address is " << posNums4ptrptr << " and the new size is " << *posNums4ptr << endl;
cout << "New array is: ";
printNewArray(posNums4, *posNums4ptr);
delete[] a;
return 0;
}
int* getPosNums1(int* arr, int arrSize, int& outPosArrSize) {
int* newArray = new int[arrSize];
int counter = 0;
for (int i = 0; i < arrSize; i++) {
if (arr[i] > 0) {
newArray[counter] = arr[i];
counter++;
}
}
outPosArrSize = counter;
return newArray;
}
int* getPosNums2(int* arr, int arrSize, int* outPosArrSizePtr) {
int size = 0, counter = 0;
int newArraySize = 0;
for (int i = 0; i < arrSize; i++) {
if (*(arr + i) > 0) {
newArraySize++;
}
}
int* newArray = new int[newArraySize];
for (int i = 0; i < arrSize; i++) {
if (*(arr + i) > 0) {
newArray[counter] = *(arr + i);
size++;
counter++;
}
}
*outPosArrSizePtr = size;
return newArray;
}
void getPosNums3(int* arr, int arrSize, int*& outPosArr, int& outPosArrSize){
int counter = 0, size = 0;
for (int i = 0; i < arrSize; i++) {
if (*(arr + i) > 0) {
size++;
}
}
int *newArray = new int[size];
for (int i = 0; i < arrSize; i++) {
if (*(arr + i) > 0) {
newArray[counter] = *(arr + i);
counter++;
}
}
delete[] outPosArr;
outPosArr = newArray;
outPosArrSize = size;
delete[] newArray;
newArray = nullptr;
}
void getPosNums4(int* arr, int arrSize, int** outPosArrPtr, int* outPosArrSizePtr){
int size = 0, counter = 0, newArraySize = 0;
for (int i = 0; i < arrSize; i++) {
if (*(arr + i) > 0) {
newArraySize ++;
}
}
int* temp = new int[newArraySize];
for (int i = 0; i < arrSize; i++) {
if (*(arr + i) > 0) {
temp[counter] = arr[i];
size++;
counter++;
}
}
*outPosArrSizePtr = size;
*outPosArrPtr = temp;
}
void printNewArray(int* arr, int arrSize) {
for (int i = 0; i < arrSize; i++)
cout << arr[i] << " ";
cout << endl;
}
void fillArray(int a[], int size) {
cout << "Enter " << size << " integers." << endl;
for (int i = 0; i < size; i++)
cin >> a[i];
}
The code in question is
void getPosNums3(int* arr, int arrSize, int*& outPosArr, int& outPosArrSize){
// [snip] count number of positive entries in arr and call it "size"
int *newArray = new int[size];
// [snip] copy positive entries in arr into newArray
delete[] outPosArr;
outPosArr = newArray;
outPosArrSize = size;
delete[] newArray;
newArray = nullptr;
}
First of all, it's not a good idea for this function to delete[] outPosArr because that presumes that outPosArr is either nullptr or something that was previously allocated with new[]. If it isn't one of those two things then this function has undefined behavior.
Somebody calling a function to copy numbers into an array is not typically going to also want the function to clean up some previous thing that may or may not have been in that array.
But your real problem is that you allocate memory for an array via int *newArray = new int[size], copy stuff in, and then immediately deallocate that memory by calling delete[] newArray. This leaves outPosArr to point to what used to be an array.
Also, assigning nullptr to newArray at the end of the function does nothing, because newArray is going out of scope anyway.

double free or corruption with dynamic arrays

my problem today is with dynamic arrays. Every time I enter more then 2 test scores I get an error after I enter the 3rd max test score which says "* Error in `./a.out': double free or corruption (out): 0x09c2e028 *
Aborted (core dumped)" Am I doing something wrong with the arrays? Or is there something I'm painfully missing?
The program is supposed to take an unlimited number of test scores and their respective max possible points (i.e. test score = 76 Max test score possible = 100) and turn those numbers into a GPA. I'be only included the class I'm using to create the GPA because the rest of the code isn't finished yet as I can't get past this part.
I have to use the dynamic arrays because it is for a school assignment.
Thanks for reading I hope someone can help me!
#include <iostream>
#include <string>
#include <cmath>
#include <math.h>
#include <iomanip>
#include <cassert>
using namespace std;
void programGreeting();
class testScores{
public:
float testAverage(){
int i = 0;
float gpa2 = 0;
int loopCountVar = 0;
int size = 1;
int size2 = 1;
float *testScore = new float[size];
float *maxScore = new float[size];
while(testScore[i] != -1){
i++;
loopCountVar++;
cout << "Enter test score #" << loopCountVar << endl;
cin >> testScore[i];
if(testScore[i] == -1){
size = i;
}
assert(testScore[i] > -2);
cout << "Enter max test score #" << loopCountVar << endl;
cin >> maxScore[i];
if(maxScore[i] == -1){
size2 = i;
}
assert(maxScore[i] > -2);
}
float *gpa = new float[size];
for(i = 1; i < size; i++){
gpa[i] = testScore[i] / maxScore[i];
cout << gpa[i] << " " << endl;
}
for(i = 1; i < size; i++){
gpa2 += gpa[i];
}
for (i = 1; i < size; i++){
cout << endl << testScore[i] << " " << endl;
}
for (i = 1; i < size2; i++){
cout << endl << maxScore[i] << " ";
}
cout << endl << gpa2 << endl;
cin >> size;
delete testScore;
delete [] maxScore;
delete gpa;
return 0;
}
};
All your allocations are new ...[], so all deletes must be delete [] ....
delete [] testScore;
delete [] maxScore;
delete [] gpa;
Also your code only allocates one element for testscore and maxscore but you keep writing elements into the Array until the user enters -1. That means you will very likely write over the end of the buffer.
You should get rid of your raw pointers and use STL containers like std::vector. With these you can easily add elements to the end without having to reallocate yourself.

How to find out addresses of the slots in dynamically allocated multidimensional array?

I created a 2-dimensional dynamically allocated array. Then I wanted to output the addresses of the slots, so I can really see it's not a contiguous block of memory. I've managed to do that by &tda[i][j] statement. However, I'm wondering how I could do that by using something like *(tda+1), which is the same as &tda[1][0]. For example, how could I output tda[1][1] address using a combination of *(tda+1).
#include <iostream>
using namespace std;
int main() {
int **tda;
tda = new int*[2];
cout << tda << endl;
cout << tda+1 << endl;
for (int i=0; i<2; i++) {
tda[i] = new int[2];
}
cout << *(tda+1) << endl;
cout << endl << "Proof that the block of memory is not contiguous:" << endl;
for (int i=0; i<2; i++) {
for (int j=0; j<2; j++) {
cout << &tda[i][j] << endl;
}
}
return 0;
}
Well, you already mentioned the equivalence of a[k] and *(a + k), but let me spell it out for you:
&tda[i][j]
is
&*(tda[i] + j)
is
*(tda + i) + j
Analogously,
tda[i][j]
becomes
*(*(tda + i) + j)

Issue with Array assignment

I am having an issue with outputting an array. When I output each element without a for loop, the program runs fine. When I try to output with a for loop, the program crashes the first time I set an element in the array. I have marked the line where the program crashes when I uncomment out the for loop. My sort seems to work fine and the program is crashing way before that, so I'm pretty sure that isn't the issue. Any ideas why the 2nd for loop would crash the program at the specified line?
int main()
{
int* Array;
int j = 5;
for(int i=0; i<5; i++)
{
Array[i] = j; //Crashes here with 2nd for loop uncommented
cout << Array[i] << endl;
j--;
}
Array = insertion_sort(Array);
cout << Array[0] << endl;
cout << Array[1] << endl;
cout << Array[2] << endl;
cout << Array[3] << endl;
cout << Array[4] << endl;
/*for(int k=0; k <5; k++)
{
cout << Array[k] << endl;
}*/
}
You are accessing the pointer before initializing it. You should change
int* Array;
to
int* Array = new int[5]; // There are 5 ints in my array
and make sure to
delete[] Array;
at the end, or even better:
int Array[5]; // This way you don't need the new keyword, so you won't need to delete[] later
Right now, your array is not instanciated. It's just a pointer. You need to choose how large of an array you want before you can start writing to it.
int* Array = new int[5];
int j = 5;
for(int i=0; i<5; i++)
{
Array[i] = j; //Crashes here with 2nd for loop uncommented
cout << Array[i] << endl;
j--;
}