也是从网上的博文学习的
分析复杂声明的准则:
1.声明中出现的操作符的优先级;
2.由内而外逐步分析,确定声明中标识符与操作符结合起来,所代表的含义;
重点:当指针解引用符 * 与一个表示函数的标识符结合时,表示这个函数的返回值,是一个指针:例,*pf表示pf是一个返回值为指针的函数
int (*(*pf( )) ( ) ) ( )
pf():pf是一个无参函数;
*pf():pf是一个无参函数,它的返回值是一个指针;
(*pf())():pf是一个无参函数,它的返回值是一个无参函数的指针;
*(*pf())():pf是一个无参函数,它的返回值是一个无参函数的指针,这个函数的返回值又是一个指针;
(*(*pf())())():pf是一个无参函数,它的返回值是一个无参函数的指针,这个函数的返回值又是一个无参函数的指针;
int (*(*pf( )) ( ) ) ( ):pf是一个无参函数,它的返回值是一个无参函数的指针,这个函数的返回值又是一个无参且返回值是int的函数的指针(回调函数的形式);
使用返回值追踪的方式分解:
int (*(*pf( )) ( ) ) ( );
auto pf() -> auto (*)() -> int (*)(){
}
可能看起来有点懵逼,我自己是用以下的方法来分解的,首先整体看,形式是回调函数,那咱就反其道而行,并不是从内而外分解,而是首尾对称结合法[咱自己命名的,勿笑。。。]:
原型:int (*(*pf( )) ( ) ) ( )
- 最左边返回值类型与 左边第一个* 和最右边括号结合:int(*)();
- 剩余 (*pf( )) ( )
- 再从左边第一个与右边第一个括号结合,咱不管类型:auto ()();
- 剩余 pf( )
- 剩下最里层pf和最里层的括号结合,咱也不管类型:auto pf();
- 分析完,从下往上结合,得到: auto pf()->auto()()->int()(){};
同样,面对更复杂的:
int(*(*(*(*fn())(int))())())() {
return nullptr;
}
//根据我自己的方法分解
//1.int(*)() 剩余 (*(*(*fn())(int))())()
//2.auto (*)() 剩余 (*(*fn())(int))()
//3.auto(*)() 剩余 (*fn())(int)
//4.auto(*)(int) 剩余 fn()
//5.auto fn() 剩余(啥也没剩)
//从下往上结合得到以下结果:
auto fnex()->auto(*)(int)->auto(*)()->auto(*)()->int(*)(){
return nullptr;
}
//经过验证:
bool bSame = std::is_same<decltype(fn), decltype(f1)>::value;//bSame=true