I have just tried to test how the compiler behaves with template in multi files. In each .cpp file, I defined a class template with the same name but a bit different implementation. See the files below:
- test.h
#include <iostream>
//#define FROM_MAIN_CPP //for choosing main() from which .cpp file
- NOT_main.cpp
#include "test.h"
//template definition
template <typename T> class cls {
public:
T prop;
cls(T _val) : prop(_val) {
std::cout << "from NOT_main.cpp\n";
}
};
//template instantiation
template class cls<int>;
extern template class cls<float>; //expect definition in main
//testing...
#ifndef FROM_MAIN_CPP
int main(void) {
cls<int> int_obj(19);
cls<float> float_obj(1.9f); //expect definition in main
}
#endif
- main.cpp
#include "test.h"
//template definition
template <typename T> class cls {
public:
T prop;
cls(T _val) : prop(_val) {
std::cout << "from main.cpp\n";
}
};
//template instantiation
extern template class cls<int>; //expect definition in NOT_main
template class cls<float>;
//testing...
#ifdef FROM_MAIN_CPP
int main(void) {
cls<int> int_obj(19); //expect definition in NOT_main
cls<float> float_obj(1.9f);
}
#endif
Now I try to compile with the main() functions in each .cpp file. See my test here: https://drive.google.com/drive/folders/1AmSZCSVZhJwNP8AxJ0saYeLZANWeX6v2?usp=sharing
I know the extern
keyword helps the compiler prevent multi instantiations in translation units. I expected when I explicitly instantiated the template defined in first file, then used the declaration with extern
in other ones, so the template definition used should be the definition in the first.
In detail, with the main() in NOT_main.cpp, it behaved as I expected. But with the main() in main.cpp, why did the compiler choose template defined in main.cpp despite using extern
.
It would be appreciated if you could point out what's wrong in my understanding. Thanks and regards.