色哟哟视频在线观看-色哟哟视频在线-色哟哟欧美15最新在线-色哟哟免费在线观看-国产l精品国产亚洲区在线观看-国产l精品国产亚洲区久久

0
  • 聊天消息
  • 系統消息
  • 評論與回復
登錄后你可以
  • 下載海量資料
  • 學習在線課程
  • 觀看技術視頻
  • 寫文章/發帖/加入社區
會員中心
創作中心

完善資料讓更多小伙伴認識你,還能領取20積分哦,立即完善>

3天內不再提示

如何判定全局變量和局部變量

strongerHuang ? 來源:strongerHuang ? 作者:strongerHuang ? 2022-09-07 09:08 ? 次閱讀

何為變量?

變量一般可以細分為如下圖:

7f0d0b24-2e45-11ed-ba43-dac502259ad0.png

本節重點為了讓大家理解內存模型的“棧”,暫時不考慮“靜態變量” 的情況,并約定如下:

“全局變量”僅僅默認為“普通全局變量”;

“局部變量”僅僅默認為“普通局部變量”。

如何判定全局變量和局部變量?

簡單直觀的來說,全局變量就是在函數外面定義的變量,局部變量就是在函數內部定義的變量,下面的例子能很清晰地說明全局變量和局部變量的判定方法:

unsigned char a;//在函數外面定義的,所以是全局變量。
voidmain()//主函數
{
 unsigned char b;//在函數內部定義的,所以是局部變量。
b=a;
while(1)
{

}
}

全局變量和局部變量的內存模型

單片機內存包括ROMRAM 兩部分,ROM存儲的是單片機程序中的指令和一些不可更改的常量數據,而 RAM存放的是可以被更改的變量數據;

也就是說,全局變量和局部變量都是存放在RAM,但是,雖然都是存放在 RAM,全局變量和局部變量之間的內存模型還是有明顯的區別的。

因此,分了兩個不同的RAM區,全局變量占用的 RAM區稱為全局數據區, 局部變量占用的 RAM 區稱為

它們的內存模型到底有什么本質的區別呢?

全局數據區就像你自己家的房間,是唯一的,一個房間的地址只能你一個人住(假設你還是單身狗的時候),而且是永久的(sorry),所以說每個全局變量都有唯一對應的 RAM 地址, 不可能重復的。

就像客棧, 一年下來每天晚上住的人不一樣,每個人在里面居住的時間是有期限的,不是長久的,一個房間的地址一年下來每天可能住進不同的人,不是唯一的。

全局數據區的全局變量擁有永久產權,區的局部變量只能臨時居住在賓館客棧, 地址不是唯一的, 有期限的。

是給程序里所有函數內部的局部變量共用的,函數被調用的時候,該函數內部的每個局部變量就會被分配對應到的某個RAM 地址,函數調用結束后,該局部變量就失效。

因此它對應的 的RAM空間就被收回,以便給下一個被調用的函數的局部變量占用。

舉例借用“賓館客棧”來比喻局部變量所在的“棧”。

voidfunction(void);//子函數的聲明

voidfunction(void)//子函數的定義
{
unsignedchara;//局部變量
a=1;
}

voidmain()//主函數
{
function();//子函數的調用
}

我們看到單片機從主函數 main 往下執行, 首先遇到function()子函數的調用, 所以就跳到function()函數的定義那里開始執行, 此時的局部變量 a 開始被分配在 RAM的“棧區” 的某個地址, 相當于你入住賓館被分配到某個房間。

單片機執行完子函數function() 后,局部變量 a 在 RAM 的棧區所分配的地址被收回, 局部變量a 消失,被收回的RAM地址可能會被系統重新分配給其它被調用的函數的局部變量。

此時相當于你離開賓館,從此你跟那個賓館的房間沒有啥關系, 你原來在賓館入住的那個房間會被賓館老板重新分配給其他的客人入住。

全局變量的作用域是永久性不受范圍限制的,而局部變量的作用域就是它所在函數的內部范圍。全局變量的全局數據區是永久的私人房子,局部變量的棧是臨時居住的客棧。

總結如下

