Как вызвать шаблонный метод? - PullRequest
6 голосов
/ 24 ноября 2010

Есть много онлайн-документов, объясняющих, как писать шаблонные методы, но не так много примеров того, как их вызывать, как использовать их в коде.

У меня есть такой шаблонный метод: VectorConvertor.h

template <class T>
static void AppendToVector(std::vector<T> & VectorToBeAppended,
                           std::vector<T> & VectorToAppend);

VectorConvertor.cpp

template <class T>
void VectorConvertor::AppendToVector(std::vector<T> & VectorToBeAppended,
                                     std::vector<T> & VectorToAppend)
{
    for (std::vector::size_type i=0; i<VectorToAppend.size(); i++)
    {
        VectorToBeAppended.push_back(VectorToAppend.at(i));
    }
}

Попытка использования в коде:

std::vector<uint8_t> InputData, OutputData;
// ...
VectorConvertor::AppendToVector(OutputData, InputData);

Я скомпилировал этот код без ошибок.Но когда я пытаюсь использовать этот метод, я получаю следующие ошибки:

ошибка LNK1120: 1 неразрешенные внешние данные

и

ошибка LNK2019: неразрешенный внешний символ "public: static void __cdecl VectorConvertor :: AppendToVector (класс std :: vector> &, класс std :: vector> &)" (?? $ AppendToVector @ E @ VectorConvertor @@ SAXAEAV? $ vector @ EV?$ allocator @ E @ std @@@ std @@ 0 @ Z) ссылка на функцию "public: staticclass std :: vector> __cdecl Utf8 :: WStringToUtf8 (класс std :: basic_string, класс std :: allocator>)" (?WStringToUtf8 @ utf8 @@ SA? AV? $ вектор @ EV? $ распределитель @ E @ станд @@@ станд @@ V? $ basic_string @ _WU? $ char_traits @ _W @ станд @@ V? $ распределитель @ _W @ 2 @@ 3 @@ Z) * ​​1027 *

Когда я не использую этот метод в своем коде, я не получаю никаких сообщений об ошибках.Что я делаю не так во время звонка?Я что-то упустил?

Я использую Visual Studio 2010 Express Edition.

Ответы [ 5 ]

7 голосов
/ 24 ноября 2010

В C ++ нельзя использовать определение в файле .cpp при использовании шаблонов.Вам нужно поместить определение в заголовочный файл.См .:

http://www.parashift.com/c++-faq-lite/templates.html#faq-35.12

5 голосов
/ 24 ноября 2010

Вам нужно поместить тело функции в заголовочный файл. См. этот FAQ .

2 голосов
/ 24 ноября 2010

Связывание шаблонов может стать хитрым.Но самое простое решение обычно:

Поместите все определения шаблонов в заголовочные файлы.

В этом случае вам следует переместить содержимое VectorConverter.cpp в VectorConverter.h(или возможно #include "VectorConverter.cpp" внизу VectorConverter.h).

0 голосов
/ 18 августа 2017

Ошибки из-за попытки записать определение метода шаблона в файле CPP.Чтобы сократить время компоновки, правило записывать реализацию (определение) встроенных и шаблонных методов в заголовочный файл.Приведенный ниже код является правильным способом объявления и определения метода шаблона.

VectorConvertor.h

class VectorConvertor
{
    public:
        template <class T>
        static void AppendToVector1(        std::vector<T> & VectorToBeAppended,
                                    const   std::vector<T> & VectorToAppend);

        template <class T>
        static void AppendToVector2(        std::vector<T> & VectorToBeAppended,
                                    const   std::vector<T> & VectorToAppend);

        template <class T>
        static void AppendToVector3(        std::vector<T> & VectorToBeAppended,
                                    const   std::vector<T> & VectorToAppend);


}

template <class T>
void VectorConvertor::AppendToVector1(          std::vector<T> & VectorToBeAppended,
                                        const   std::vector<T> & VectorToAppend)
{
    VectorToBeAppended.reserve(VectorToBeAppended.size() + VectorToAppend.size());
    for (std::vector<T>::size_type i=0; i<VectorToAppend.size(); i++)
    {
        VectorToBeAppended.push_back(VectorToAppend[i]);
    }
}

template <class T>
void VectorConvertor::AppendToVector2(          std::vector<T> & VectorToBeAppended,
                                        const   std::vector<T> & VectorToAppend)
{
    VectorToBeAppended.reserve(VectorToBeAppended.size() + VectorToAppend.size());
    for (std::vector<T>::const_iterator cit=VectorToAppend.cbegin(); cit!=VectorToAppend.cend(); ++cit)
    {
        VectorToBeAppended.push_back(*cit);
    }
}

template <class T>
void VectorConvertor::AppendToVector3(          std::vector<T> & VectorToBeAppended,
                                        const   std::vector<T> & VectorToAppend)
{
    VectorToBeAppended.insert(VectorToBeAppended.end(), VectorToAppend.cbegin(), VectorToAppend.cend());
}

VectorConvertor.cpp

// Nothing to write in the CPP file.

И вот как это использовать в коде:

std::vector<uint8_t> InputData, OutputData;
// ...
VectorConvertor::AppendToVector3(OutputData, InputData);
0 голосов
/ 24 ноября 2010

Помимо размещения определения функции шаблона в заголовке или включения исходного файла (файл cpp), вы можете явно создать экземпляр своей функции для любых типов, которые вам нужны.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...