title: Reason for range for and decomposition not allowing constexpr
body: <p>I wanted to do a couple of sanity tests for a pair of convenience functions that split a 64-bit integer in two 32-bit integers, or do the reverse. The intent is that you don't do the bit shifts and logic ops all over again with the potential of a typo somewhere. The sanity tests were supposed to make 100% sure that the pair of functions, although pretty trivial, <em>indeed</em> works as intended.</p>
  
  <p>Nothing fancy, really... so as the first thing I added this:</p>
  
  <pre><code>static constexpr auto joinsplit(uint64_t h) noexcept { auto [a,b] = split(h); return join(a,b); }
  static_assert(joinsplit(0x1234) == 0x1234);
  </code></pre>
  
  <p>... which works perfectly well, but is less "exhaustive" than I'd like. Of course I can follow up with another 5 or 6 tests with different patterns, copy-paste to the rescue. But seriously... wouldn't it be nice to have the compiler check a dozen or so values, within a pretty little function? No copy-paste? Now that would be cool.</p>
  
  <p>With a recursive variadic template, this can be done (and it's what I'm using in lack of something better), but it's in my opinion needlessly ugly.</p>
  
  <p>Given the power of <code>constexpr</code> functions and range-based <code>for</code>, wouldn't it be cool to have something nice and readable like:</p>
  
  <pre><code>    constexpr bool test()
      {
          for(constexpr auto value : {1,2,3}) // other numbers of course
          {
              constexpr auto [a,b] = split(value);
              static_assert(value == join(a,b));
          }
          return true; // never used
      }
      static_assert(test()); // invoke test
  </code></pre>
  
  <p>A big plus of this solution would be that in addtion to being much more readable, it would be obvious from the failing <code>static_assert</code> not just that the test <em>failed in general</em>, but also the exact value for which it failed.</p>
  
  <p>This, however, doesn't work for two reasons:</p>
  
  <ol>
  <li>You cannot declare <code>value</code> as <code>constexpr</code> because, as stated by the compiler: <em>"The value of <code>__for_begin</code> is not usable in a constant expression"</em>. The reason for that is also explained by the compiler: <em>"note: <code>__for_begin</code> was not declared <code>constexpr</code>"</em>. Fair enough, <em>that is a reason</em>, silly as it may be.</li>
  <li>Decomposition declaration cannot be declared <code>constexpr</code> (which is promptly followed by a non-constexpr condition for <code>static_assert</code> error).</li>
  </ol>
  
  <p>In both cases, I wonder if there is truly a hindrance to allowing these being <code>constexpr</code>. I understand why it doesn't work (see above!), but the interesting question is <em>why is it like that?</em></p>
  
  <p>I acknowledge that declaring <code>value</code> as <code>constexpr</code> is a lie to begin with since its value obviously is not constant (it's different in each iteration). On the other hand, any value that it ever takes is from a compiletime constant set of values, yet without the <code>constexpr</code> keyword the compiler refuses to treat it as such, i.e. the result of <code>split</code> is non-<code>constexpr</code> and not usable with <code>static_assert</code> although it really is, by all means.<br>
  OK, well... I'm probably really asking too much if I want to declare something that has a changing value as constant. Even though from some point of view, if <em>it is</em> constant, in each iteration's scope. Somehow... is the language missing a concept here?</p>
  
  <p>I acknowledge that range-based <code>for</code> is, like lambdas, really just a hack that mostly works, and mostly works invisibly, not a true language feature -- the mention of <code>__for_begin</code> is a dead giveaway on its implementation. I also acknowledge that it's generally tricky (forbidding) to allow the counter in a normal <code>for</code> loop being <code>constexpr</code>, not only because it's not constant, but because you can in principle have any kind of expressions in there, and it <em>truly</em> cannot be easily told in advance what values in general will be generated (not with reasonable effort during compiletime, anyway).<br>
  On the other hand, given an exact finite sequence of literals (which is as compiletime-constant as it can get), the compiler should be able to do a number of iterations, each iteration of the loop with a different, compiletime-constant value (unroll the loop if you will). Somehow, in a readable (non-recursive-template) manner, such thing should be possible?
  Am I asking too much there?</p>
  
  <p>I acknowledge that a decomposition declaration is not an altogether "trivial" thing. It might for example require calling <code>get</code> on a tuple, which is a class template (that could in principle be anything). But, whatever, <code>get</code> happens to be <code>constexpr</code> (so that's no excuse), and also in my concrete example, an anonymous temporary of an anonymous struct with two members is returned, so public direct member binding (to a <code>constexpr</code> <code>struct</code>) is used.<br>
  Ironically, the compiler even <em>does exactly the right thing</em> in the first example, too (and with recursive templates as well). So apparently, it's quite possible. Only just, for some reason, not in the second example.<br>
  Again, am I asking too much here?</p>
  
  <p>The likely correct answer will be "The standard doesn't provide that".</p>
  
  <p>Apart from that, are there any true, technical reasons why this cannot, could not, or <em>should not</em> work? Is that an oversight, an implementation deficiency, or intentionally forbidden?</p>