第七色在线视频,2021少妇久久久久久久久久,亚洲欧洲精品成人久久av18,亚洲国产精品特色大片观看完整版,孙宇晨将参加特朗普的晚宴

為了賬號安全,請及時綁定郵箱和手機立即綁定

C++霧中風景番外篇:理解C++的復(fù)雜聲明與聲明解析

標簽:
C++

在学习C系列语言的过程之中,理解C/C++的复杂声明一直是初学者很困扰的问题。笔者初学之时也深受困扰,对很多规则死记硬背。后续在阅读《C专家编程》之后,尝试在编译器的角度来理解C/C++的声明解析,并且编写代码将这部分逻辑串联起来,之后再看到许多看似复杂的声明,也能够很好的理解和消化了。

1.复杂的声明

在编写C/C++代码时偶尔能看到如下的复杂声明:float(*(*e[10])(int*))[5]。我想你的第一反应一定是:MMP。虽然我们在实际工作之中是很少出现这种极其复杂的声明逻辑,同时也不提倡使用这样的声明。但是学会理解和解析这类复杂的声明逻辑,可以更好的理解C/C++之中诸个关键词是如何进行组织,来表达逻辑的,也能更好的理解各个关键词的使用方式。

比如之前笔者写的一篇文章之中整理了C/C++之中const关键词的用法

万变而不离其中,总结出规律之后,再复杂的模型也可以简化成我们可以理解的单元来处理。所以我们先来看看C/C++声明的优先级规则

掌握了上述的优先级规则之后,我们回到本文一开始举的一个小栗子
float(*(*e[10])(int*))[5],我们依照上文的逻辑来解析这个声明。

1.找到声明e,e将作为声明的名字。

2.处理后缀操作符,也就是e代表的是一个容量为10的数组。

3.回到前缀操作符,该数组存储的内容为指针。

4.跳出括号,开始新的一轮的优先级规则,处理后缀操作符(),我们
发现这个指针指向的是一个参数为int*的函数。

5.接着再次回到前缀操作符,所以这个函数返回值依然是一个指针。

6.跳出括号,继续前文的逻辑,我们发现该指针指向了一个内容为float,容量为5的数组。

通过上述栗子我们不难发现,对于声明的处理本质上是一个有限自动机的状态变化过程,所以编译器同样也是按照上述的规律来理解并处理程序的复杂声明的。了解了优先级规则,我们也就不难去实现一个简单的小程序cdecl来处理声明逻辑了。

3.简单的代码实现

通过上述流程的说明,我们很容易想到可以用来保存声明标识符左边的内容,而名字右边的内容则依照优先级规则依次处理。(优先处理数组与函数)。

enum type_tag {IDENTIFIER,QUALIFIER,TYPE,POINTER,LPAREN,\
LBRACKET,RPAREN,RBRACKET};struct token {
    type_tag type;    string content;
};
void read_to_first_identifer() {
    gettoken();    while (this_t.type != IDENTIFIER) {
        token_stack.push(this_t);
        gettoken();
    }    cout << this_t.content + " is ";
    gettoken();
}
void deal_with_declarator(){    switch (this_t.type) {        case LBRACKET:deal_with_arrays();break;        case LPAREN:deal_with_function_args();
    }

    deal_with_pointers();    while(!token_stack.empty()) {        if(token_stack.top().type == LPAREN) {
            token_stack.pop();
            gettoken();
            deal_with_declarator();
        } else {            cout << token_stack.top().content + " ";
            token_stack.pop();
        }
    }

}
void deal_with_arrays() {    while (this_t.type == LBRACKET) {        cout << "array ";
        gettoken();        if(isdigit(this_t.content[0])) {            printf("0....%d of ",atoi(this_t.content.c_str()) - 1);
            gettoken();
        }

        gettoken();
    }
}
void deal_with_function_args() {    while(this_t.type != RPAREN) {
        gettoken();
    }
    gettoken();    cout << "function returning ";
}

所以通过上述的代码串联起来,我们就可以简单的完成一个解析C/C++声明的小程序。尝试这个小程序解析笔者在本文提出的示例:

webp

用代码进行声明解析


上述实现代码的
完整版,笔者放在了自己的github之上,需要的可以自取。《C专家编程》之中也有对应C语言版本,需要的也可以用作参考。



作者:LeeHappen
链接:https://www.jianshu.com/p/20b8b542d971


點擊查看更多內(nèi)容
TA 點贊

若覺得本文不錯,就分享一下吧!

評論

作者其他優(yōu)質(zhì)文章

正在加載中
  • 推薦
  • 評論
  • 收藏
  • 共同學習,寫下你的評論
感謝您的支持,我會繼續(xù)努力的~
掃碼打賞,你說多少就多少
贊賞金額會直接到老師賬戶
支付方式
打開微信掃一掃,即可進行掃碼打賞哦
今天注冊有機會得

100積分直接送

付費專欄免費學

大額優(yōu)惠券免費領(lǐng)

立即參與 放棄機會
微信客服

購課補貼
聯(lián)系客服咨詢優(yōu)惠詳情

幫助反饋 APP下載

慕課網(wǎng)APP
您的移動學習伙伴

公眾號

掃描二維碼
關(guān)注慕課網(wǎng)微信公眾號

舉報

0/150
提交
取消