每定義一個新的全局變量,就意味著多開銷一個新的RAM 內存。而每定義一個局部變量,只要在函數內部所定義的局部變量總數不超過單片機的棧區,此時的局部變量不開銷新的 RAM內存, 因為局部變量是臨時借用棧的, 使用后就還給棧,棧是公共區, 可以重復利用,可以服務若干個不同的函數內部的局部變量。

單片機每次進入執行函數時,局部變量都會被初始化改變,而全局變量則不會被初始化, 全局變量是一直保存之前最后一次更改的值。

有哪些常見疑問?

全局數據區棧區是誰在幕后分配的, 怎么分配的?

是C編譯器自動分配的, 至于怎么分配,誰分配多一點,誰分配少一點,C 編譯器會有一個默認的比例分配, 我們一般都不用管。

棧區是臨時借用的,子函數被調用的時候,它內部的局部變量才會“臨時” 被分配到“棧” 區的某個地址,那么問題來了,誰在幕后主持“棧區” 這些分配的工作?

單片機已經上電開始運行程序的時候,編譯器已經不起作用,“棧區” 分配給函數內部局部變量的工作,確實是 C 編譯器做的,但這是在單片機上電前。

C 編譯器就把所有函數內部的局部變量的分配工作就規劃好了,都指定了如果某個函數一旦被調用,該函數內部的哪個局部變量應該分到“棧區” 的哪個地址,C 編譯器都是事先把這些“后事” 都交代完畢了才結束自己的生命。

等單片機上電開始工作的時候,雖然C編譯器此時不在了,但是單片機都是嚴格按照C編譯器交代的遺囑開始工作和分配“棧區”的。因此,“棧區” 的“臨時分配” 非真正嚴格意義上的“臨時分配”。

函數內部所定義的局部變量總數不超過單片機的“棧” 區的 RAM 數量, 那, 萬一超過了“棧” 區的 RAM數量, 后果嚴重嗎?

這種情況專業術語叫爆棧。程序會出現莫名其妙的異常,后果特別嚴重。

為了避免這種情況, 一般在編寫程序的時候, 函數內部都不能定義大數組的局部變量, 局部變量的數量不能定義太多太大,尤其要避免剛才所說的定義開辟大數組局部變量這種情況。

大數組的定義應該定義成全局變量,或者定義成 靜態的局部變量

有一些C編譯器,遇到“爆棧” 的情況,會好心跟你提醒讓你編譯不過去,但是也有一些 C 編譯器可能就不會給你提醒,所以大家以后做項目寫函數的時候,要對爆棧心存敬畏。

全局變量和局部變量的優先級

剛才說到,全局變量的作用域是永久性并且不受范圍限制的,而局部變量的作用域就是它所在函數的內部范圍。

那么問題來了,假如局部變量和全局變量的名字重名了,此時函數內部執行的變量到底是局部變量還是全局變量?

這個問題就涉及到優先級。

注意,當面對同名的局部變量和全局變量時,函數內部執行的變量是局部變量,也就是局部變量在函數內部要比全局變量的優先級高。

我們來舉一些例子

請看下面第一個例子

unsignedchara=5;//此處第1個a是全局變量

voidmain()//主函數
{
unsignedchara=2;//此處第2個a是局部變量,跟上面全局變量的第1個a重名了
print(a);//把a發送到電腦端的串口助手軟件上觀察
while(1)
{

}
}

正確的答案是 2。在函數內部的局部變量比全局變量的優先級更加高。

雖然這里的兩個a重名了, 但是它們的內存模型不一樣,第1個全局變量的a是分配在全局數據區,是具有唯一的地址的,而第2個局部變量的a是被分配在臨時的棧區的,寄生在 main 函數內部。

再看下面第二個例子

voidfunction(void);//函數聲明
unsignedchara=5;//此處第1個a是全局變量

voidfunction(void)//函數定義
{
 unsigned char a=3;//此處第 2 個 a 是局部變量。
}

voidmain()//主函數
{
 unsigned char a=2;//此處第 3 個 a 也是局部變量。
function();//子函數被調用
print(a);//把 a 發送到電腦端的串口助手軟件上觀察。
while(1)
{
}
}

