【问题标题】:Disadvantages of using void* pointers in C在 C 中使用 void* 指针的缺点
【发布时间】:2010-09-25 06:56:36
【问题描述】:

在 C 中使用 void * 有很多缺点(内存相关、类型相关、效率方面......)。尽管它们提供了灵活性,但我们还是经常使用它们。

使用void * 列出缺点/缺点(以及 C 中的首选解决方案 - 如果可能)。

编辑: 请通过以下链接: http://attractivechaos.wordpress.com/2008/10/02/using-void-in-generic-c-programming-may-be-inefficient/

【问题讨论】:

  • 从款式上看,像功课。正如答案所解释的那样,这是一个奇怪的问题。

标签: c void-pointers


【解决方案1】:

我不知道,我发现 void 指针对于访问不同的抽象级别 (ABC) 非常有效。作为在不同抽象级别导航相互关联的类的一种方法。它是如此简单,它太棒了。就像 e 或黄金比例的公式一样,应该有一个崇拜虚空*的神秘学*它很棒:)

【讨论】:

    【解决方案2】:

    链接到的帖子将操作与 void 指针与 C++ 模板的操作进行比较,并得出结论认为模板更有效。这并不奇怪,而且我见过的 C++ 代码很少或从不使用 void 指针。与其他 C++ 工具相比,它通常没有任何优势,并且可能是类型系统中的一个漏洞。

    但是,C 没有 C++ 样式的模板,并且 void 指针是实现必须独立于数据类型的功能所必需的。

    因此,当您使用 C 编写并且需要泛型时,void 指针是获得它的最有效方法(因为它们是唯一的方法)。当您使用 C++ 编写代码时,几乎所有 void 指针可以完成的事情都有更好的方法,所以不要使用它们。

    【讨论】:

      【解决方案3】:

      您给定的链接部分正确。特别是,当您不处理对象(结构)时,或者通常不处理尚未分配的类型时。使用 int、double 等本机类型和 void-pointers(例如对于容器)几乎总是一件令人讨厌的事情,因为您可以选择将 int(对于 double 这不起作用)转换为指针或您需要为数据类型分配额外的内存。

      第一选择很糟糕,因为它不可移植,0 可能不允许作为值,而且感觉很糟糕。第二种选择会浪费内存,并且由于额外的分配确实会(大量)减慢速度。

      但是在大多数情况下,您不是在处理本机类型,而是在处理对象,最好是使用指向已经分配的对象的指针,至少我这样做。我从不需要哈希表或整数或双精度映射。并且仅仅为了指针的类型安全而使用不同的容器实现对我来说是错误的,因为每个实现都会增加你的二进制大小。因此,如果您只需要一个容器来存储您的指针,那么使用 void-pointers 不会减慢或浪费内存。

      但请注意,这都是关于容器实现的,就像你提到的博客文章一样。一般来说,如果不使用 void-pointers,您将无法完成许多事情。

      【讨论】:

        【解决方案4】:

        我不同意这个问题的前提。我们在 C 中使用 void* 是因为它是获得多态性的唯一方法。示例:库函数 qsort 和 bsearch。只有一个缺点,即基于 void * 的多态性是不安全的:一旦你将一个指针强制转换为 void *,就没有什么可以阻止你将 void * 强制转换为 wrong 指针类型错误。我的学生经常犯这个错误。

        可能会产生效率成本,因为有时需要分配堆空间才能使用多态数据结构。

        任何想了解使用带有 void * 的多态数据结构的优势和权衡的人都应该获得 Dave Hanson 的书 C Interfaces and Implementations

        【讨论】:

          【解决方案5】:

          void 指针没有效率问题。 void 指针的唯一限制是:

          • 由于显而易见的原因,您不能取消引用 void 指针
          • sizeof(void) 是非法的
          • 您不能对 void 指针执行指针运算

          但是 GCC 假定 sizeof(void) 为 1 并允许对 void 指针进行指针算术 - see here

          【讨论】:

          • sizeof(void *) 不是非法的,AFAIK。但是 sizeof(void) 没有任何意义。
          • 也许这可以解决一些与效率相关的问题:attractivechaos.wordpress.com/2008/10/02/…
          • Hasturkun,你对 sizeof() 的看法是对的——我把事情搞混了。已编辑。感谢您发现这一点。
          • void 指针作为一种类型不会增加任何开销,但是程序员使用它的方式可能会减慢速度,但这是人的问题,而不是语言问题。
          【解决方案6】:

          呃……我不确定有那么多。当然,你不应该在不必要的时候使用void*。如果有可以使用的明确定义的类型,那就这样做吧。

          根据我的经验,void* 最适合“匿名”指针(真是令人震惊!),就像在 malloc() 的返回值中一样,并且仅在处理不透明的位缓冲区时。通常,您希望在例如地址处处理这些缓冲区。字节级别,然后你当然会使用unsigned char *

          在任何需要指针的地方随意使用void* 只会损坏、发臭的代码,当然要避免。

          【讨论】:

            猜你喜欢
            • 2015-12-06
            • 2011-04-01
            • 2010-09-29
            • 1970-01-01
            • 2023-03-04
            • 2014-05-30
            • 1970-01-01
            相关资源
            最近更新 更多