const vec operator + (const vec & a) {
Эта перегрузка возвращает const vec
. Не vec
. Это важно.
v1 + v2 + temp;
Первый оператор сложения, таким образом, возвращает const vec
. Второй оператор сложения попытается добавить const vec
к vec
. Однако перегрузка не является методом класса const
, поэтому ее нельзя вызывать для объекта const
(это не является технически точным объяснением на 100%, см. Ниже, но его легче понять в этом примере).
Просто измените перегрузку следующим образом:
const vec operator + (const vec & a) const {
Так и должно быть, поскольку в this
ничего не изменяется. Есть и другие причины, по которым эта перегрузка должна быть методом класса const
;легче понять, почему в этом случае, учитывая тот факт, что const vec
возвращается. Вы также можете объявить эту перегрузку как возвращаемую vec
вместо const vec
, но это не материальная проблема (по другой причине произойдет та же ошибка компиляции).
Когда дело доходит до объявленияПерегрузки операторов, применяется следующее правило: если перегруженный оператор ничего не изменяет в this
, вы должны объявить его как const
метод класса.