正確的答案是2。因為,function這個子函數是被調用結束之后,才執行 print(a)的, 就意味函數內部的局部變量(第2個局部變量 a)是在執行 print(a)語句的時候就消亡不存在了, 所以此時print(a)的a是第3個局部變量的a(在 main 函數內部定義的局部變量的 a)。

再看下面第三個例子

voidfunction(void);//函數聲明
unsignedchara=5;//此處第1個a是全局變量

voidfunction(void)//函數定義
{
unsignedchara=3;//此處第2個a是局部變量
}

voidmain()//主函數
{
function();//子函數被調用
print(a);//把a發送到電腦端的串口助手軟件上觀察
while(1)
{
}
}

正確的答案是5。因為function這個子函數是被調用結束之后,才執行print(a)的,就意味function函數內部的局部變量(第2個局部變量)是在執行function(a)語句的時候就消亡不存在了。

同時,因為此時main函數內部也沒有定義a的局部變量,所以此時function(a)的a是必然只能是第1個全局變量的a(在main函數外面定義的全局變量的a)。

最后

看到本文之后,相信大家已經對棧有了一些基礎的認識,在嵌入式編程中,我們也要時刻注意,避免爆棧;如果有錯誤歡迎指出,我們下一期,再見。

審核編輯:彭靜
聲明:本文內容及配圖由入駐作者撰寫或者入駐合作網站授權轉載。文章觀點僅代表作者本人,不代表電子發燒友網立場。文章及其配圖僅供工程師學習之用,如有內容侵權或者其他違規問題,請聯系本站處理。 舉報投訴
  • 存儲
    +關注

    關注

    13

    文章

    4328

    瀏覽量

    85942
  • 函數
    +關注

    關注

    3

    文章

    4338

    瀏覽量

    62739
  • 模型
    +關注

    關注

    1

    文章

    3261

    瀏覽量

    48914

原文標題:從嵌入式編程中感悟「棧」為何方神圣?

文章出處:【微信號:strongerHuang,微信公眾號:strongerHuang】歡迎添加關注!文章轉載請注明出處。

