*单个变量中允许多少个指针()?
让我们考虑以下示例.
int a = 10;
int *p = &a;
同样我们也可以
int **q = &p;
int ***r = &q;
等等.
例如,
int ****************zz;
P.P*_*.P. 396
该C标准规定了下限:
5.2.4.1翻译限制
276实施应能够翻译和执行至少一个包含以下每个限制的至少一个实例的程序:[...]
279 - 12指针,数组和函数声明符(以任意组合)修改声明中的算术,结构,联合或void类型
上限是特定于实现的.
Kaz*_*Kaz 152
实际上,C程序通常使用无限指针间接.一个或两个静态级别很常见.三重间接是罕见的.但无限是非常普遍的.
无限指针间接是在结构的帮助下实现的,当然,不是直接声明器,这是不可能的.并且需要一个结构,以便您可以在此结构中包含可以终止的不同级别的其他数据.
struct list { struct list *next; ... };
现在你可以拥有list->next->next->next->...->next.这实际上只是多个指针间接:*(*(..(*(*(*list).next).next).next...).next).next.而且.next基本上是一个空操作时,它的结构的第一个成员,所以我们可以想像这是***..***ptr.
对此没有任何限制,因为链接可以用循环遍历而不是像这样的巨型表达式,而且,结构可以很容易地变成圆形.
因此,换句话说,链接列表可能是添加另一级间接来解决问题的最终示例,因为您在每次推送操作时都会动态地执行此操作.:)
Alo*_*ave 82
从理论上讲:
您可以根据需要拥有多个级别的间接.
几乎:
当然,任何消耗内存的东西都是无限期的,由于主机环境上可用的资源而存在限制.实际上,实现可以支持的最大限制是,实现应该适当地记录它.因此,在所有此类工件中,标准未指定最大限制,但它确实指定了下限.
这是参考:
C99标准5.2.4.1翻译限制:
- 12个指针,数组和函数声明符(以任意组合)修改声明中的算术,结构,联合或void类型.
这指定了每个实现必须支持的下限.请注意,在标准中,标准进一步说:
18)实施应尽可能避免强加固定的翻译限制.
BoB*_*ish 76
正如人们所言,"在理论上"没有限制.然而,出于兴趣,我使用g ++ 4.1.2运行它,它的大小高达20,000.编译虽然很慢,所以我没有尝试更高.所以我猜g ++也没有任何限制.(尝试设置size = 10并查看ptr.cpp,如果它不是很明显的话.)
g++ create.cpp -o create ; ./create > ptr.cpp ; g++ ptr.cpp -o ptr ; ./ptr
create.cpp
#include <iostream>
int main()
{
    const int size = 200;
    std::cout << "#include <iostream>\n\n";
    std::cout << "int main()\n{\n";
    std::cout << "    int i0 = " << size << ";";
    for (int i = 1; i < size; ++i)
    {
        std::cout << "    int ";
        for (int j = 0; j < i; ++j) std::cout << "*";
        std::cout << " i" << i << " = &i" << i-1 << ";\n";
    }
    std::cout << "    std::cout << ";
    for (int i = 1; i < size; ++i) std::cout << "*";
    std::cout << "i" << size-1 << " << \"\\n\";\n";
    std::cout << "    return 0;\n}\n";
    return 0;
}
mih*_*hai 63
听起来很有趣.
Visual Studio 2010(在Windows 7上),在获得此错误之前,您可以拥有1011个级别:
致命错误C1026:解析器堆栈溢出,程序太复杂
gcc(Ubuntu),100k + *没有崩溃!我猜硬件是这里的限制.
(仅使用变量声明进行测试)
Nan*_*ale 27
没有限制,例如检查这里.
答案取决于"指针水平"的含义.如果你的意思是"你可以在一个声明中有多少级别的间接?" 答案是"至少12".
int i = 0;
int *ip01 = & i;
int **ip02 = & ip01;
int ***ip03 = & ip02;
int ****ip04 = & ip03;
int *****ip05 = & ip04;
int ******ip06 = & ip05;
int *******ip07 = & ip06;
int ********ip08 = & ip07;
int *********ip09 = & ip08;
int **********ip10 = & ip09;
int ***********ip11 = & ip10;
int ************ip12 = & ip11;
************ip12 = 1; /* i = 1 */
如果你的意思是"在程序难以阅读之前你可以使用多少级别的指针",这是一个品味问题,但是有一个限制.具有两个间接级别(指向某事物的指针)是常见的.除此之外,更容易思考; 除非替代方案会更糟,否则不要这样做.
如果你的意思是"你可以在运行时有多少级别的指针间接",那就没有限制.这一点对于循环列表尤为重要,其中每个节点都指向下一个节点.你的程序可以永远遵循指针.
Mat*_* M. 24
实际上,指向函数的指针更加有趣.
#include <cstdio>
typedef void (*FuncType)();
static void Print() { std::printf("%s", "Hello, World!\n"); }
int main() {
  FuncType const ft = &Print;
  ft();
  (*ft)();
  (**ft)();
  /* ... */
}
如图所示,这给出了:
你好,世界!
你好,世界!
你好,世界!
并且它不涉及任何运行时开销,因此您可以根据需要堆叠它们......直到编译器对文件进行阻塞.
Sac*_*tre 19
有没有限制.指针是一块内存,其内容是一个地址.
如你所说
int a = 10;
int *p = &a;
指向指针的指针也是一个包含另一个指针地址的变量. 
int **q = &p;
这q是指向指针的指针,其地址p已经保存了地址a.
指向指针的指针没有什么特别之处.
所以对持有另一个指针地址的poniters链没有限制.
即.
 int **************************************************************************z;
被允许.
Mar*_*tus 15
每个C++开发人员都应该听说过着名的三星级程序员
而且似乎有一些神奇的"指针屏障"必须被伪装
来自C2的报价:
三星程序员
C程序员的评级系统.你的指针越间接(即你的变量之前的"*"越多),你的声誉就越高.没有明星的C程序员几乎不存在,因为几乎所有非平凡的程序都需要使用指针.大多数是一星级程序员.在过去(好吧,我很年轻,所以这些看起来至少对我而言),偶尔会找到一个由三星级程序员完成的代码并且敬畏地颤抖.有些人甚至声称他们在不止一个间接层面上看到了涉及函数指针的三星代码.听起来像UFO一样真实.
Kaz*_*Kaz 13
请注意,这里有两个可能的问题:我们可以在C类型中实现多少级别的指针间接,以及我们可以将多少级别的指针间接填充到单个声明符中.
C标准允许对前者施加最大值(并给出最小值).但是这可以通过多个typedef声明来规避:
typedef int *type0;
typedef type0 *type1;
typedef type1 *type2; /* etc */
所以最终,这是一个实现问题,它与C程序在被拒绝之前的大/复杂程度有关,这是一个非常特定于编译器的.
我想指出的是,生成具有任意数量 * 的类型是模板元编程可能发生的事情。我忘记了我到底在做什么,但有人建议我可以通过使用递归T* 类型来生成新的不同类型,这些类型在它们之间具有某种元操作。
模板元编程是慢慢陷入疯狂的,所以在生成几千级间接的类型时没有必要找借口。例如,这只是将 peano 整数映射到模板扩展作为功能语言的一种方便的方法。