Если заявление не в состоянии оценить условие - PullRequest
0 голосов
/ 12 января 2019

У меня есть базовый класс, который содержит два перечислителя, один для ввода и один для вывода. Он имеет две функции-члена, которые являются статическими. Первая функция - это просто статическая функция, которая возвращает значение на основе ввода. Он вызовет вторую функцию, которая является шаблоном функции constexpr, который будет возвращать значения constexpr. Вы можете увидеть полный класс здесь.

class Foo {
public:
    enum Input {
        INPUT_0 = 0,
        INPUT_1,
        INPUT_2
    };

    enum Output {
        OUTPUT_0 = 123,
        OUTPUT_1 = 234,
        OUTPUT_2 = 345
    };

    static uint16_t update( uint8_t input ) {
        if ( static_cast<int>(input) == INPUT_0 )
            return updater<INPUT_0>();
        if ( static_cast<int>(input) == INPUT_1 )
            return updater<INPUT_1>();
        if ( static_cast<int>(input) == INPUT_2 )
            return updater<INPUT_2>();

        return updater<INPUT_0>();
    }

    template<const uint8_t In>
    static constexpr uint16_t updater() {

        if constexpr( In == INPUT_0 ) {
            std::cout << "Output updated to: " << OUTPUT_0 << '\n';
            return OUTPUT_0;
        }

        if constexpr( In == INPUT_1 ) {
            std::cout << "Output updated to: " << OUTPUT_1 << '\n';
            return OUTPUT_1;
        }

        if constexpr( In == INPUT_2 ) {
            std::cout << "Output updated to: " << OUTPUT_2 << '\n';
            return OUTPUT_2;
        }
    }
};

Если я использую сам шаблон функции как таковой, когда значения известны во время компиляции:

#include <iostream>

int main() {
    auto output0 = Foo::updater<Foo::INPUT_0>();
    auto output1 = Foo::updater<Foo::INPUT_1>();
    auto output2 = Foo::updater<Foo::INPUT_2>();

    std::cout << "\n--------------------------------\n";
    std::cout << "Output0: " << output0 << '\n'
              << "Output1: " << output1 << '\n'
              << "Output2: " << output2 << '\n';    

    return 0;
}

Я получаю правильный вывод:

-Output-

Output updated to: 123
Output updated to: 234
Output updated to: 345

---------------------------------
Output0: 123
Output1: 234
Output2: 345

Однако, когда я пытаюсь использовать функцию-член non constexpr, когда значения определяются во время выполнения, по той или иной причине функция non constexpr не может выполнить код внутри операторов if.

#include <iostream>

int main() {
    uint8_t input;
    std::cout << "Please enter input value [0,2]\n";
    std::cin >> input;

    auto output = Foo::update( input );

    std::cout << "Output: " << output << '\n';

    return 0;        
}

Независимо от того, какое значение я ввожу с клавиатуры, 0, 1 или 2, он не может выполнить код в Foo::update()'s операторах if. Всегда печатается значение 123.

Если это поможет; Я использую Visual Studio 2017 CE v15.9.4 и собираю его с языком, установленным на ISO C++ Latest Draft Standard (/std:c++latest).

Я не знаю, почему этот код не может оценить if statements в true и вызывает код в своей области видимости.

1 Ответ

0 голосов
/ 12 января 2019

input получает char, поэтому ему будет присвоено значение ASCII введенного символа. Например. ввод 2 установит input на 50.

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

...