2013-09-26 2 views
2

У меня есть этот пример кода:Ошибка передачи аргументов функции шаблона с константным спецификатором

#include <iostream> 
#include <memory> 

template <typename T> 
void func1(T& value) 
{ 
    std::cout << "passed 1 ..." << std::endl; 
} 

template <template <typename> class T, typename U> 
void func2(T<U>& value) 
{ 
    std::cout << "passed 2 ..." << std::endl; 
} 

int main() 
{ 
    std::auto_ptr<int> a; 
    const std::auto_ptr<int> ca; 

    // case 1: using func1 
    func1(a); // OK 
    func1(ca); // OK 

    // case 2: using func2 
    func2(a); // OK 
    func2(ca); // Compilation error 

    return 0; 
} 

В первом случае функция «FUNC1» принимает общий аргумент, независимо от классификатором, однако во втором случае функции ' func2 'не работает, когда аргумент имеет определитель констант. Почему это происходит?

Это ошибка компиляции:

make all 
Building file: ../src/Test2.cpp 
Invoking: GCC C++ Compiler 
g++ -O0 -g3 -Wall -c -fmessage-length=0 -MMD -MP -MF"src/Test2.d" -MT"src/Test2.d" -o "src/Test2.o" "../src/Test2.cpp" 
../src/Test2.cpp: In function ‘int main()’: 
../src/Test2.cpp:27: error: invalid initialization of reference of type ‘std::auto_ptr<int>&’ from expression of type ‘const std::auto_ptr<int>’ 
../src/Test2.cpp:11: error: in passing argument 1 of ‘void func2(T<U>&) [with T = std::auto_ptr, U = int]’ 
make: *** [src/Test2.o] Error 1 
+2

Сообщите, пожалуйста, точную ошибку. –

+0

Clang, OTOH, сообщает об [замещении замены] (http://coliru.stacked-crooked.com/a/4f3b5cf491634c3e). – jrok

+0

Игнорируя причину, вы можете поместить 'const' для решения проблемы:' void func2 (const T & value) '. – deepmax

ответ

1

Проблема заключается в том, что в случае func1, компилятор должен вывести T и мы получаем

  • T в первом вызове
  • std::auto_ptr<int>
  • T является const std::auto_ptr<int> при втором обращении

В обоих случаях T действителен сам по себе.

Теперь func2, компилятор должен вывести T и U, где T параметр шаблона шаблон. Что будет нужно, это:

  • T является std::auto_ptr, U в первом вызове
  • T является const std::auto_ptrint, U во втором вызове

и есть ваша проблема int: T может не должен быть const std::auto_ptr сам, поскольку он объединяет тип-свойство const с шаблоном std::auto_ptr, который не является допустимым типом.

+0

Привет, я понимаю, что вы говорите. Но в обеих функциях компилятор должен вычесть «Т», в «func1», по-видимому, можно без ограничений вычесть как «const std :: auto_ptr», однако вы говорите, что в «func2» недопустимо. На самом деле я хочу знать, относится ли эта проблема к аргументам шаблона шаблона в процессе вычитания. Спасибо – hammer

+0

@hammer Вы действительно не понимаете, что это значит. 'func1' does * not * выводит' T' в 'const std :: auto_ptr', но для' const std :: auto_ptr ', что является решающим отличием здесь. Вам нужно различать шаблон 'std :: auto_ptr' (который сам по себе не может быть объединен с' const') и тип 'std :: auto_ptr ', который основан на шаблоне и который может быть объединен с 'const '. –

+0

Теперь я вижу все это, это было объяснение, в котором я нуждался. Спасибо за все. – hammer

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