The following is a toy example
The class student has a std::array<char, 15> called name and an integer age. A student has a member function called encode that calls a global template function encode using name.size() as a template parameter.
The code is shown below:
//main.cpp
#include <iostream>
#include <array>
template <unsigned long num1>
unsigned long encode(unsigned long num2){
return num1 + num2;
}
struct student {
std::array<char, 15> name;
int age;
student(const std::array<char, 15>& name, int age):
name(name),
age(age)
{}
unsigned long encode(){
return ::encode<name.size()>(age);
}
};
int main(){
std::array<char, 15> name = {"Tim"};
student Tim(name, 17);
std::cout << Tim.encode();
}
However, this produces the following compiler error
>g++ main.cpp -std=c++11
main.cpp: In member function 'long unsigned int student::encode()':
main.cpp:22:43: error: use of 'this' in a constant expression
22 | return ::encode<name.size()>(age);
| ^
main.cpp:22:45: error: no matching function for call to 'encode<((student*)this)->student::name.std::array<char, 15>::size()>(int&)'
22 | return ::encode<name.size()>(age);
| ~~~~~~~~~~~~~~~~~~~~~^~~~~
main.cpp:9:15: note: candidate: 'template<long unsigned int num1> long unsigned int encode(long unsigned int)'
9 | unsigned long encode(unsigned long num2){
| ^~~~~~
main.cpp:9:15: note: template argument deduction/substitution failed:
main.cpp:22:45: error: use of 'this' in a constant expression
22 | return ::encode<name.size()>(age);
| ~~~~~~~~~~~~~~~~~~~~~^~~~~
main.cpp:22:42: note: in template argument for type 'long unsigned int'
22 | return ::encode<name.size()>(age);
Is it required I do ::encode<15>(age) to solve this problem, because I thought one of the major benefits of a std::array is being able to carry a size rather than having to store the size in some extra variable (or hardcoding the size).
g++ version: 14.1.0
std::string(unless you are on firmware and can't use dynamic memory allocation)