W poniższym przykładzie argumenty funkcji są używane do testowania wymaganym wyrażeniem, czy wyrażenie, które ich używa, jest poprawnie utworzone. Wymagane wyrażenie nie przyjmuje żadnych argumentów; wykorzystuje bezpośrednio zmienne w zakresie funkcji:
#include <cstddef>
#include <vector>
template<typename T>
void Resize(T &v, std::size_t const n)
{
if constexpr (requires { v.resize(n); })
v.resize(n);
}
template<typename T>
void Eziser(T &v, std::size_t const n)
{
if constexpr (requires { v.eziser(n); })
v.eziser(n);
}
int main()
{
std::vector<int> v;
Resize(v, 10u);
Eziser(v, 10u);
}
Powyższy kod kompiluje się z gałęzią pojęć Clanga. Jednak GCC10 przyjmuje tylko połączenie z Resize
. GCC9 ICE. Czy Clang ma rację, akceptując to?
c++
c++20
c++-concepts
metalfox
źródło
źródło
Resize
iEziser
powinien odrzucić) lub zarówno funkcja powinna skompilować. Powiedziałbym, że clang ma rację.Odpowiedzi:
Tak, wyrażenie wymagające może wykorzystywać wszystko, co jest w zasięgu. Trzeba tylko typ czegokolwiek niej nazwisk, mimo wszystko, z wyjątkiem w zagnieżdżonych-wymogu lub innej stałej ekspresji. Dotyczy to zarówno deklaracji otaczających, jak i własnych (formalnych) parametrów.
[expr.prim.req] / 5 :
źródło