Ihr Code wird nicht kompiliert, weil eine if
-Anweisung ein Laufzeitkonstrukt ist. Betrachten Sie diesen Code:
int foo(bool b)
{
if (b)
{
// attempt to call a function that does not exist
function_that_does_not_exist();
}
else
{
return 1;
}
}
Sie mir den ganzen Tag darüber reden können, wie b
ist immerfalse
, aber der Compiler erfordert immer noch den Code in das true
Fall des if
Block zu kompilieren. Was ist in Ihrem Beispiel für so etwas wie ein int
geschieht, ist dies:
template<>
void config::readConfig(char* setting, char* subsetting, int& status) {
char temp[255];
if (!GetPrivateProfileStringA(setting, subsetting, nullptr, temp, 255, cfg)) {
error = true;
}
// if (std::is_same<size, char [4]>::value) {
if (false) {
sprintf_s(status, "%s", temp);
} else { status = atof(temp); }
}
Der Compiler weiß nicht, wie sprintf_s
Kompilierung zu machen, wenn status
ein int
ist.
Die Lösung ist eine Überlastung zu verwenden:
template<class size>
void config::readConfig(char * setting, char * subsetting, size & status) {
char temp[255];
if (!GetPrivateProfileStringA(setting, subsetting, nullptr, temp, 255, cfg)) {
error = true;
}
status = atof(temp);
}
template<size_t N>
void config::readConfig(char* setting, char* subsetting, char (&status)[N]) {
char temp[255];
if (!GetPrivateProfileStringA(setting, subsetting, nullptr, temp, 255, cfg)) {
error = true;
}
sprintf_s(status, "%s", temp);
}
Das Ding Sie suchen ist in der Regel als static_if
(ähnlich dem D bedingte Kompilierung Konstrukt einer "Static If Condition") bezeichnet. Es gibt keine Unterstützung in C++ 17 und es ist (noch) nicht für C++ 2a geplant, aber Sie können es leicht mit der Antwort auf this question emulieren.
#include <type_traits>
template <typename T, typename F>
auto static_if(std::true_type, T t, F f) { return t; }
template <typename T, typename F>
auto static_if(std::false_type, T t, F f) { return f; }
template <bool B, typename T, typename F>
auto static_if(T t, F f) { return static_if(std::integral_constant<bool, B>{}, t, f); }
template <class size>
void config::readConfig(char* setting, char* subsetting, size& status)
{
char temp[255];
if (!GetPrivateProfileStringA(setting, subsetting, nullptr, temp, 255, cfg))
{
error = true;
}
static_if<std::is_same<size, char [4]>::value>
(
[&] (auto& status) { sprintf_s(status, "%s", temp); },
[&] (auto& status) { status = atof(temp); }
)(status);
}
Versuchen Sie, wann immer Sie können, mit 'std :: string' zu steuern. Bare, veränderbare Zeichenpuffer sind nichts als Ärger. – tadman
Anstatt eine Template-Funktion zu verwenden, warum bieten Sie nicht eine Implementierung für 'float' und eine für' int' an? – tadman
Ich versuche mich selbst herauszufordern, die Menge an Code so gering wie möglich zu halten. Warum verdoppeln Sie die Menge an Code, wenn ich einen Scheck einreichen kann? Ich würde std :: string verwenden, aber ich lande am gleichen Fehler in der is_same-Prüfung –