社区
C语言
帖子详情
char (*(*x())[])()
slowgrace
2009-09-26 05:45:25
char (*(*x())[])()
请问这个声明是表示函数,还是表示函数指针?
俺比较笨,请楼下的朋友说详细点,谢谢!
...全文
365
34
打赏
收藏
char (*(*x())[])()
char (*(*x())[])() 请问这个声明是表示函数,还是表示函数指针? 俺比较笨,请楼下的朋友说详细点,谢谢!
复制链接
扫一扫
分享
转发到动态
举报
AI
作业
写回复
配置赞助广告
用AI写文章
34 条
回复
切换为时间正序
请发表友善的回复…
发表回复
打赏红包
Tiger_Zhao
2009-09-29
打赏
举报
回复
[Quote=引用 5 楼 hpsmouse 的回复:]下次看到有人写这种代码,直接抡起砖头……[/Quote]
slowgrace
2009-09-27
打赏
举报
回复
那你们看看
这个帖子
吧,如果不弄懂这些、不熟练本帖这些,你很多常见的语句都会蒙的。
xiaobozz
2009-09-27
打赏
举报
回复
[Quote=引用 27 楼 slowgrace 的回复:]
引用 25 楼 xiaobozz 的回复:
引用 8 楼 pengzhixi 的回复:
typedef char(*FUNPTR)();
typedef FUNPTR[] FUNPTR_ARRAY;
char (*(*x())[])()就可以写成 FUNPTR_ARRAY * x();
除了用来考试和炫耀自己的基本功外,写这样的表达式有什么好处?
可以简化的问题写成这样多清楚
这只是一种练习,通过这种练习让你对指针运算达到滚瓜烂熟、条件反射的地步。个人认为这种练习还是很必要的,毕竟在C中指针的使用比比皆是,如果不能达到超级熟练的地步,在使用C的过程中可以说步步皆是雷区。
[/Quote]
我觉得这纯粹是表达式的解释,不涉及到指针的原理,最多是一个指针类型
用typedef多么符合人的逻辑思维啊,而扩展开是编译器的工作,没必要去重复编译器的劳动。
如果大家全部都用typedef,难道大家指针就都不会用了????
鼠
2009-09-27
打赏
举报
回复
[Quote=引用 26 楼 slowgrace 的回复:]
我觉得你理解的不对。这是声明不是使用!
*在这里不是当做解引用运算符,而是当做指针修饰符。()在这里是函数声明,而不是函数调用。
[/Quote]
我第一句话说的就是“按使用方式声明”……这句话我是从 Bjarne Stroustrup 那里抄来的……
这当然是声明不是使用,我的意思是说 C 的声明是以描述使用方式实现的……
forster
2009-09-27
打赏
举报
回复
写这个 是靠编译器玩的
考别人就是找抽。。
zxl0511
2009-09-27
打赏
举报
回复
哎,误人子弟啊。。。
slowgrace
2009-09-27
打赏
举报
回复
[Quote=引用 25 楼 xiaobozz 的回复:]
引用 8 楼 pengzhixi 的回复:
typedef char(*FUNPTR)();
typedef FUNPTR[] FUNPTR_ARRAY;
char (*(*x())[])()就可以写成 FUNPTR_ARRAY * x();
除了用来考试和炫耀自己的基本功外,写这样的表达式有什么好处?
可以简化的问题写成这样多清楚
[/Quote]
这只是一种练习,通过这种练习让你对指针运算达到滚瓜烂熟、条件反射的地步。个人认为这种练习还是很必要的,毕竟在C中指针的使用比比皆是,如果不能达到超级熟练的地步,在使用C的过程中可以说步步皆是雷区。
slowgrace
2009-09-27
打赏
举报
回复
[Quote=引用 23 楼 hpsmouse 的回复:]
引用 21 楼 slowgrace 的回复:
引用 8 楼 pengzhixi 的回复:
typedef char(*FUNPTR)();
typedef FUNPTR[] FUNPTR_ARRAY;
char (*(*x())[])()就可以写成 FUNPTR_ARRAY * x();
谢谢。我发现如果是自己去阅读复杂的声明,那应该“从内到外”,就是从最里面的圆括号往外读;而如果是拆分复杂的声明typedef,那就要“从外向里剥”。是不是这样?
一般来说,typedef 和一般声明的方法是一样的。去掉 typedef 关键字,你通常会发现这依旧是一个合法的声明。
另外,typedef FUNPTR[] FUNPTR_ARRAY; 这种声明办法不对。要写成 typedef FUNPTR FUNPTR_ARRAY[];
C 中的声明方法的一大特点就是“按使用方式声明”,通过描述使用方法声明标识符的类型,懂得这点以后看声明就简单多了。
例如:char (*(*x())[])()
可以从最里面看起。
首先 *x 是一个指针解引用,然后 *x() 对 *x 解引用的结果进行函数调用,这就是说,x 是一个函数指针;
然后 (*x())[] 对函数调用的返回值进行下标运算,表明返回的是一个数组(或指针);
*(*x())[] 对下标运算的结果(即数组中的元素)继续指针解引用,表示数组中的元素是指针;
(*(*x())[])() 表示对解引用的结果又可以做一次函数调用,就是说数组中的元素是函数指针;
最后 char(*(*x())[])() 说明了数组中的函数指针调用结果是一个 char。
这也算提供一种方法吧~~具体用什么办法要看个人喜好了~~
[/Quote]
我觉得你理解的不对。这是
声明
不是使用!
*在这里不是当做解引用运算符,而是当做指针修饰符。()在这里是函数声明,而不是函数调用。
xiaobozz
2009-09-27
打赏
举报
回复
[Quote=引用 8 楼 pengzhixi 的回复:]
typedef char(*FUNPTR)();
typedef FUNPTR[] FUNPTR_ARRAY;
char (*(*x())[])()就可以写成 FUNPTR_ARRAY * x();
[/Quote]
除了用来考试和炫耀自己的基本功外,写这样的表达式有什么好处?
可以简化的问题写成这样多清楚
slowgrace
2009-09-27
打赏
举报
回复
[Quote=引用 22 楼 qingye2008 的回复:]
西西看的是啥书啊?
[/Quote]
"The C Programming Language (2nd Edition)"
鼠
2009-09-27
打赏
举报
回复
[Quote=引用 21 楼 slowgrace 的回复:]
引用 8 楼 pengzhixi 的回复:
typedef char(*FUNPTR)();
typedef FUNPTR[] FUNPTR_ARRAY;
char (*(*x())[])()就可以写成 FUNPTR_ARRAY * x();
谢谢。我发现如果是自己去阅读复杂的声明,那应该“从内到外”,就是从最里面的圆括号往外读;而如果是拆分复杂的声明typedef,那就要“从外向里剥”。是不是这样?
[/Quote]
一般来说,typedef 和一般声明的方法是一样的。去掉 typedef 关键字,你通常会发现这依旧是一个合法的声明。
另外,typedef FUNPTR[] FUNPTR_ARRAY; 这种声明办法不对。要写成 typedef FUNPTR FUNPTR_ARRAY[];
C 中的声明方法的一大特点就是“按使用方式声明”,通过描述使用方法声明标识符的类型,懂得这点以后看声明就简单多了。
例如:char (*(*x())[])()
可以从最里面看起。
首先 *x 是一个指针解引用,然后 *x() 对 *x 解引用的结果进行函数调用,这就是说,x 是一个函数指针;
然后 (*x())[] 对函数调用的返回值进行下标运算,表明返回的是一个数组(或指针);
*(*x())[] 对下标运算的结果(即数组中的元素)继续指针解引用,表示数组中的元素是指针;
(*(*x())[])() 表示对解引用的结果又可以做一次函数调用,就是说数组中的元素是函数指针;
最后 char(*(*x())[])() 说明了数组中的函数指针调用结果是一个 char。
这也算提供一种方法吧~~具体用什么办法要看个人喜好了~~
qingye2008
2009-09-27
打赏
举报
回复
西西看的是啥书啊?
slowgrace
2009-09-27
打赏
举报
回复
[Quote=引用 8 楼 pengzhixi 的回复:]
typedef char(*FUNPTR)();
typedef FUNPTR[] FUNPTR_ARRAY;
char (*(*x())[])()就可以写成 FUNPTR_ARRAY * x();
[/Quote]
谢谢。我发现如果是自己去阅读复杂的声明,那应该“从内到外”,就是从最里面的圆括号往外读;而如果是拆分复杂的声明typedef,那就要“从外向里剥”。是不是这样?
geochway
2009-09-27
打赏
举报
回复
作为语法分析的例子可以,在实际编程中写出这样的代码就是变态.
slowgrace
2009-09-27
打赏
举报
回复
谢谢supermegaboy 。
slowgrace
2009-09-27
打赏
举报
回复
[Quote=引用 14 楼 sytstarac 的回复:]
这句话声明了一个函数指针数组对吧,X是函数名吗?借助一个函数名来声明一个指针可以吗?我觉得函数名代表一个对象,而非一个类型。用一个对象来表示一个类型我觉得不妥啊。
[/Quote]
不对。声明的是一个函数。详见1楼和7楼。
开心乐源
2009-09-27
打赏
举报
回复
*x()看完这个,就可以知道x是函数。
Targui1989
2009-09-26
打赏
举报
回复
四楼正解!顶!
lzx258
2009-09-26
打赏
举报
回复
学习学习~~~~~~~~
飞天御剑流
2009-09-26
打赏
举报
回复
[Quote=引用 13 楼 slowgrace 的回复:]
引用 7 楼 supermegaboy 的回复:
int (*(*func)(int *p))[5];
func是一个函数指针,这类函数具有int*类型的形参,返回值是指向数组的指针,所指向的数组的元素是具有5个int元素的数组。
这里是不是有笔误:
你的原话是:返回值是指向数组的指针,所指向的数组的元素是具有5个int元素的数组。
是不是应该:返回值是指向数组的指针,所指向的数组是具有5个int元素的数组。
[/Quote]
对,是多了“的元素”三个字。
还有“但C语言的数组名是一个右值,它不能作为左值来接收另一个数组,”这句话也是错的,正确的应该是“但C语言的数组名是一个不可修改的左值,它不能作为赋值运算符的左操作数来接受另一个数组”。
加载更多回复(14)
char
** x做形参解析
一、
char
** x做形,传入前的理解: int pthread_join(pthread_t tid,void** rva_ptr) 此函数功能:阻塞调用线程,直到指定的线程终止,rva_ptr是线程退出 返回值的指针。 一般都会这样写程序调用: int ret; pthread_t
关于const
char
*和
char
*、const
char
** 和
char
** 赋值问题
根据ANSI C标准的赋值约束条件: 1. 两个操作数都是指向有限定符或无限定符的相容类型的指针。 2. 左边指针所指向的类型必须具有右边指针所指向类型的全部限定符。 一、const
char
*和
char
* const
char
*的类型是:“指向一个具有const限定符的
char
类型的指针”。(不能修改其值)
char
*的类型是:“指向一个
char
类型的指
char
,
char
*,
char
**数组
平时都用的是
char
数组,基本忘记了
char
*数组和
char
**数组该怎么用了
char
s1[10]; s1[0]s1[1]等都是
char
s1是
char
*,等同于&s1[0]
char
*s2[10]; s2[0]s2[1]等都是
char
* *s2[0]*s2[1]等都是
char
,是s2[0] s2[1]指向的字符串的第一个字符 s2是
char
**,等同于&s2[0]
const
char
**与
char
** 的传参问题
当我们使用这一代码测试时 #include<iostream> using namespace std; void foo(const
char
**a) { cout << "123"; } void main() {
char
b = 'x';
char
* a = &b;
char
** v = &a; foo(v); cout << (void*)&b<<"\n"<<&a<<"\n"<
char
* 定义的字符串为什么修改不了?(
char
*最好还是写成 const
char
*)
### 我们或许都知道
char
型数组与
char
* 都能够用来定义字符串,但可能不清楚
char
*定义字符串 有着不一样的地方。 用
char
* 来定义一个字符串,当我们试图对字符串的内容进行改动,即直接进行 改动,或进行传参,在子函数中进行改动。都改动失败,而用
char
型数组定义的字符串进行 改动操作则成功。 ●原因是什么: 由于
char
型数组是一段连续的存储空间,所以内容是可以改变的 而
char
*定义的字符串存储在字符常量区,是不可以修改的。 我们知道
char
*用来定义一个指针变量时,指针变量是可以改变
C语言
70,019
社区成员
243,267
社区内容
发帖
与我相关
我的任务
C语言
C语言相关问题讨论
复制链接
扫一扫
分享
社区描述
C语言相关问题讨论
社区管理员
加入社区
获取链接或二维码
近7日
近30日
至今
加载中
查看更多榜单
社区公告
暂无公告
试试用AI创作助手写篇文章吧
+ 用AI写文章