template<typename T, typename U> struct same;
template<typename T> struct same<T, T> { ~same(); };
struct Empty {};
struct A {
int a;
};
namespace NonPublicMembers {
struct NonPublic1 {
protected:
int a; };
struct NonPublic2 {
private:
int a; };
struct NonPublic3 : private A {};
struct NonPublic4 : NonPublic2 {};
void test() {
auto [a1] = NonPublic1(); auto [a2] = NonPublic2(); auto [a3] = NonPublic3(); auto [a4] = NonPublic4(); }
}
namespace AnonymousMember {
struct Struct {
struct { int i;
};
};
struct Union {
union { int i;
};
};
void test() {
auto [a1] = Struct(); auto [a2] = Union(); }
}
namespace MultipleClasses {
struct B : A {
int a;
};
struct C { int a; };
struct D : A, C {};
struct E : virtual A {};
struct F : A, E {};
struct G : virtual A {};
struct H : E, G {};
struct I { int i; };
struct J : I {};
struct K : I, virtual J {};
struct L : virtual J {};
struct M : virtual J, L {};
void test() {
auto [b] = B(); auto [d] = D(); auto [e] = E();
auto [f] = F(); auto [h] = H(); auto [k] = K(); auto [m] = M();
same<decltype(m), int>();
}
}
namespace BindingTypes {
struct A {
int i = 0;
int &r = i;
const float f = i;
mutable volatile int mvi;
};
void e() {
auto [i,r,f,mvi] = A();
same<decltype(i), int>();
same<decltype(r), int&>();
same<decltype(f), const float>();
same<decltype(mvi), volatile int>();
same<decltype((i)), int&>();
same<decltype((r)), int&>();
same<decltype((f)), const float&>();
same<decltype((mvi)), volatile int&>();
}
void f() {
auto &&[i,r,f,mvi] = A();
same<decltype(i), int>();
same<decltype(r), int&>();
same<decltype(f), const float>();
same<decltype(mvi), volatile int>();
same<decltype((i)), int&>();
same<decltype((r)), int&>();
same<decltype((f)), const float&>();
same<decltype((mvi)), volatile int&>();
}
void g() {
const auto [i,r,f,mvi] = A();
same<decltype(i), const int>();
same<decltype(r), int&>();
same<decltype(f), const float>();
same<decltype(mvi), volatile int>();
same<decltype((i)), const int&>();
same<decltype((r)), int&>();
same<decltype((f)), const float&>();
same<decltype((mvi)), volatile int&>(); }
void h() {
typedef const A CA;
auto &[i,r,f,mvi] = CA();
same<decltype(i), const int>(); same<decltype(r), int&>();
same<decltype(f), const float>();
same<decltype(mvi), volatile int>();
same<decltype((i)), const int&>(); same<decltype((r)), int&>();
same<decltype((f)), const float&>();
same<decltype((mvi)), volatile int&>(); }
struct B {
mutable int i;
};
void mut() {
auto [i] = B();
const auto [ci] = B();
volatile auto [vi] = B();
same<decltype(i), int>();
same<decltype(ci), int>();
same<decltype(vi), volatile int>();
}
}
namespace Bitfield {
struct S { unsigned long long x : 4, y : 32; int z; }; int f(S s) {
auto [a, b, c] = s;
unsigned long long &ra = a; unsigned long long &rb = b; int &rc = c;
same<decltype(a), unsigned long long>();
same<decltype(b), unsigned long long>();
same<decltype((a)), unsigned long long&>();
same<decltype((b)), unsigned long long&>();
same<decltype(+a), int>();
same<decltype(+b), unsigned int>();
return rc;
}
}
namespace Constexpr {
struct Q { int a, b; constexpr Q() : a(1), b(2) {} };
constexpr Q q;
auto &[qa, qb] = q;
static_assert(&qa == &q.a && &qb == &q.b);
static_assert(qa == 1 && qb == 2);
}
namespace std_example {
struct S { int x1 : 2; volatile double y1; };
S f();
const auto [x, y] = f();
same<decltype((x)), const int&> same1;
same<decltype((y)), const volatile double&> same2;
}
namespace p0969r0 {
struct A {
int x;
int y;
};
struct B : private A { void test_member() {
auto &[x, y] = *this;
}
friend void test_friend(B);
};
void test_friend(B b) {
auto &[x, y] = b;
}
void test_external(B b) {
auto &[x, y] = b; }
struct C {
int x;
protected:
int y; void test_member() {
auto &[x, y] = *this;
}
friend void test_friend(struct D);
};
struct D : C {
static void test_member(D d, C c) {
auto &[x1, y1] = d;
auto &[x2, y2] = c; }
};
void test_friend(D d) {
auto &[x, y] = d;
}
void test_external(D d) {
auto &[x, y] = d; }
}