Podstawowy problem nie jest bezpośrednio związany z rozluźnionymi regułami constexpr, funkcja constexpr jest tylko stałym wyrażeniem, jeśli argumenty są wyrażeniami stałymi. W twoim drugim przypadku:
int array[std::max(1,2)];
to działa, ponieważ liczby całkowite są rzeczywiście stałymi wyrażeniami.
C++ 11 była bardziej specyficzna w tym przypadku standardowe dla Projekt C++ 11 w sekcji 5.19
[expr.const] określa się przypadki, w których sub ekspresja nie jest uważany za stały ekspresji i zawiera następujący:
prosząc o funkcji constexpr argumentów, że gdy podstawiony przez podstawienie funkcji wywołania (7.1.5) nie uzyskanie stałej ekspresji;
C++ 14 ustęp ten usunięto i mają następujące wyjątki:
jest wywołanie funkcji innej od konstruktora constexpr dla dosłownym klasy, w zależności constexpr, lub niejawne wywołanie trywialnego destruktora (12.4) [Uwaga: Rozdzielczość przeciążenia (13.3) to zastosowana w zwykły sposób -end note];
i musimy wykorzystać resztę zasad w odniesieniu do argumentów (sub-wyrażeń).
W pierwszym przypadku:
int array[std::max(a.size(), b.size()];
std::vector::size nie zaznaczono constexpr a więc podlega wyżej cytowanej wyjątku.
Należy również zauważyć, że w części 7.1.5
[dcl.constexpr] mamy następujące:
Wywołanie funkcji constexpr daje taki sam wynik jak wywołanie o podobnej funkcji w innych niż constexpr wszystkie aspekty z wyjątkiem tego, że wywołanie do funkcji constexpr może pojawić się w wyrażeniu stałym.
Przekazywanie argumentów do funkcji constexpr, które nie są wyrażeniami stałymi, oznacza po prostu, że wyrażenie nie jest dostępne dla zastosowań w kontekstach wymagających stałego wyrażenia.
Jak DYP wskazuje, że std::max
nie powstał constexpr w 11 ze względu do różnych kwestii C++ prawdopodobnie tym komisja jest konserwatywne i ograniczony czas, możemy zobaczyć niektóre z zagadnień w N3039. to zapomnienia zobaczyć N3856 który mówi:
Ten krótki dokument proponuje, aby standardowych funkcji MIN i MAX constexpr. Byli na szczycie listy motywujących przypadków dla obniżania parametrów referencyjnych dla funkcji constexpr w C++ 11. Zostali zapomniane po zmianie języka rdzeń został przyjęty
Dla odniesienia wiemy, że 1
i 2
są stałe wyrażenie z sekcji 5.19
który mówi:
Dosłowne stała wyrażenie jest prvalue rdzeń stałym wyrażeniem typu literowego, ale nie typu wskaźnika. Stałe wyrażenie całkowe jest dosłownym ciągłym wyrażeniem typu wyliczeniowego całkowego lub nieskrępowanego. [...]
'constexpr' tutaj nie oznacza, że funkcja zwraca wartość' constexpr'. Oznacza to, że funkcją jest 'constexpr'. (Podobnie jak "static int x();" nie oznacza, że 'x' zwraca statyczną int). –