【问题标题】:The definition of char (*(*a)())[];char(*(*a)())[]的定义;
【发布时间】:2020-08-08 21:43:18
【问题描述】:

我无法理解 char (*(*a)())[]

int main()
{    
    char (*(*a)())[]; // do not change this

    char *x="My endless\n";

    char *  func (){
        return(x);
    }

    a=func;
    return 0;
}

当我编译时,我收到如下警告:
main.c:13:6:警告:来自不兼容指针类型的赋值 [-Wincompatible-pointer-types]

指的是a=func

我知道char (*(*a)()) 表示指向返回char 指针的函数的指针,但我不知道添加[] 对它有什么作用,即char (*(*a)())[];

【问题讨论】:

  • 首先你不能在另一个函数中定义一个函数,将 func 定义移出 main 并调整它的定义
  • @bruno:C 标准允许在函数内部定义函数等扩展,GCC 支持这一点。
  • @EricPostpischil 创建一个闭包?哇
  • @bruno:它不是一个功能齐全的闭包,因为它不包含绑定变量;它们仅在其正常生命周期内有效。见gcc manual:“如果你试图在包含函数退出后通过它的地址调用嵌套函数,一切都会崩溃。”

标签: c arrays pointers function-pointers


【解决方案1】:

这个

char (*(*a)())[];

是一个指向函数指针的声明,它返回指向不完整类型数组char[]的指针。

请注意,在另一个函数中定义函数不是标准的 C 特性。

这是一个至少可以编译的演示程序。

#include <stdio.h>

char ( *f() )[]
{
    static char s[][10] =
    {
        "Hello",
        "World"
    };

    return s;
}

int main(void) 
{
    char (*(*a)())[] = f;

    char ( *p )[] = a();

    puts( *p );

    return 0;
}

程序输出是

Hello

在这个程序中使用强制转换

char ( *p )[10] = ( char ( * )[10] ) a();

您可以获得指向完整数组类型的指针。

【讨论】:

    【解决方案2】:

    要破译复杂的 C 声明,您可以使用螺旋规则,请参阅 http://c-faq.com/decl/spiral.anderson.html。还有一个将 C 声明翻译成简单英语的工具:

    https://cdecl.org/

    一般来说,最好把复杂的声明分成几部分,给它们起有意义的名字,例如

    #include <stdlib.h>
    
    typedef char (*ArrayPointer)[];
    typedef ArrayPointer (*Function)();
    
    int main(void)
    {
        char (*(*a)())[] = NULL;
        Function b;
    
        b = a;
        return 0;
    }
    

    【讨论】:

      猜你喜欢
      • 2014-07-28
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-03-16
      • 2021-08-07
      • 2021-08-28
      相关资源
      最近更新 更多