29 std::vector<unsigned> numbers(input_numbers);
30 std::sort(numbers.begin(), numbers.end());
31 unsigned end_number=numbers.back();
32 if(numbers.front()==end_number)
33 return std::to_string(end_number);
35 std::stringstream number_range;
37 auto start_number = numbers.front();
39 for(std::vector<unsigned>::const_iterator it = numbers.begin();
43 const auto number = *it;
44 const auto next = std::next(it);
47 if(next != numbers.end() && *next <= number + 1)
51 if(start_number != numbers.front())
54 if(number == start_number)
56 number_range << number;
58 else if(number == start_number + 1)
60 number_range << start_number <<
',' << number;
64 number_range << start_number <<
'-' << number;
67 if(next != numbers.end())
72 return number_range.str();
77 const std::string &number_range,
78 std::vector<unsigned> &numbers,
79 bool last_number_is_set,
82 if(!last_number_is_set && is_range)
85 "unterminated number range '" + std::to_string(*(++numbers.rbegin())) +
89 if(!last_number_is_set)
92 "invalid number range '" + number_range +
"'");
97 unsigned end_range = numbers.back();
99 unsigned begin_range = numbers.back();
101 if(begin_range > end_range)
104 "lower bound must not be larger than upper bound '" +
105 std::to_string(begin_range) +
"-" + std::to_string(end_range) +
"'");
107 for(
unsigned i = begin_range; i < end_range; ++i)
108 numbers.push_back(i);
111 numbers.push_back(end_range);
117 std::vector<unsigned> numbers(1, 0);
118 bool last_number_is_set =
false;
119 bool is_range =
false;
121 for(
char c : number_range)
123 if(
'0' <= c && c <=
'9')
125 numbers.back() *= 10;
126 numbers.back() += c -
'0';
127 last_number_is_set =
true;
131 append_numbers(number_range, numbers, last_number_is_set, is_range);
133 numbers.push_back(0);
134 last_number_is_set =
false;
139 if(!last_number_is_set)
142 "lower bound missing in number range '" + number_range +
"'");
144 numbers.push_back(0);
145 last_number_is_set =
false;
151 std::string(
"character '") + c +
"' not allowed in number range");
154 append_numbers(number_range, numbers, last_number_is_set, is_range);
Thrown when failing to deserialize a value from some low level format, like JSON or raw bytes.
#define PRECONDITION(CONDITION)
#define POSTCONDITION(CONDITION)