Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/c/55.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 如何可靠地获得C型阵列的大小?_C++_C_Arrays_Size - Fatal编程技术网

C++ 如何可靠地获得C型阵列的大小?

C++ 如何可靠地获得C型阵列的大小?,c++,c,arrays,size,C++,C,Arrays,Size,如何可靠地获取C样式数组的大小?通常推荐的方法似乎是使用sizeof,但它在foo函数中不起作用,其中x被传入: #include <iostream> void foo(int x[]) { std::cerr << (sizeof(x) / sizeof(int)); // 2 } int main(){ int x[] = {1,2,3,4,5}; std::cerr << (sizeof(x) / sizeof(int));

如何可靠地获取C样式数组的大小?通常推荐的方法似乎是使用
sizeof
,但它在
foo
函数中不起作用,其中
x
被传入:

#include <iostream>

void foo(int x[]) {
  std::cerr << (sizeof(x) / sizeof(int)); // 2  
}

int main(){
    int x[] = {1,2,3,4,5};
    std::cerr << (sizeof(x) / sizeof(int)); // 5                              
    foo(x);
    return 0;
}
#包括
void foo(整数x[]{

C中的std::cerrC中的数组参数实际上只是指针,因此
sizeof()
将不起作用。您需要将大小作为另一个参数传递,或者使用哨兵-以最适合您的设计为准

其他一些选择:

其他一些信息:

    > P> C++,而不是传递原始数组指针,您可能希望参数使用包中的数组来跟踪数组大小,并提供方法以安全的方式将数据复制到数组中。类似或有帮助。e、 在使用参数的函数中,可以得到类似于
    std::vector
    的操作,但是函数的调用方可以使用简单的C数组。没有对数组的复制-
    array\u proxy
    模板几乎自动打包数组指针和数组大小

  • 在C中用于确定数组中元素数的宏(当sizeof()可能有帮助时,例如,您没有处理简单的指针):


您可以传递大小,使用sentinel,或者更好地使用std::vector。尽管std::vector缺少初始值设定项列表,但使用一组元素构建向量仍然很容易(尽管没有那么好)

static const int arr[]={1,2,3,4,5};
向量向量向量(arr,arr+sizeof(arr)/sizeof(arr[0]);

STD::向量类也使得错误更难,这是它的重量,它的重量是金的。另外一个好处是所有的C++都应该熟悉它,并且大多数C++应用程序应该使用一个STD::vector而不是原始C数组。 作为简要说明,C++0x添加了

std::vector v={1,2,3,4};
您也可以使用来做同样的事情,尽管语法有点复杂

std::vector<int> v = boost::assign::list_of(1)(2)(3)(4);
std::vector v=boost::assign::list_of(1)(2)(3)(4);

std::vector v;
v+=1,2,3,4;

c对此不提供本机支持。一旦数组超出其声明的作用域,其大小将丢失

你可以通过数组传递大小。如果你总是想保持大小,你甚至可以将它们捆绑到一个结构中,尽管这样会有一些簿记开销。

这个怎么样

template <int N>
void foo(int (&x)[N]) {
    std::cerr << N;
}
模板
void foo(int&x)[N]){

std::cerr您需要将大小与数组一起传递,就像在许多库函数中一样,例如
strncpy()
strncmp()
等。抱歉,这只是C:-)中的工作方式

或者,您可以推出自己的结构,如:

struct array {
    int* data;
    int size;
};
并将其传递给您的代码

<>当然可以使用<代码> STD::列表< /COD>或 STD::向量< /代码>,如果你想更多的C++-ISH。

< P> >在GNU LIbSTDC++文档中提到的是<代码>长度
函数:

template<typename T, unsigned int sz>
inline unsigned int lengthof(T (&)[sz]) { return sz; }
模板
内联无符号整数长度(T(&)[sz]){return sz;}
你可以把它当作

int x[] = {1,2,3,4,5};
std::cerr << lengthof(x) << std::endl;
intx[]={1,2,3,4,5};

std::cerr数组表达式的类型将从“T的N元素数组”隐式转换为“指向T的指针”,其值将是数组中第一个元素的地址,除非数组表达式是
sizeof
的操作数或(
&
的地址)运算符,或者如果数组表达式是用于初始化声明中另一个数组的字符串文字。简而言之,不能将数组作为数组传递给函数;函数接收的是指针值,而不是数组值

必须将数组大小作为单独的参数传递

因为你使用C++,使用向量(或者其他合适的STL容器)代替C样式数组。是的,你失去了方便的速记语法,但是折衷是不值得的。认真。

< P>我也同意Corwin的方法是非常好的。< /P>
模板
void foo(int&x)[N])
{

自c++11以来,有一种非常方便的方法:

static const int array[] = { 1, 2, 3, 6 };
int size = (int)std::distance(std::begin(array), std::end(array))+1;
现在,您可以使用C++11的和

举例来说:

#include <iostream>
#include <type_traits>

int main()
{
  int a[][3] = {{1, 2, 3}, {4, 5, 6}};

  std::cout << "\nRank:           : " << std::rank<decltype(a)>::value;
  std::cout << "\nSize: [_here_][]: " << std::extent<decltype(a), 0>::value;
  std::cout << "\nSize: [][_here_]: " << std::extent<decltype(a), 1>::value;
  std::cout << "\nSize: [][]_here_: " << std::extent<decltype(a), 2>::value;
}

如果函数的用户没有按照文档的要求去做,那是他们的问题,而不是你的问题。不可能防止无知者误用API。
foo
中的
x
是一个指针,而不是数组。另外,请看,.dup:@Neil Butterworth:这就是
private
修饰符的作用。@Brian:可能是,也可能是ot是个坏主意,这取决于上下文。为什么你认为它很糟糕?这是个好主意,因为如果你传入一个指针,它将不会编译。如果函数很大,并且使用许多不同的数组大小调用,它将生成一组函数,这是个坏主意-它将生成一组函数。另一种选择可能是,这个foo然后转过来调用private/internal foo____________________________________________________。
int x[] = {1,2,3,4,5};
std::cerr << lengthof(x) << std::endl;
template <int N>
void foo(int (&x)[N]) 
{
    std::cerr << N;
}
int numbers [] = {1, 2, 3, 4};
for(int i = 0; i < numbers.length(); i++)
{
   System.out.println(numbers[i]+"\n");
}
int numbers [] = {1, 2, 3, 4};
int size = sizeof(numbers)/sizeof(int);
for(int i = 0; i < size; i++)
{
    cout << numbers[i] << endl;
}
template <int N>
int size(int (&X)[N])
{
   return N;
}
template < int N >
int size(int (&X)[N])
{
   int value = (sizeof(X)/sizeof(X[0]));
   return value;
}
int numbers [] = {1, 2, 3, 4};
for(int i = 0; i < size(numbers); i++)
{
   cout << numbers[i] << endl;
}
static const int array[] = { 1, 2, 3, 6 };
int size = (int)std::distance(std::begin(array), std::end(array))+1;
#include <iostream>
#include <type_traits>

int main()
{
  int a[][3] = {{1, 2, 3}, {4, 5, 6}};

  std::cout << "\nRank:           : " << std::rank<decltype(a)>::value;
  std::cout << "\nSize: [_here_][]: " << std::extent<decltype(a), 0>::value;
  std::cout << "\nSize: [][_here_]: " << std::extent<decltype(a), 1>::value;
  std::cout << "\nSize: [][]_here_: " << std::extent<decltype(a), 2>::value;
}
Rank:           : 2
Size: [_here_][]: 2
Size: [][_here_]: 3
Size: [][]_here_: 0