Search code examples
c++constexprstatic-assert

Can state be maintained across static asserts?


Came across this need a while back and was forced to work around it. I'm wondering if there is a way to carry state across a compile time check.

So for example a motivating example would be how to set up counter so that you can do something like:

static_assert(foo() == 0, "..");
static_assert(foo() == 1, "..");
static_assert(foo() == 2, "..");

Where each subsequent call increased the result by 1. I'm specifically interested in accomplishing this at compile time. I've tried setting up foo as a constexpr with an internal counter but then hit read-only constraints. I would like to know whether something along these lines is possible with the current C++ standard.

int main() {

    static constexpr int counter = 0; 
    struct test
    {
        constexpr int foo(){return counter++;}
    };

    test myTest;

    static_assert(myTest.foo() == 0, "failed");
    static_assert(myTest.foo() == 1, "failed");

    return 0;
}

Solution

  • This is not feasible at compile time:

    1. Objects such as myTest are instantiated at runtime.
    2. Objects might be passed by reference or value to functions. When compiling the function, the compiler can't know for sure which was the original object it is referd to.
    3. If your state would be object independent, and if it would be feasible at compile time, the state would depend on the order of encounter of status inquiry in each separately compiled unit, and not on the execution flow (e.g. would the state be referred to in a loop, it would have only one constant value throughout the loop, regardless if there are 1 or 1000 iterations).

    But it's easy at runtime, with normal variables and asserts.