从指针获取数组大小的方法(C++)

31

我正在编写一个简单的函数,用于返回数组中最大的整数。我遇到的问题是如何找到数组中元素的数量。

这里是函数的头部:

int largest(int *list, int highest_index)

如何获取数组'list'中整数的数量。

我尝试了以下方法:

int i = sizeof list/sizeof(int); //returns incorrect value
int i = list.size(); // does not compile

非常感谢您的帮助!


2
参数是一个固定大小的数组还是一个指针?如果它是一个指针,你无法找出它所指向的数组的大小。 - juanchopanza
这是一个指针,我被要求使用该函数头部。显然我采取了错误的方法。我试图编写一个递归函数来返回数组中最大的整数。个人而言,我并不认为这有什么意义,我觉得用for循环会做得更好... - user906357
“highest_index”不是告诉你列表中有多少个整数吗?名称暗示整数的计数将为“highest_index + 1”。 - Phillip Kinkade
我相信你是完全正确的,谢谢! - user906357
6个回答

46
C++基于C语言并继承了许多特性。关于这个问题,它继承了一种叫做“数组/指针等价”的规则,这个规则允许数组在作为函数参数传递时衰变为指针。这并不意味着数组就是指针,只是意味着它可以衰变为指针。
void func(int* ptr);

int array[5];
int* ptr = array; // valid, equivalent to 'ptr = &array[0]'
func(array); // equivalent to func(&array[0]);

这最后一部分与你的问题最相关。你不是传递数组,而是传递第0个元素的地址。
为了让你的函数知道传入的数组有多大,你需要将这个信息作为参数发送。
static const size_t ArraySize = 5;
int array[ArraySize];
func(array, ArraySize);

因为指针不包含大小信息,所以无法使用sizeof。
void func(int* array) {
    std::cout << sizeof(array) << "\n";
}

这将输出"int*"的大小 - 根据32位还是64位,它的大小为4或8个字节。
相反,您需要接受大小参数。
void func(int* array, size_t arraySize);

static const size_t ArraySize = 5;
int array[ArraySize];
func(array, ArraySize);

即使你试图传递一个固定大小的数组,结果证明这只是一种语法糖。
void func(int array[5]);

http://ideone.com/gaSl6J

记得我之前说过,数组不是指针,只是等价而已吗?
int array[5];
int* ptr = array;

std::cout << "array size " << sizeof(array) << std::endl;
std::cout << "ptr size " << sizeof(ptr) << str::endl;

数组大小将为5 * sizeof(int) = 20

指针大小将为sizeof(int *),其大小将为4或8个字节。

*sizeof返回所提供类型的大小,如果提供的是对象,则推断类型并返回其大小。

如果您想知道数组中有多少个元素,当您有数组而不是指针时,您可以编写:

sizeof(array) / sizeof(array[0])

或者

sizeof(array) / sizeof(*array)

12

无法这样做。这是使用向量而不是数组的一个好理由(其中之一)。但是如果您必须使用数组,则必须将数组的大小作为参数传递给函数。

int largest(int *list, int list_size, int highest_index)

C ++ 中的数组相当差,越早学会使用向量,你会发现事情变得更容易。


4
简单的回答是你不能。你需要将它存储在一个变量中。C++的优点是它有STL,你可以使用vector。size()方法给出了向量在那一时刻的大小。
#include<iostream>
#include<vector>
using namespace std; 
int main () {
    vector<int> v;
    for(int i = 0; i < 10; i++) {
        v.push_back(i);
    }
    cout << v.size() << endl;
    for(int i = 0; i < 10; i++) {
        v.push_back(i);
    }
    cout << v.size() << endl;
    return 0;
}

输出:
10
20

未测试。但应该可以工作。;)


4
指针没有关于它们所引用的元素数量的信息。如果您正在谈论函数调用的第一个参数,那么如果列表是数组,则确实可以使用语法。
sizeof( list ) / sizeof( int )

我想补充一下,有三种方法:

  1. 使用通过引用传递的数组
  2. 使用指向第一个元素和元素数量的指针。
  3. 使用两个指针 - 开始指针和最后指针,因为标准算法通常是这样定义的。字符数组有额外的处理可能性。

2

在变量数组大小中,无法从指针中检索数组大小。

需要注意的是,在变量数组大小中,无法从指针中获取数组大小。

const int SIZE = 10;
int list[SIZE];
// or
int* list = new int[SIZE];  // do not forget to delete[]

1
sizeof(list) / sizeof(*list)将始终返回定义它的作用域内数组的大小(只要它是一个常量大小的C风格数组)。 - Elliott

-1

我的答案使用了字符数组而不是整数数组,但我希望它能有所帮助。

您可以使用计数器直到达到数组的末尾。字符数组总是以 '\0' 结尾,您可以使用它来检查是否已经到达了数组的末尾。

char array[] = "hello world";
char *arrPtr = array;

char endOfString = '\0';
int stringLength = 0;

while (arrPtr[stringLength] != endOfString) {
stringLength++;
}
stringLength++;
cout << stringLength << endl;

现在你有了字符数组的长度。
我尝试使用这种方法来计算数组中整数的个数。显然,'\0'在这里不适用,但是数组的-1索引是0。所以假设在你使用的数组中没有0。你可以将代码中的'\0'替换为0,并修改代码使用int指针和数组。

这个答案不适用于这个问题,因为整数数组没有结束标记,而 C 风格的字符数组以 '\0' 结尾。 - Arjonais

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接