Thursday, September 23, 2021

Careful with that initializer

Initializer

 The other day I used some test coding and created a vector with some points like the following:


std::vector<Point> vecPoint{10};

 Unfortunately this didn't created a std::vector of 10 points. Instead this was intepreted as an initializer_list since the point class had a possiblity to be created from one argument. The code was somewhat similar to this one (but templated):


struct Point
{
   Point (int x = 0, int y = 0);
};

 The Point class was adjusted but the problem is also with std::vector. The ambiguity can easily be solved by introducing a jumper class as size argument:


struct Size
{
   Size(size_t n)
};

Size operator ""_sz(size_t n)
{
   return Size{n};
}

template<class T, class Allocator = std::allocator<T>>
class vector
{
public:
	vector(Size n);
};

 There is no ambiguity now:


void f()
{
  std::vector<Point> vec1{10_sz};  // 10 default points
  std::vector<Point> vec2{10};     // initialized with one point
}

Careful with std::ranges

<ranges>   C++20 has added the the ranges library. Basically it works on ranges instead of iterators but added some subtle constraint...