3

I have a problem with generics in c++.I have two Matrix.h and Matrix.cpp files.Here is files:

#pragma once
template<class T>
class Matrix
{
    public:
        static T** addSub(int size,T** firstMatrix,T** secondMatrix,int operation);
}

and Matrix.cpp

#include "Martix.h"
template<class T>
static T** Matrix<T>::addSub( int n,T **firstMatrix,T **secondMatrix,int operation)
{
    //variable for saving result operation
    T **result = new T*[n];

    //create result matrix
    for( int i=0;i<n;i++)
        result[i] = new T[n];

    //calculate result
    for( int i=0;i<n;i++)
        for(int j=0;j<n;j++)
            result[i][j] = 
            (operation == 1) ? firstMatrix[i][j] + secondMatrix[i][j]:
                                firstMatrix[i][j] - secondMatrix[i][j];

    return result;
}

when I run these I get the below error:

Error   1   error LNK2019: unresolved external symbol "public: static int * * __cdecl Matrix<int>::addSub(int,int * *,int * *,int)" (?addSub@?$Matrix@H@@SAPAPAHHPAPAH0H@Z) referenced in function "public: static int * * __cdecl Matrix<int>::strassenMultiply(int,int * *,int * *)" (?strassenMultiply@?$Matrix@H@@SAPAPAHHPAPAH0@Z) C:\Users\ba.mehrabi\Desktop\Matrix\matrixMultiplication\main.obj    matrixMultiplication

what is the problem?

Babak Mehrabi
  • 2,155
  • 4
  • 23
  • 24
  • Do you have template method definition in the same compilation unit as declaration? – Simone Sep 12 '11 at 16:20
  • 2
    http://stackoverflow.com/questions/488959/how-do-you-create-a-static-template-member-function-that-performs-actions-on-a-te – Patrick Sep 12 '11 at 16:20
  • You misspelt the name of the include file. I wonder if you're giving us your real code here, or if you're just writing down some fiction from memory... Also, C++ doesn't have "generics"; if you come from a Java background, it'd probably be worth your while to accustom yourself with the common C++ idioms, which are quite different. For example, you should rarely or never say `new` in C++. – Kerrek SB Sep 12 '11 at 16:22

3 Answers3

5

Unfortunately, you can't have the declaration of a template class in the *.cpp files. The full definition has to stay in the header file. This is a rule of many C++ compilers.

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

  1. A template is not a class or a function. A template is a "pattern" that the compiler uses to generate a family of classes or functions.
  2. In order for the compiler to generate the code, it must see both the template definition (not just declaration) and the specific types/whatever used to "fill in" the template. For example, if you're trying to use a Foo, the compiler must see both the Foo template and the fact that you're trying to make a specific Foo.
  3. Your compiler probably doesn't remember the details of one .cpp file while it is compiling another .cpp file. It could, but most do not and if you are reading this FAQ, it almost definitely does not. BTW this is called the "separate compilation model."

The link has a workaround, but keep in mind that a template is a glorified macro so the header file is probably the best place for it.

The poster of this SO post shows a demonstration of the workaround.

Community
  • 1
  • 1
Jordan Parmer
  • 36,042
  • 30
  • 97
  • 119
1

First of all, the definition of functions of a class template, should go in the header itself.

Second, if you define the static member function out of class (though in the header itself), then don't use the static keyword (in the definition). It only needed in the declaration only.

Nawaz
  • 353,942
  • 115
  • 666
  • 851
0

Add

template Matrix<int>;

at the end of your cpp file and it will work. But you need to learn a few things about templates, otherwise you'll have to deal with lots of issues you don't understand.

Benoît
  • 16,798
  • 8
  • 46
  • 66