0

Case 1 Input

10
1 2 3 1 2 3 1 2 3 1 2 3

Case 1 Output

a.out: malloc.c:2401: sysmalloc: Assertion `(old_top == initial_top (av) && old_size == 0) || ((unsigned long) (old_size) >
= MINSIZE && prev_inuse (old_top) && ((unsigned long) old_end & (pagesize - 1)) == 0)' failed.
Aborted (core dumped)

Case 2 Input

4
1 2 3 1 2 3 1 2 3 1 2 3

Case 2 Output

1 1 2 3

I very well know that in both cases I am giving extra integers as input. My question is why the code is giving an error in Case 1 and not in Case 2. I am compiling my code with g++ -pipe -O2 -std=c++11 ./filename.cpp. There are no errors or warnings. I even tried replacing vector<int> arr(right) with vector<int> arr(1000000) for Case 1 still same error. The first line is the size of the array. Next line is elements of the array. Replacing all temp[...] and arr[...] with temp.at(...) and arr.at(...) I am getting following error in Case 2.

terminate called after throwing an instance of 'std::out_of_range'
  what():  vector::_M_range_check: __n (which is 6) >= this->size() (which is 6)
Aborted (core dumped)
#include<iostream>
#include<vector>
using namespace std;
void quick_sort_3(vector<int> &arr,int &left,int &right)
{
    if(left<right)
    {
        vector<int> temp(right-left+1);
        int pivot=arr[left];
        int small=left,large=right;
        for(int i=left+1;i<=right;i++)
        {
            if(arr[i]<pivot)
                temp[small++]=arr[i];
            else if(arr[i]>pivot)
                    temp[large--]=arr[i];
        }
        for(int i=left;i<small;i++)
            arr[i]=temp[i];
        for(int i=small;i<=large;i++)
            arr[i]=pivot;
        for(int i=large+1;i<=right;i++)
            arr[i]=temp[i];
        small--;
        large++;
        quick_sort_3(arr,left,small);
        quick_sort_3(arr,large,right);
    }
}   
int main(void)
{
    int left=0,right;
    cin>>right;
    vector<int> arr(right);
    right--;
    for(int i=0;i<=right;i++)
        cin>>arr[i];
    quick_sort_3(arr,left,right);
    for(int i=0;i<=right;i++)
        cout<<arr[i]<<" ";
    cout<<endl;
    return 0;
}
  • 3
    Replace all of your `arr[...]` and `temp[...]` calls with `arr.at(...)` and `temp.at(...)`. That will throw an exception on an out-of-bounds access to help you debug the issue. – Kevin Aug 18 '20 at 19:16
  • @Kevin As you said I replaced `arr[...]` and `temp[...]` with `arr.at(...)` and `temp.at(...)` and now it is giving error `terminate called after throwing an instance of 'std::out_of_range' what(): vector::_M_range_check: __n (which is 6) >= this->size() (which is 6) Aborted (core dumped)` – Mohammad Shahwez Aug 18 '20 at 19:29
  • You want to know why one oob triggers an error and the other doesn't? First and foremost oob access is UB. That aside the most likely reason would be with how vector chooses to allocate space. If you really want to catch errors in both cases use ASAN or UBSAN. – Taekahn Aug 18 '20 at 19:31
  • 1
    Now run your code through your debugger to see where that exception is thrown. – Kevin Aug 18 '20 at 19:31
  • @Kevin I'm pretty sure he already knows what the issue is, he seems to want to know *why*. But that is really an implementation detail for vector. – Taekahn Aug 18 '20 at 19:34
  • @Taekahn Knowing where a crash happens is step one in finding out what the problem is. What are you referring to when you say "that is really an implementation detail for vector"? – Kevin Aug 18 '20 at 19:37
  • 2
    Out of bounds access results in Undefined Behaviour. The behaviour of Undefined Behaviour is undefined. You could get an error message. You could get a wrong answer. You could get the right answer. You could get a crash. You could get a crash later. You could never get a crash. You could start receiving unsolicited e-mails. The possibilities are endless with Undefined Behaviour. Usually it's not worth trying to reason out the whys and wherefores. – user4581301 Aug 18 '20 at 19:42
  • @Kevin Yes, I debugged it and found the error. Thanks to everyone else also. The error was that `vector temp(right-left+1)` was being accessed as `temp.at(i)` causing out of bounds I replaced it with `temp.at(i-left)` This solved the error. I used Online C++ debugger. Once again thanks, everyone. – Mohammad Shahwez Aug 18 '20 at 19:45
  • And now you know how to debug! :) – Kevin Aug 18 '20 at 19:46
  • I assume you also fixed `temp[small++]=arr[i];` and `temp[large--]=arr[i];` – drescherjm Aug 18 '20 at 19:48
  • @drescherjm Yes, I did that also. Infact that was the one which caused the error. Thanks a lot. – Mohammad Shahwez Aug 18 '20 at 19:53
  • @drescherjm anything that isn't defined by the standard is undefined behavior. What is "supposed" to happen if you access an array outside of its bounds isnt defined. – Taekahn Aug 18 '20 at 20:06

1 Answers1

1

The error was because of temp.at(i) or temp[i] in loops for(int i=left;i<=right;i++) . To solve error temp.at(i-left) or temp[i-left] is to be used. Thanks to @Kevin for his suggestion and also to everyone else.