繁体   English   中英

计算未知类型数组的元素

[英]Count elements of an unknown type array

您好,我正在尝试编写一个函数,函数返回作为参数传递的数组元素的数量,该函数必须在任何类型的数组上工作

我尝试了这个:

int nb_elems(void* array)
{
    void* end = array;
    while(*end != NULL) // The last element have to be null, it is not counted.
        end++;

    return end - array;
}

如您所料,它不起作用。

实际上它甚至不编译,我得到这些错误:
错误:非法的间接访问。 <while(* end!= NULL)>
错误:无效*:大小未知。 <while(* end!= NULL)>
错误:无效*:大小未知。 <返回端-数组>

首先,您能告诉我我想做的事是否可行吗?
其次, 我试图实现这一目标的方法是否有意义 ,还是我完全忘记了要点?
那么, 为什么我会得到这些错误,它们意味着什么?

谢谢你的帮助!

由于C不传递数组,因此nb_elems(void* array)收到了一个指针 void *pointer不知道其指向多少个元素(也不包括类型)。

由于它需要“处理任何类型的数组”,因此代码需要定义如何将任意类型与NULL比较。

对于函数,您需要传递指针,数组元素的大小和用于测试NULL的函数。

int nb_elems(void* array, size_t esize, int (*cmp)(void *ptr)) {
  char *ptr = array;
  int count = 0;
  while (*cmp(ptr) == 0) {
    ptr += esize;
    count++;
  }
  return count;
}

不,您的操作方式是不可能的,因为执行指针算术(这里是++- )时,编译器必须知道数组基本类型的大小。

同样, void*是指向void的指针,即指向“非类型”的指针。 因此, *end类型为void ,您无法将其与任何东西进行比较,尤其是不能与NULL ,后者可以是指针类型或整数。 如果将基本类型比较为零,则只需使用0

在甚至尝试对任何类型的指针执行此操作之前,您应该对指向已知类型的指针(例如unsigneddouble尝试相同的操作。 如果您牢记这一点更改代码,那么它就有很好的机会工作。

您的代码无法编译的原因是由于编译器无法确定void的大小。 以++运算符为例。 我们可以将其大致翻译为:

end = end + sizeof(void);

未定义空隙的大小,因此编译器无法为此生成任何代码,从而给您一个错误。

接下来,您尝试取消引用空指针。 这会给你一些类型为void的东西。 但是由于void不代表任何内容(它不代表任何内容),因此编译器无法确定应为什么。 然后,您可以使用相等运算符将任何内容都不与NULL比较。 您无法将某物与任何事物进行比较,因此会产生错误。

在C语言中,仅由于您无法确定void *的类型,就不可能实现执行此类操作的函数。 您至少需要知道传递给函数的类型以及将用于终止数组的特定于类型的值。 C没有提供此功能,因此无法实现此功能。

因为您正在检查!= NULL我想您有一个指针数组。 使用指针数组,您的代码可以工作,因为您知道指针的大小,即使它是空指针也是如此。

如果我的假设是正确的,则可以这样编写:

int nb_elems(void** array) {
    void** end = array;
    while(*end != NULL) {
        end++;
    }
    return end - array;
}

但是此代码仅适用于指向指针的指针或指针数组。


用法:

int** iptrs = (int**)malloc(3 * sizeof(int*));

iptrs[0] = (int*)malloc(sizeof(int));
*(iptrs[0]) = 42;
iptrs[1] = (int*)malloc(sizeof(int));
*(iptrs[1]) = 23;
iptrs[2] = NULL;

printf("%d", nb_elems(iptrs));

该示例打印2

如果您有一个实际的数组,而不是一个指针,则可以使用sizeof(array) / sizeof(array[0])确定其中的元素数量。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM