3

C++ 11에서는 constexpr을 사용하여 컴파일 할 때 내장 된 1 차원 배열의 크기 (요소 수)를 반환하는 함수를 만들 수 있습니다. 아래의 예 :가변 템플릿 함수를 사용하는 내장 다차원 배열의 크기

template <typename T, std::size_t N> 
constexpr std::size_t size(T (&array)[N]) 
{ 
    return N; 
} 

이것은 ARRAY_SIZE 및 유사한 매크로 imo 대신 우수한 대안입니다.

그러나 내장 된 다차원 배열의 가장 중요한 차원 크기 만 반환합니다.

나는의 크기를 결정하기 위해 다음과 같은 기능을 사용하여 내장 된 두 개의 차원 배열 : 이상적으로

template <typename T, std::size_t N, std::size_t N2> 
constexpr std::size_t size(T (&array)[N][N2]) 
{ 
    return N * N2; 
} 

, 그것의 크기를 반환하는 기능이 매우 유용 할 것이다 내장 배열 임의의 수의 차원으로 난 variadic 템플릿 도움이 될 수도 있지만 단 하나의 인수가 전달되면서 템플릿 매개 변수의 압축을 푸는 방법을 볼 수 없다고 생각. 그러한 기능이 가능합니까?

미리 감사드립니다.

+0

세 가지 작업 응답 받고, 모든 다른 :). 나는 KennyTM이 가장 우아하다고 생각하여 그의 대답을 받아 들였고, Johannes 's가 그 뒤를이었다. – Ricky65

답변

5
#include <type_traits> 
#include <cstdlib> 

template <typename T> 
constexpr size_t size(const T&) noexcept 
{ 
    return sizeof(T)/sizeof(typename std::remove_all_extents<T>::type); 
} 

예 :

#include <cstdio> 
int main() 
{ 
    int a[3][4][7][12]; 
    char f[6]; 

    printf("%lu == %ld ?\n", size(a), 3*4*7*12); 
    printf("%lu == %ld ?\n", size(f), 6); 

    return 0; 
} 
2

당신은 std::extent을 찾고 있습니다. C++ 11 §20.9.5 :의

template <class T, unsigned I = 0> struct extent; 

T가 어레이 형 아니거나 경우 I가 0이고 t가있는 경우 I에 이하인 순위 경우 또는 "어레이 U의 미지의 경계 ", 그 다음에 0; 그렇지 않으면 I의 인덱스가 0 인 T의 I 차원의 경계 (8.3.4)입니다. 필요에 따라 std::와도 표준에서

사용, 접두사 extent는 :

assert((extent<int[2][4], 1>::value) == 4); 

당신은 또한 아마 당신의 정의를 size 기능을 대체하려면이 옵션을 사용해야합니다.

편집 : 죄송합니다. 이제 질문의 마지막 부분까지 읽습니다 : vP. std::remove_extent도 필요합니다.

template< typename multi_array, bool = std::is_array<multi_array>::value > 
struct total_extent; 

template< typename multi_array > 
struct total_extent< multi_array, false > { 
    enum { value = 1 }; 
}; 

template< typename multi_array > 
struct total_extent< multi_array, true > { 
    enum { 
     value = std::extent<multi_array>::value 
       * total_extent< typename std::remove_extent<multi_array> 
           ::type >::value 
    }; 
}; 
3
template<typename T> constexpr int size(T const&) { 
    return 1; 
} 

template<typename T, int N> constexpr int size(T const (&a)[N]) { 
    return N * size(a[0]); 
}