收藏 人收藏

    評論

    相關推薦

    labview深入探索------全局變量局部變量與內存管理

    不存在全局變量和局部變量,同樣可以編制規模很大的程序,這說明局部變量全局變量并不是必須的,LV提供了它們是因為在特定的情況下可以簡化編程。當我們使用SUBVI時,我們需要定義一個連接
    發表于 07-13 17:49

    LabVIEW結構的使用——全局變量和局部變量

    全局變量和局部變量是LabVIEW用來傳遞數據的工具。LabVIEW編程是一種數據流編程,它是通過連線來傳遞數據的。但是如果一個程序太復雜的話,有時連線會很困難甚至無法連接,這時就需要用到局部變量
    發表于 02-09 14:46

    LabVIEW編程難點之局部變量全局變量

    最近學習Labview,找了3、4本書看,但是對局部變量全局變量的說法不是特別清晰,就此跟大家討論下:Labview中局部變量是在一個VI中傳遞數據,如果說創建了前面板某個數值輸入控件類型為
    發表于 01-08 20:46

    謹慎使用局部變量全局變量

    局部全局變量是高級的LabVIEW概念。它們不是LabVIEW數據流執行模型中固有的部分。使用局部變量全局變量時,程序框圖可能會變得難以閱讀,因此需謹慎使用。錯誤地使用
    發表于 01-30 10:58

    靜態變量全局變量和局部變量

    域。全局變量只需在一個源文件中定義,就可以作用于所有的源文件。當然,其他不包含全局變量定義的源文件需要用extern關鍵字再次聲明這個全局變量。2>靜態局部變量具有
    發表于 06-20 09:52

    【原創分享】STM32 C語言全局變量和局部變量

    作者:張角老師(張飛實戰電子高級工程師)大家好,我們今天來探討一下C語言的全局變量和局部變量。如果我們想徹底搞清楚這兩個概念,我們必須回答幾個問題:第一,C語言為什么要區分變量的作用域,或者說做出
    發表于 06-17 11:18

    全局變量和局部變量的相關資料推薦

    一些注意事項:全局變量和局部變量重名以后,根據就近原則,打印會顯示局部變量的值,可在變量前加入::代表全部變量;應減少不必要的全部
    發表于 12-15 06:10

    編程時可以用局部變量替代全局變量

    盡量用局部變量替代全局變量。如果用局部變量能實現功能,最好用局部變量。在函數僅僅只是要用到某個全局變量,而無需改動時,就將
    發表于 02-28 06:22

    static作用(修飾函數、局部變量全局變量

    詳細介紹了static作用(修飾函數、局部變量全局變量)的用法
    發表于 11-17 10:30 ?4次下載

    全局變量和局部變量有什么區別

    全局變量是編程術語中的一種,源自于變量之分。變量分為局部全局局部變量又可稱之為內部
    發表于 12-11 11:58 ?3.3w次閱讀
    <b class='flag-5'>全局變量</b><b class='flag-5'>和局部變量</b>有什么區別

    LABVIEW初級教程之局部變量全局變量的示例程序合集免費下載

    本文檔的主要內容詳細介紹的是LABVIEW初級教程之局部變量全局變量的示例程序合集免費下載
    發表于 01-16 10:23 ?34次下載
    LABVIEW初級教程之<b class='flag-5'>局部變量</b>與<b class='flag-5'>全局變量</b>的示例程序合集免費下載

    在C語言中,全局變量濫用的后果是什么

    01 啥是全局變量 說起全局變量,就不得不提到全局變量局部變量,靜態全局變量,靜態局部變量,這
    發表于 06-24 17:14 ?1662次閱讀

    C語言中局部變量全局變量

    全局變量也稱為外部變量,它是在函數外部定義的變量。它不屬于哪一個函數,它屬于一個源程序文件。其作用域是整個源程序。在函數中使用全局變量,一般應作全局
    的頭像 發表于 10-15 10:48 ?5604次閱讀

    詳解LABVIEW中的局部變量全局變量

    本文檔的主要內容詳細介紹的是LABVIEW初級教程之局部變量全局變量的詳細資料說明。
    發表于 03-29 15:00 ?26次下載

    Python-局部變量全局變量

    局部變量是在函數內部定義的變量,只能在函數內部使用,函數執行結束后,函數內部的局部變量會被系統回收,不同的函數,可以定義相同名稱的局部變量,相互之間沒有任何關聯
    的頭像 發表于 02-16 15:16 ?911次閱讀
    Python-<b class='flag-5'>局部變量</b>與<b class='flag-5'>全局變量</b>
    主站蜘蛛池模板: 色综合色综合久久综合频道| 女子叉开腿让男子桶免费软件| 久久黄色免费| 受喷汁红肿抽搐磨NP双性| NANANA在线观看高清影院| 老司机福利在视频在ae8| 亚洲视频网站欧美视频网站| 国产成人精品s8p视频| 美女动态图真人后进式| 伊人久久精品99热超碰| 一本大道手机在线看| 国内国外精品影片无人区| 色婷婷99综合久久久精品| 成人影片迅雷下载| 日本红怡院亚洲红怡院最新| 不卡的在线AV网站| 国色天香视频在线社区| 亚洲国产精品嫩草影院久久| 国产精品自在拍在线播放| 午夜福利08550| 国产亚洲视频在线| 夜里18款禁用的免费B站动漫| 火影忍者高清无码黄漫| 影音先锋 av天堂| 美国69xxxx59| 变形金刚7免费观看完整| 日日夜夜噜噜| 国产曰批试看免费视频播放免费| 亚洲伊人久久综合影院2021| 美女18黄| 成人天堂婷婷青青视频在线观看| 色综合色综合久久综合频道| 国产亚洲精品精华液| 亚洲色图另类小说| 精品亚洲麻豆1区2区3区 | 精品国产露脸久久AV麻豆| 亚洲精品无码专区在线播放| 久久久视频2019午夜福利| gogogo高清在线观看| 试看2分钟AA片| 久久99国产精品一区二区|