2015-07-31 2 views
3

У меня есть класс, который я пишу, который будет использовать особый тип для одного из его конструкторов, который может быть любого типа, который соответствует моим требованиям. Я столкнулся с проблемой, что этот шаблонный конструктор заставляет мою копию и перемещать конструкторы в незаконные перегрузки!Перегруженный конструктор незаконный с перемещением и копией

Мой класс изложил так:

template<typename ... Types> 
class myclass{ 
    public: 
     myclass(const myclass &other){/* copy constructor */} 
     myclass(myclass &&other){/* move constructor */} 

     template<typename Special> 
     myclass(Special &&arg){/* stops copy/move implementations */} 
} 

Как я могу обойти это ограничение?

+1

Я думаю, вы имеете в виду, что 'mycla ss (Special && arg) 'предпочтительнее для конструктора копирования для аргумента non-const lvalue? –

+0

@PiotrSkotnicki yeahp, я делаю – CoffeeandCode

ответ

5

Ограничить это.

template<typename Special, 
     std::enable_if_t<!std::is_same<std::decay_t<Special>, myclass>{}, int> = 0 > 
myclass(Special &&arg) { /* ... */ } 

В зависимости от конкретного случая использования, вы можете также ограничить Special дальше только типы, которые соответствуют вашим требованиям.

+0

Я понятия не имею, почему я просто случайно забыл о SFINAE. Я буду принимать это как ответ – CoffeeandCode

0

Этот пример показывает различные случаи:

const myclass c1(42);  // special: int 
myclass c2(c1);   // copy 
myclass c3(c2);   // special: myclass& (non const) 
myclass c4(std::move(c3)); // move 

Live Demo

ваша копия/перемещение Конструкторы по-прежнему правовые перегрузками, но не сопзЬ л значение имеет точное соответствие с вашим шаблоном конструктора.

Вы можете:

  • использование SFINAE запретить myclass& в шаблоне (например, в ответ у TC)
  • обеспечивают перегрузку, (с точным соответствием):

    myclass(myclass &other) : myclass(static_cast<const myclass &>(other)) {} 
    

    Demo

+0

Это похоже на комментарий, отличный от ответа – CoffeeandCode

+0

@CoffeeandCode: Я писал свой ответ небольшими частями. – Jarod42

+0

Это не будет обрабатывать 'myclass c5 (std :: move (c1));'. –

Смежные вопросы