1

I'm trying to throw an exception in my code if a vector that is created from user input is not sorted in either descending or ascending order.

using namespace std;
#include <iostream>
#include <vector>
#include <algorithm>

int main () {
vector <int> vec;

//Let user fill a vector with 12 integers.
//cout << "Please note that input data should be either increasing or decreasing." << endl;
int n = 0;
int size = 0;
while(size < 12) {
    cout << "Type integer to add to the vector." << endl;
    cin >> n;
    vec.push_back(n);
    ++size;
}

//throw exception if unsorted
try {
    if (!((is_sorted(vec.begin(), vec.end())) || (is_sorted(vec.end(), vec.begin())))) {
        throw "Input was not sorted.";
    }
}
catch(exception &error){
    cerr << "Error: " << error.what() << endl;
}

}

I have not included the rest of the code, which searches for a particular number, because I am pretty sure that it is irrelevant to this issue. When the data filled into the vector is ascending or descending, everything is fine, but when I test the exception, I get, "terminate called after throwing an instance of 'char const*' Aborted" instead of my desired error message. I don't understand what is going on here. Is it something wrong with the way I'm handling exceptions or am I using the sort() function incorrectly?

AdamK
  • 389
  • 1
  • 4
  • 12
  • 1
    If you swap `begin()` and `end()`, you don't get an interval that goes backwards, you get an empty interval. You want to use `rbegin()` and `rend()` instead. – n. m. could be an AI Jul 12 '17 at 04:40
  • There is no sense to throw and catch an exception in the same block. You should use a simple 'if' instead. – Mattia72 Jul 12 '17 at 04:44
  • Wow, so many parentheses! You can remove the ones around the calls to `is_sorted` -- they're redundant. And you can get rid of the outermost pair in the expression inside the `if` statement by applying De Morgan's theorem: `!(A || B)` is equivalent to `!A && !B`. – Pete Becker Jul 12 '17 at 12:25
  • @n.m. -- it's worse than that. Trying to use the sequence `[end(), begin())` produces undefined behavior because the second iterator is not reachable from the first. – Pete Becker Jul 12 '17 at 12:27
  • @Mattia72 -- maybe, but this is **supposed to be** a minimal example **that shows the problem**. And it does exactly that. – Pete Becker Jul 12 '17 at 12:29

3 Answers3

2

In C++, all types are throwable and catchable, but you are only catching subclasses of std::exception.

The best fix to your code would be changing your throw statement to:

throw std::runtime_error("Input was not sorted.");
0

You're throwing a const char* not an std::exception. So catch it as a const char*:

  catch(const char* error) {
    std::cout << "Error: " << error << "\n";
  }

Or throw an std::exception.

Remember that you can throw many types and have many catch blocks, the one that will be invoked is the one that matches the type of the thrown exception.

A.S.H
  • 29,101
  • 5
  • 23
  • 50
0

If you want to catch an exception, you should throw an exception, not a const char*. See this answer: c++ exception : throwing std::string

Mattia72
  • 825
  • 1
  • 8
  • 23