欧美色欧美亚洲高清在线观看,国产特黄特色a级在线视频,国产一区视频一区欧美,亚洲成a 人在线观看中文

  1. <ul id="fwlom"></ul>

    <object id="fwlom"></object>

    <span id="fwlom"></span><dfn id="fwlom"></dfn>

      <object id="fwlom"></object>

      單片機(jī)c語(yǔ)言學(xué)習(xí)心得轉(zhuǎn)載

      時(shí)間:2019-05-13 01:12:47下載本文作者:會(huì)員上傳
      簡(jiǎn)介:寫(xiě)寫(xiě)幫文庫(kù)小編為你整理了多篇相關(guān)的《單片機(jī)c語(yǔ)言學(xué)習(xí)心得轉(zhuǎn)載》,但愿對(duì)你工作學(xué)習(xí)有幫助,當(dāng)然你在寫(xiě)寫(xiě)幫文庫(kù)還可以找到更多《單片機(jī)c語(yǔ)言學(xué)習(xí)心得轉(zhuǎn)載》。

      第一篇:?jiǎn)纹瑱C(jī)c語(yǔ)言學(xué)習(xí)心得轉(zhuǎn)載

      單片機(jī)c語(yǔ)言學(xué)習(xí)心得

      (一)相信很多愛(ài)好電子的朋友,對(duì)單片機(jī)這個(gè)詞應(yīng)該都不會(huì)陌生了吧。不過(guò)有些朋友可能只聽(tīng)說(shuō)他叫單片機(jī),他的全稱(chēng)是什么也許并不太清楚,更不用說(shuō)他的英文全稱(chēng)和簡(jiǎn)稱(chēng)了。單片機(jī)是一塊在集成電路芯片上集成了一臺(tái)有一定規(guī)模的微型計(jì)算機(jī)。簡(jiǎn)稱(chēng)為:?jiǎn)纹⑿陀?jì)算機(jī)或單片機(jī)(Single Chip Computer)。單片機(jī)的應(yīng)用到處可見(jiàn),應(yīng)用領(lǐng)域廣泛,主要應(yīng)用在智能儀表、實(shí)時(shí)控制、通信、家電等方面。不過(guò)這一切都沒(méi)什么關(guān)系,因?yàn)槲遥ó?dāng)然也包括任何人)都是從不知道轉(zhuǎn)變成知道的,再轉(zhuǎn)變成精通的?,F(xiàn)在我只想把我學(xué)習(xí)單片機(jī)的經(jīng)歷,詳細(xì)地講敘給大家聽(tīng)聽(tīng),可能有些大蝦會(huì)笑話(huà)我,想:那么簡(jiǎn)單的東西還在這里賣(mài)弄。但是你錯(cuò)了,我只是把我個(gè)人學(xué)習(xí)的經(jīng)歷講述一遍而已,僅僅對(duì)那些想學(xué)習(xí)單片機(jī),但又找不到好方法或者途徑的朋友,提供一個(gè)幫助,使他們?cè)趯W(xué)習(xí)過(guò)程中,盡量少走些彎路而已!

      首先,你必須有學(xué)習(xí)單片機(jī)的熱情,不是說(shuō)今天去圖書(shū)館看了一個(gè)下午關(guān)于單片機(jī)的書(shū),而明天玩上半天,后天就不知道那個(gè)本書(shū)在講什么東西了。還是先說(shuō)說(shuō)我吧,我從大二的第一個(gè)學(xué)期期末的時(shí)候才開(kāi)始接觸單片機(jī),但在這之前,正如上面所說(shuō)的:我知道有種芯片叫單片機(jī),但是具體長(zhǎng)成什么樣子,卻一點(diǎn)也不知道!看到這里很多朋友一定會(huì)忍不住發(fā)笑。嘿嘿,你可千萬(wàn)別笑,有些大四畢業(yè)的人也同樣不知道單片機(jī)長(zhǎng)成什么樣子呢!而我對(duì)單片機(jī)的癡迷更是常人所不能想象的地步,大二的期末考試,我全放棄了復(fù)習(xí),每當(dāng)室友拿著書(shū)在埋頭復(fù)習(xí)的時(shí)候,我卻捧著自己從圖書(shū)館借的單片機(jī)書(shū)在那看,雖然有很多不懂,但是我還是堅(jiān)持了下來(lái),當(dāng)時(shí)我就想過(guò),為了單片機(jī)值不值得我這樣去付出,或許這也是在一些三流學(xué)校的好處吧,考試掛科后,明年開(kāi)學(xué)交上幾十元一門(mén)的補(bǔ)考費(fèi),應(yīng)該大部分都能過(guò)了。于是,我橫下一條心,堅(jiān)持看我的單片機(jī)書(shū)和資料。當(dāng)你明白了單片機(jī)是這么一回事的時(shí)候,顯而易見(jiàn)的問(wèn)題出來(lái)了:我要選擇那種語(yǔ)言為單片機(jī)編寫(xiě)程序呢?這個(gè)問(wèn)題,困擾了我好久。具體選擇C51還是A51呢?匯編在我們大二之前并沒(méi)有開(kāi)過(guò)課,雖然看著人家的講解,很容易明白單片機(jī)的每一時(shí)刻的具體工作情況,但是一合上書(shū)或者資料,自己卻什么也不知道了,根本不用說(shuō)自己寫(xiě)程序了。于是,我最終還是決定學(xué)C51,畢竟C51和我們課上講的C語(yǔ)言,有些類(lèi)似,編程的思想可以說(shuō)是相通的。而且C51還有更大的優(yōu)點(diǎn)就是編寫(xiě)大程序時(shí)的優(yōu)越性更不言而喻,當(dāng)然在那時(shí),我并沒(méi)有想的那么深遠(yuǎn),C51的特點(diǎn),還是在后來(lái)的實(shí)踐過(guò)程中,漸漸體會(huì)到的!朋友如果你選擇了C51,那么請(qǐng)繼續(xù)往下看,如果你選擇了A51,那么你可以不要看了!因?yàn)橄旅嬷v的全是C方面的,完全在浪費(fèi)你的時(shí)間!呵呵 ^_^

      第二,既然你想學(xué)好單片機(jī),你必須得舍得花錢(qián),如果不買(mǎi)些芯片回來(lái)自己動(dòng)手焊焊拆拆的(但是在后期會(huì)介紹給大家一個(gè)很好用的硬件仿真軟件,并不需要你用實(shí)驗(yàn)板和仿真器了,直接在你的PC上完成,但是軟件畢竟是軟件,從某個(gè)特定的意義上來(lái)說(shuō)是并不能代替硬件的),即使你每天捧著本書(shū),把那本書(shū)翻爛,也永遠(yuǎn)學(xué)不會(huì)單片機(jī)的!剛接觸單片機(jī)的朋友,看了資料,一定會(huì)對(duì)以下幾個(gè)詞見(jiàn)的比較多,但是具體的概念還是比較模糊,現(xiàn)作如下說(shuō)明:

      (1)編程器編程器是用來(lái)燒單片機(jī)芯片的,是把HEX或者BIN文件燒到單片機(jī)ROM里的。

      (2)實(shí)驗(yàn)板實(shí)驗(yàn)板是專(zhuān)為初學(xué)者根據(jù)某些要求而特做的板,一般上面就有一個(gè)單片機(jī)的最小系統(tǒng),使用者只需寫(xiě)好程序,燒好芯片,放到上面加以驗(yàn)證的這么一個(gè)工具。有了實(shí)驗(yàn)板,對(duì)與初學(xué)者來(lái)說(shuō),省去了焊?jìng)€(gè)最小系統(tǒng)的麻煩。但是對(duì)于電子開(kāi)發(fā)人員來(lái)說(shuō),作用并不是很大

      (3)仿真器仿真器是直接把HEX或者BIN文件暫時(shí)放在一個(gè)芯片里,再通過(guò)這個(gè)芯片的引腳連接到實(shí)驗(yàn)板或者系統(tǒng)上工作。這樣以來(lái),可以省去了來(lái)回插拔芯片帶來(lái)的不必要麻煩。

      我一開(kāi)始也不知道上面3個(gè)的概念和作用,嘿嘿,原本想買(mǎi)個(gè)實(shí)驗(yàn)板(不想焊板,因?yàn)椴豢赡転榱它c(diǎn)亮幾個(gè)流水燈,而去焊?jìng)€(gè)單片機(jī)的最小系統(tǒng))的,可是結(jié)果,確和我想的正好相反,人家出售的是編程器。等貨物寄到后,才知道自己搞錯(cuò)了!汗。。嘿嘿?,F(xiàn)在想想實(shí)在是又氣又笑。我花了160大樣買(mǎi)了個(gè)編程器(很不幸的是,這個(gè)編程器更本用不了,一燒芯片,芯片就燒壞了)把我給氣的,這個(gè)編程器,現(xiàn)在還躺在我的抽屜里呢不過(guò),現(xiàn)在想想,唯一讓我覺(jué)得欣慰的是,那個(gè)老板每次能解答我的問(wèn)題,連那種超級(jí)幼稚的問(wèn)題,他也能不嫌麻煩地盡量幫我解答!這點(diǎn)讓我很感動(dòng)!

      第三,想學(xué)單片機(jī)的必需品--PC。因?yàn)閷?xiě)程序,編譯或者是仿真都是通過(guò)PC完成的。如果沒(méi)有PC,什么也做不了??!有了PC最好還要可以上網(wǎng),因?yàn)槿绻銢](méi)有可以和你交流單片機(jī)的人,遇到自己解決不了的問(wèn)題,一直都想不通,那么估計(jì)你學(xué)習(xí)單片機(jī)的熱情就會(huì)隨著時(shí)間的推移而慢慢耗盡。如果你能上網(wǎng)通過(guò)論壇或者QQ群,問(wèn)題就很快得到解決。這樣的學(xué)習(xí)效率一定很高!真正的高手是從論壇中泡出來(lái)的!

      有了上述3個(gè)條件后,你就可以開(kāi)始學(xué)你的單片機(jī)了。但是,真的做起來(lái)并沒(méi)有我所說(shuō)的那么簡(jiǎn)單。你一定會(huì)遇到很多很多的問(wèn)題。比如為了讓單片機(jī)實(shí)現(xiàn)某個(gè)功能,你可能不知道怎么去寫(xiě)某個(gè)程序?;蚴悄憧炊速Y料上某個(gè)相似的程序,你自己卻寫(xiě)不出來(lái)。遇到類(lèi)似的情況,記?。呵f(wàn)不要急噪,就行!

      (二)說(shuō)了這么多了,相信你也看了很多資料了,手頭應(yīng)該也有必備的工具了吧?。ú灰松厦嬷v過(guò)幾個(gè)條件的哦)。那個(gè)單片機(jī)究竟有什么功能和作用呢?先不要著急!接下來(lái)讓我們點(diǎn)亮一個(gè)LED(搞電子的應(yīng)該知道LED是什么吧^_^)我們?cè)趩纹瑱C(jī)最小系統(tǒng)上接個(gè)LED,看我們能否點(diǎn)亮它!對(duì)了,上面也有好幾次提到過(guò)單片機(jī)最小系統(tǒng)了,所謂單片機(jī)最小系統(tǒng)就是在單片機(jī)上接上最少的外圍電路元件讓單片機(jī)工作。一般只須連接晶體、VCC、GND、RST即可,一般情況下,AT89C51的31腳須接高電平。

      #include//頭文件定義。或用#include其具體的區(qū)別在于:后者定義了更多的地址空間。

      //在Keil安裝文件夾中,找到相應(yīng)的文件,比較一下便知!sbit P1_0 = P1 ^ 0;

      void main(void)

      {

      while(1)

      {

      P1_0 = 0;//低電平有效,如果把LED反過(guò)來(lái)接那么就是高電平有效}

      }

      就那么簡(jiǎn)單,我們就把接在單片機(jī)P1_0上的LED點(diǎn)亮了,當(dāng)然LED是低電平,才能點(diǎn)亮。因?yàn)槲覀儼袻ED的正通過(guò)電阻接至VCC。

      P1_0 = 0;類(lèi)似與C語(yǔ)言中的賦值語(yǔ)句,即把 0 賦給單片機(jī)的P1_0引腳,讓它輸出相應(yīng)的電平。那么這樣就能達(dá)到了我們預(yù)先的要求了。while(1)語(yǔ)句只是讓單片機(jī)工作在死循環(huán)狀態(tài),即一直輸出低電平。如果我們要試著點(diǎn)亮其他的LED,也類(lèi)似上述語(yǔ)句。這里就不再講了。

      點(diǎn)亮了幾個(gè)LED后,是不是讓我們聯(lián)想到了繁華的街區(qū)上流動(dòng)的彩燈。我們是不是也可以讓幾個(gè)LED依次按順序亮呢?答案是肯定的!其實(shí)顯示的原理很簡(jiǎn)單,就是讓一個(gè)LED滅后,另一個(gè)立即亮,依次輪流下去。假設(shè)我們有8個(gè)LED分別接在P1口的8個(gè)引腳上。硬件連接,在P1_1--P1_7上再接7個(gè)LED即可。例程如下:

      #include

      sbit P1_0 = P1 ^ 0;

      sbit P1_1 = P1 ^ 1;

      sbit P1_2 = P1 ^ 2;

      sbit P1_3 = P1 ^ 3;

      sbit P1_4 = P1 ^ 4;

      sbit P1_5 = P1 ^ 5;

      sbit P1_6 = P1 ^ 6;

      sbit P1_7 = P1 ^ 7;

      void Delay(unsigned char a)

      {

      unsigned char i;

      while(--a!= 0)

      {

      for(i = 0;i < 125;i++);//一個(gè);表示空語(yǔ)句,CPU空轉(zhuǎn)。

      }//i 從0加到125,CPU大概就耗時(shí)1毫秒}

      void main(void)

      {

      while(1)

      {

      P1_0 = 0;

      Delay(250);

      P1_0 = 1;

      P1_1 = 0;

      Delay(250);

      P1_1 = 1;

      P1_2 = 0;

      Delay(250);

      P1_2 = 1;

      P1_3 = 0;

      Delay(250);

      P1_3 = 1;

      P1_4 = 0;

      Delay(250);

      P1_4 = 1;

      P1_5 = 0;

      Delay(250);

      P1_5 = 1;

      P1_6 = 0;

      Delay(250);

      P1_6 = 1;

      P1_7 = 0;

      Delay(250);

      P1_7 = 1;

      }

      }

      sbit 定義位變量,unsigned char a 定義無(wú)符字符型變量a,以節(jié)省單片機(jī)內(nèi)部資源,其有效值為0~255。main函數(shù)調(diào)用Delay()函數(shù)。Delay函數(shù)使單片機(jī)空轉(zhuǎn),LED持續(xù)點(diǎn)亮后,再滅,下一個(gè)LED亮。while(1)產(chǎn)生循環(huán)。

      第二篇:?jiǎn)纹瑱C(jī)C語(yǔ)言學(xué)習(xí)心得

      8、指針的使用

      8.1 在定義的時(shí)候,*ap中的‘*’是指針類(lèi)型說(shuō)明符;

      在進(jìn)行指針預(yù)算時(shí),x = *ap 中的‘*’是指針運(yùn)算符。8.2 如果在已定義好的指針變量,并引用,即

      int *ap, int a;ap = &a;則在進(jìn)行指針運(yùn)算的時(shí)候:

      (1)*ap與a是等價(jià)的,即 *ap就是a;

      (2)&*ap:由于*ap與a等價(jià),則&*ap與&a等價(jià)(地址);

      (3)*&a:由于&a = ap,則*&a與*ap等價(jià),即*&a與a等價(jià)(變量);(4)*ap++相當(dāng)于a++。

      8.3 指向數(shù)組的指針變量的定義,應(yīng)用,賦值:

      int a[10];int *app;則有兩種方法:app = &a[0];或 app = &a;(1)app+I 或a+i就是數(shù)組元素a[i]的地址;(2)*(app+i)或 *(a+i)就是元素a[i]中的內(nèi)容;

      (3)指針變量也可以帶下表,即app[i]與*(app+i)等價(jià)。8.4 數(shù)組和指針可以互換,但在代碼執(zhí)行的效率上卻大不相同。用數(shù)組找元素必須每次計(jì)算元素的地址,效率不高;而用指針則直接指向某個(gè)元素,不必每次計(jì)算地址,可以大大的提高運(yùn)算效率。8.5 關(guān)于指針的運(yùn)算:

      (1)p++(或p+=1):使指針p指向下一個(gè)數(shù)組元素,地址加1;

      (2)*p++:先得到p指向的變量值,再執(zhí)行p加1,指向下一個(gè)數(shù)組元素;(3)*++p:先使p加1,指向下一個(gè)數(shù)組元素,再去p指向的變量值;(4)(*p)++:表示p指向的變量值加1;

      (5)若p指向當(dāng)前數(shù)組中的第i個(gè)元素,則:

      (p--)與a[i--] 等價(jià):先執(zhí)行*p,然后p自減;(++p)與a[++i] 等價(jià):先執(zhí)行p自加,再執(zhí)行*p;(--p)與a[--p] 等價(jià):先執(zhí)行p自減,再執(zhí)行*p。

      8.6 指向多維數(shù)組:

      定義一個(gè)二維數(shù)組:a[3][4];定義一個(gè)指針變量:(*p)[4];(注意:列數(shù)相同(第二維相同))使指針變量指向數(shù)組:p = a;此時(shí): p與a等價(jià):指向數(shù)組a[3][4]的第0行首地址;

      p+1與a+1等價(jià):指向數(shù)組a[3][4]的第1行首地址; p+2與a+2等價(jià):指向數(shù)組a[3][4]的第2行首地址;

      而:

      *(p+1)+3與& a[1][3]等價(jià),指向a[1][3]的地址;

      *(*(p+1)+3)與a[1][3]等價(jià),表示a[1][3]的值; 一般的:對(duì)于數(shù)組a[i][j]來(lái)講,有

      *(p+i)+j相當(dāng)于&a[i][j],表示第i行第j列元素的地址; *(*(p+i)+j)相當(dāng)于a[i][j],表示第i行第j列元素的值。

      8.7 指向結(jié)構(gòu)體:

      如果指針p指向結(jié)構(gòu)體數(shù)組msg1[0]的首地址,則:

      (1)(*p).flg與p->flg和msg1[0].flg三者完全等價(jià),即(*p).成員名 與p->成員名 以及 結(jié)構(gòu)體數(shù)組元素成員名三種形式是等價(jià)的;

      (2)p+1:使指針指向結(jié)構(gòu)數(shù)組msg1[0]的下一個(gè)元素msg1[1]的首地址;(3)由于指向運(yùn)算符->的優(yōu)先級(jí)高于自加運(yùn)算符++,則:

      (++p)->flg:先使p自加1指向msg1[1]的地址,再指向msg1[1]的flg成員值;(p++)->flg:先得到msg1[0].flg的值,再使p自加1指向msg1[1]的首地址;

      p->flg++:先得到msg1[0].flg的值,使用完后再使msg1[0].flg的值加1; ++p->flg:先將msg1[0].flg的值加1,再使用。

      第三篇:?jiǎn)纹瑱C(jī)C語(yǔ)言學(xué)習(xí)心得

      8、指針的使用

      8.1 在定義的時(shí)候,*ap中的‘*’是指針類(lèi)型說(shuō)明符;

      在進(jìn)行指針預(yù)算時(shí),x = *ap 中的‘*’是指針運(yùn)算符。

      8.2 如果在已定義好的指針變量,并引用,即

      int *ap, int a;

      ap = &a;

      則在進(jìn)行指針運(yùn)算的時(shí)候:

      (1)*ap與a是等價(jià)的,即 *ap就是a;

      (2)&*ap:由于*ap與a等價(jià),則&*ap與&a等價(jià)(地址);

      (3)*&a:由于&a = ap,則*&a與*ap等價(jià),即*&a與a等價(jià)(變量);

      (4)*ap++相當(dāng)于a++。

      8.3 指向數(shù)組的指針變量的定義,應(yīng)用,賦值:

      int a[10];int *app;

      則有兩種方法:app = &a[0];或 app = &a;

      (1)app+I 或a+i就是數(shù)組元素a[i]的地址;

      (2)*(app+i)或 *(a+i)就是元素a[i]中的內(nèi)容;

      (3)指針變量也可以帶下表,即app[i]與*(app+i)等價(jià)。

      8.4 數(shù)組和指針可以互換,但在代碼執(zhí)行的效率上卻大不相同。用數(shù)組找元素必須每次計(jì)算

      元素的地址,效率不高;而用指針則直接指向某個(gè)元素,不必每次計(jì)算地址,可以大大的提高運(yùn)算效率。

      8.5 關(guān)于指針的運(yùn)算:

      (1)p++(或p+=1):使指針p指向下一個(gè)數(shù)組元素,地址加1;

      (2)*p++:先得到p指向的變量值,再執(zhí)行p加1,指向下一個(gè)數(shù)組元素;

      (3)*++p:先使p加1,指向下一個(gè)數(shù)組元素,再去p指向的變量值;

      (4)(*p)++:表示p指向的變量值加1;

      (5)若p指向當(dāng)前數(shù)組中的第i個(gè)元素,則:

      (p--)與a[i--] 等價(jià):先執(zhí)行*p,然后p自減;

      (++p)與a[++i] 等價(jià):先執(zhí)行p自加,再執(zhí)行*p;

      (--p)與a[--p] 等價(jià):先執(zhí)行p自減,再執(zhí)行*p。

      8.6 指向多維數(shù)組:

      定義一個(gè)二維數(shù)組:a[3][4];定義一個(gè)指針變量:(*p)[4];(注意:列數(shù)相同(第二維相同))

      使指針變量指向數(shù)組:p = a;

      此時(shí): p與a等價(jià):指向數(shù)組a[3][4]的第0行首地址;

      p+1與a+1等價(jià):指向數(shù)組a[3][4]的第1行首地址;

      p+2與a+2等價(jià):指向數(shù)組a[3][4]的第2行首地址;

      而:*(p+1)+3與& a[1][3]等價(jià),指向a[1][3]的地址;*(*(p+1)+3)與a[1][3]等價(jià),表示a[1][3]的值; 一般的:對(duì)于數(shù)組a[i][j]來(lái)講,有*(p+i)+j相當(dāng)于&a[i][j],表示第i行第j列元素的地址; *(*(p+i)+j)相當(dāng)于a[i][j],表示第i行第j列元素的值。

      8.7 指向結(jié)構(gòu)體:

      如果指針p指向結(jié)構(gòu)體數(shù)組msg1[0]的首地址,則:

      (1)(*p).flg與p->flg和msg1[0].flg三者完全等價(jià),即(*p).成員名 與p->成員名 以及 結(jié)

      構(gòu)體數(shù)組元素成員名三種形式是等價(jià)的;

      (2)p+1:使指針指向結(jié)構(gòu)數(shù)組msg1[0]的下一個(gè)元素msg1[1]的首地址;

      (3)由于指向運(yùn)算符->的優(yōu)先級(jí)高于自加運(yùn)算符++,則:

      (++p)->flg:先使p自加1指向msg1[1]的地址,再指向msg1[1]的flg成員值;(p++)->flg:先得到msg1[0].flg的值,再使p自加1指向msg1[1]的首地址; p->flg++:先得到msg1[0].flg的值,使用完后再使msg1[0].flg的值加1; ++p->flg:先將msg1[0].flg的值加1,再使用。

      第四篇:?jiǎn)纹瑱C(jī)c語(yǔ)言學(xué)習(xí)心得(改編)

      單片機(jī)c語(yǔ)言學(xué)習(xí)心得

      (一)相信很多愛(ài)好電子的朋友,對(duì)單片機(jī)這個(gè)詞應(yīng)該都不會(huì)陌生了吧。不過(guò)有些朋友可能只聽(tīng)說(shuō)他叫單片機(jī),他的全稱(chēng)是什么也許并不太清楚,更不用說(shuō)他的英文全稱(chēng)和簡(jiǎn)稱(chēng)了。單片機(jī)是一塊在集成電路芯片上集成了一臺(tái)有一定規(guī)模的微型計(jì)算機(jī)。簡(jiǎn)稱(chēng)為:?jiǎn)纹⑿陀?jì)算機(jī)或單片機(jī)(Single Chip Computer)。單片機(jī)的應(yīng)用到處可見(jiàn),應(yīng)用領(lǐng)域廣泛,主要應(yīng)用在智能儀表、實(shí)時(shí)控制、通信、家電等方面。不過(guò)這一切都沒(méi)什么關(guān)系,因?yàn)槲遥ó?dāng)然也包括任何人)都是從不知道轉(zhuǎn)變成知道的,再轉(zhuǎn)變成精通的?,F(xiàn)在我只想把我學(xué)習(xí)單片機(jī)的經(jīng)歷,詳細(xì)地講敘給大家聽(tīng)聽(tīng),可能有些大蝦會(huì)笑話(huà)我,想:那么簡(jiǎn)單的東西還在這里賣(mài)弄。但是你錯(cuò)了,我只是把我個(gè)人學(xué)習(xí)的經(jīng)歷講述一遍而已,僅僅對(duì)那些想學(xué)習(xí)單片機(jī),但又找不到好方法或者途徑的朋友,提供一個(gè)幫助,使他們?cè)趯W(xué)習(xí)過(guò)程中,盡量少走些彎路而已!

      首先,你必須有學(xué)習(xí)單片機(jī)的熱情,不是說(shuō)今天去圖書(shū)館看了一個(gè)下午關(guān)于單片機(jī)的書(shū),而明天玩上半天,后天就不知道那個(gè)本書(shū)在講什么東西了。還是先說(shuō)說(shuō)我吧,我從大二的第一個(gè)學(xué)期期末的時(shí)候才開(kāi)始接觸單片機(jī),但在這之前,正如上面所說(shuō)的:我知道有種芯片叫單片機(jī),但是具體長(zhǎng)成什么樣子,卻一點(diǎn)也不知道!看到這里很多朋友一定會(huì)忍不住發(fā)笑。嘿嘿,你可千萬(wàn)別笑,有些大四畢業(yè)的人也同樣不知道單片機(jī)長(zhǎng)成什么樣子呢!而我對(duì)單片機(jī)的癡迷更是常人所不能想象的地步,大二的期末考試,我全放棄了復(fù)習(xí),每當(dāng)室友拿著書(shū)在埋頭復(fù)習(xí)的時(shí)候,我卻捧著自己從圖書(shū)館借的單片機(jī)書(shū)在那看,雖然有很多不懂,但是我還是堅(jiān)持了下來(lái),當(dāng)時(shí)我就想過(guò),為了單片機(jī)值不值得我這樣去付出,或許這也是在一些三流學(xué)校的好處吧,考試掛科后,明年開(kāi)學(xué)交上幾十元一門(mén)的補(bǔ)考費(fèi),應(yīng)該大部分都能過(guò)了。于是,我橫下一條心,堅(jiān)持看我的單片機(jī)書(shū)和資料。

      當(dāng)你明白了單片機(jī)是這么一回事的時(shí)候,顯而易見(jiàn)的問(wèn)題出來(lái)了:我要選擇那種語(yǔ)言為單片機(jī)編寫(xiě)程序呢?這個(gè)問(wèn)題,困擾了我好久。具體選擇C51還是A51呢?匯編在我們大二之前并沒(méi)有開(kāi)過(guò)課,雖然看著人家的講解,很容易明白單片機(jī)的每一時(shí)刻的具體工作情況,但是一合上書(shū)或者資料,自己卻什么也不知道了,根本不用說(shuō)自己寫(xiě)程序了。于是,我最終還是決定學(xué)C51,畢竟C51和我們課上講的C語(yǔ)言,有些類(lèi)似,編程的思想可以說(shuō)是相通的。而且C51還有更大的優(yōu)點(diǎn)就是編寫(xiě)大程序時(shí)的優(yōu)越性更不言而喻,當(dāng)然在那時(shí),我并沒(méi)有想的那么深遠(yuǎn),C51的特點(diǎn),還是在后來(lái)的實(shí)踐過(guò)程中,漸漸體會(huì)到的!朋友如果你選擇了C51,那么請(qǐng)繼續(xù)往下看,如果你選擇了A51,那么你可以不要看了!因?yàn)橄旅嬷v的全是C方面的,完全在浪費(fèi)你的時(shí)間!

      呵呵 ^_^

      第二,既然你想學(xué)好單片機(jī),你必須得舍得花錢(qián),如果不買(mǎi)些芯片回來(lái)自己動(dòng)手焊焊拆拆的(但是在后期會(huì)介紹給大家一個(gè)很好用的硬件仿真軟件,并不需要你用實(shí)驗(yàn)板和仿真器了,直接在你的PC上完成,但是軟件畢竟是軟件,從某個(gè)特定的意義上來(lái)說(shuō)是并不能代替硬件的),即使你每天捧著本書(shū),把那本書(shū)翻爛,也永遠(yuǎn)學(xué)不會(huì)單片機(jī)的!剛接觸單片機(jī)的朋友,看了資料,一定會(huì)對(duì)以下幾個(gè)詞見(jiàn)的比較多,但是具體的概念還是比較模糊,現(xiàn)作如下說(shuō)明:

      (1)編程器

      編程器是用來(lái)燒單片機(jī)芯片的,是把HEX或者BIN文件燒到單片機(jī)ROM里的。

      (2)實(shí)驗(yàn)板

      實(shí)驗(yàn)板是專(zhuān)為初學(xué)者根據(jù)某些要求而特做的板,一般上面就有一個(gè)單片機(jī)的最小系統(tǒng),使用者只需寫(xiě)好程序,燒好芯片,放到上面加以驗(yàn)證的這么一個(gè)工具。有了實(shí)驗(yàn)板,對(duì)與初學(xué)者來(lái)說(shuō),省去了焊?jìng)€(gè)最小系統(tǒng)的麻煩。但是對(duì)于電子開(kāi)發(fā)人員來(lái)說(shuō),作用并不是很大

      (3)仿真器

      仿真器是直接把HEX或者BIN文件暫時(shí)放在一個(gè)芯片里,再通過(guò)這個(gè)芯片的引腳連接到實(shí)驗(yàn)板或者系統(tǒng)上工作。這樣以來(lái),可以省去了來(lái)回插拔芯片帶來(lái)的不必要麻煩。

      我一開(kāi)始也不知道上面3個(gè)的概念和作用,嘿嘿,原本想買(mǎi)個(gè)實(shí)驗(yàn)板(不想焊板,因?yàn)椴豢赡転榱它c(diǎn)亮幾個(gè)流水燈,而去焊?jìng)€(gè)單片機(jī)的最小系統(tǒng))的,可是結(jié)果,確和我想的正好相反,人家出售的是編程器。等貨物寄到后,才知道自己搞錯(cuò)了!汗。。嘿嘿。現(xiàn)在想想實(shí)在是又氣又笑。我花了160大樣買(mǎi)了個(gè)編程器(很不幸的是,這個(gè)編程器更本用不了,一燒芯片,芯片就燒壞了)把我給氣的,這個(gè)編程器,現(xiàn)在還躺在我的抽屜里呢不過(guò),現(xiàn)在想想,唯一讓我覺(jué)得欣慰的是,那個(gè)老板每次能解答我的問(wèn)題,連那種超級(jí)幼稚的問(wèn)題,他也能不嫌麻煩地盡量幫我解答!這點(diǎn)讓我很感動(dòng)!

      第三,想學(xué)單片機(jī)的必需品--PC。因?yàn)閷?xiě)程序,編譯或者是仿真都是通過(guò)PC完成的。如果沒(méi)有PC,什么也做不了??!有了PC最好還要可以上網(wǎng),因?yàn)槿绻銢](méi)有可以和你交流單片機(jī)的人,遇到自己解決不了的問(wèn)題,一直都想不通,那么估計(jì)你學(xué)習(xí)單片機(jī)的熱情就會(huì)隨著時(shí)間的推移而慢慢耗盡。如果你能上網(wǎng)通過(guò)論壇或者QQ群,問(wèn)題就很快得到解決。這樣的學(xué)習(xí)效率一定很高!真正的高手是從論壇中泡出來(lái)的!

      有了上述3個(gè)條件后,你就可以開(kāi)始學(xué)你的單片機(jī)了。但是,真的做起來(lái)并沒(méi)有我所說(shuō)的那么簡(jiǎn)單。你一定會(huì)遇到很多很多的問(wèn)題。比如為了讓單片機(jī)實(shí)現(xiàn)某個(gè)功能,你可能不知道怎么去寫(xiě)某個(gè)程序。或是你看懂了資料上某個(gè)相似的程序,你自己卻寫(xiě)不出來(lái)。遇到類(lèi)似的情況,記?。呵f(wàn)不要急噪,就行!

      (二)說(shuō)了這么多了,相信你也看了很多資料了,手頭應(yīng)該也有必備的工具了吧!(不要忘了上面講過(guò)幾個(gè)條件的哦)。那個(gè)單片機(jī)究竟有什么功能和作用呢?先不要著急!接下來(lái)讓我們點(diǎn)亮一個(gè)LED(搞電子的應(yīng)該知道LED是什么吧^_^)

      我們?cè)趩纹瑱C(jī)最小系統(tǒng)上接個(gè)LED,看我們能否點(diǎn)亮它!對(duì)了,上面也有好幾次提到過(guò)單片機(jī)最小系統(tǒng)了,所謂單片機(jī)最小系統(tǒng)就是在單片機(jī)上接上最少的外圍電路元件讓單片機(jī)工作。一般只須連接晶體、VCC、GND、RST即可,一般情況下,AT89C51的31腳須接高電平。

      #include

      //頭文件定義?;蛴?include其具體的區(qū)別在于:后者定義了更多的地址空間。

      //在Keil安裝文件夾中,找到相應(yīng)的文件,比較一下便知!

      sbit P1_0 = P1 ^ 0;

      void main(void)

      {

      while(1)

      {

      P1_0 = 0;//低電平有效,如果把LED反過(guò)來(lái)接那么就是高電平有效

      }

      }

      就那么簡(jiǎn)單,我們就把接在單片機(jī)P1_0上的LED點(diǎn)亮了,當(dāng)然LED是低電平,才能點(diǎn)亮。因?yàn)槲覀儼袻ED的正通過(guò)電阻接至VCC。

      P1_0 = 0;類(lèi)似與C語(yǔ)言中的賦值語(yǔ)句,即把 0 賦給單片機(jī)的P1_0引腳,讓它輸出相應(yīng)的電平。那么這樣就能達(dá)到了我們預(yù)先的要求了。while(1)語(yǔ)句只是讓單片機(jī)工作在死循環(huán)狀態(tài),即一直輸出低電平。如果我們要試著點(diǎn)亮其他的LED,也類(lèi)似上述語(yǔ)句。這里就不再講了。

      點(diǎn)亮了幾個(gè)LED后,是不是讓我們聯(lián)想到了繁華的街區(qū)上流動(dòng)的彩燈。我們是不是也可以讓幾個(gè)LED依次按順序亮呢?答案是肯定的!其實(shí)顯示的原理很簡(jiǎn)單,就是讓一個(gè)LED滅后,另一個(gè)立即亮,依次輪流下去。假設(shè)我們有8個(gè)LED分別接在P1口的8個(gè)引腳上。硬件連接,在P1_1--P1_7上再接7個(gè)LED即可。例程如下:

      #include

      sbit P1_0 = P1 ^ 0;

      sbit P1_1 = P1 ^ 1;

      sbit P1_2 = P1 ^ 2;

      sbit P1_3 = P1 ^ 3;

      sbit P1_4 = P1 ^ 4;

      sbit P1_5 = P1 ^ 5;

      sbit P1_6 = P1 ^ 6;

      sbit P1_7 = P1 ^ 7;

      void Delay(unsigned char a)

      {

      unsigned char i;

      while(--a!= 0)

      {

      for(i = 0;i < 125;i++);//一個(gè);表示空語(yǔ)句,CPU空轉(zhuǎn)。

      }

      //i 從0加到125,CPU大概就耗時(shí)1毫秒

      }

      void main(void)

      {

      while(1)

      {

      P1_0 = 0;

      Delay(250);

      P1_0 = 1;

      P1_1 = 0;

      Delay(250);

      P1_1 = 1;

      P1_2 = 0;

      Delay(250);

      P1_2 = 1;

      P1_3 = 0;

      Delay(250);

      P1_3 = 1;

      P1_4 = 0;

      Delay(250);

      P1_4 = 1;

      P1_5 = 0;

      Delay(250);

      P1_5 = 1;

      P1_6 = 0;

      Delay(250);

      P1_6 = 1;

      P1_7 = 0;

      Delay(250);

      P1_7 = 1;

      }

      }

      sbit 定義位變量,unsigned char a 定義無(wú)符字符型變量a,以節(jié)省單片機(jī)內(nèi)部資源,其有效值為0~255。main函數(shù)調(diào)用Delay()函數(shù)。Delay函數(shù)使單片機(jī)空轉(zhuǎn),LED持續(xù)點(diǎn)亮后,再滅,下一個(gè)LED亮。while(1)產(chǎn)生循環(huán)。

      (三)上面我們講了如何使LED產(chǎn)生流動(dòng),但是你是否發(fā)現(xiàn)一個(gè)問(wèn)題:寫(xiě)的太冗長(zhǎng)了!能不能再簡(jiǎn)單點(diǎn)呢?可以!可以使用C51的內(nèi)部函數(shù)INTRINS.H實(shí)現(xiàn)。函數(shù)unsigned char _crol_(unsigned char a, unsigned char n)可以使變量a循環(huán)左移n位,如果我們先給P1口賦0000 0001那么當(dāng)n為1時(shí),便會(huì)產(chǎn)生和上面一樣的效果!

      #include

      #include

      void Delay(unsigned char a)

      {

      unsigned char i;

      while(a--!= 0)

      {

      for(i = 0;i < 125;i++);

      }

      }

      void main(void)

      {

      unsigned char b, i;

      while(1)

      {

      b = 0xfe;

      for(i = 0;i < 8;i++)

      {

      P1 = char _crol_(b, 1);

      b = P1;

      Delay(250);

      }

      }

      }

      INTRINS.H函數(shù)中的unsigned char _cror_(unsigned char a, unsigned char n)右移也可以實(shí)現(xiàn)同樣的效果!這里就不再累述。

      流水燈的花樣很多,我還寫(xiě)過(guò)那種拉幕式的流動(dòng)等,程序很簡(jiǎn)單,有興趣的朋友,可以自己試著寫(xiě)寫(xiě)!

      對(duì)了,講了那么多,有些朋友一定還不知道編譯軟件怎么用?這里給大家介紹幾個(gè)吧?WAVE(偉福)大家一定聽(tīng)說(shuō)過(guò)吧!還有一個(gè)就是KEIL2,我用的就是KEIL2,下面就來(lái)講講如何使用KEIL2這個(gè)編譯軟件!

      1.安裝軟件,這個(gè)應(yīng)該不用再講了吧!

      2.安裝完后,啟動(dòng)KEIL軟件左擊Project-->New Project-->輸入文件名-->選擇我們所以使用的芯片(這里我們一般用到Atmel的AT89C51或AT89C2051,點(diǎn)確定。

      3.點(diǎn)File-->New-->輸入我們編寫(xiě)的程序,保存為.C文件。(一般情況下,我們保存的文件名和前面的工程名一樣。)

      4.展開(kāi)Target 1-->右擊Source Group 1-->Add Files to Group 'Source Group 1'-->選擇剛才保存的.C文件點(diǎn)擊ADD后,關(guān)閉對(duì)話(huà)框。這樣.C文件就被加到了Source Group 1 下。

      5.右擊Target 1-->Options

      for 'Target 1'-->Target中填寫(xiě)晶體的大小,Output中,在Create HEX Files 前打上鉤,點(diǎn)確定。

      6.點(diǎn)Project-->Rebuild All Traget Files,若提示

      creating hex file from “XXX”...“XXX”5000)/ 256;//載入高8位初值

      TL0 =(655365000)/ 256;//載入高8位初值。若在12M晶體下,定時(shí)5000微秒,即為5毫秒;但是如果不是在12M下,那又該怎么計(jì)算了呢?如果是11.0592M呢?還記不記得,我們前面講過(guò)的機(jī)器周期和時(shí)鐘周期的概念? ^_^忘了,還是看看前面吧!呵呵!沒(méi)事,學(xué)習(xí)嘛,忘了再翻翻書(shū),看看就可以了!其實(shí)上訴的5000 = 1 * C 很顯然C=5000,但是如果是11.0592M那么就不是1了,應(yīng)該是1.085了,那么5000 = 1.085 * C,則C就為5000 / 1.085 = ? 具體多少,大家自己去算算吧?同理TL0也是一樣的!但是,細(xì)心的朋友會(huì)發(fā)現(xiàn)網(wǎng)上或者是資料上的TH0,TL0并不是和上面一樣的,而是直接TH0 = 0XEC;TL0 = 0X78 是不是和上面的一樣的,別忘了單片機(jī)也是計(jì)算機(jī)的一種哦。用C的話(huà),直接寫(xiě)上計(jì)算公式就行,計(jì)算就交給單片機(jī)完成。

      TR0 = 1;這句就是啟動(dòng)定時(shí)器0,開(kāi)始記數(shù)!哦,還有一點(diǎn),有些朋友會(huì)問(wèn),你是65536是哪里來(lái)的呢?呵呵你可別忘了:設(shè)置定時(shí)器0 工作方式0是16位的(2的16次方是多少,自己算算就知道了)簡(jiǎn)單吧?但是如何和中斷一起使用呢?請(qǐng)繼續(xù)看下面的講解!

      TMOD = 0X01;//設(shè)置定時(shí)器0 工作方式0

      TH0 =(655365000)% 256;//載入低8位初值

      TR0 = 1;

      //啟動(dòng)定時(shí)器

      EA = 1;//開(kāi)總中斷

      ET0 = 1;//開(kāi)定時(shí)器中斷。若為0則表示關(guān)閉!

      這樣我們,就初始化定時(shí)器T0和中斷了,也就是定時(shí)器滿(mǎn)5毫秒后,產(chǎn)生一次中斷。產(chǎn)生中斷后,我們?cè)趺刺幚砟??嘿嘿!仔?xì)想想?^_^ 每次中斷后,我們可以讓一個(gè)變量自加1,那么200次中斷后,不就是1秒的時(shí)間了嗎?比起上面我們說(shuō)的延時(shí)來(lái)出來(lái)是不是更加精確多了呢?那是肯定的!但是想想1秒種的時(shí)間就讓單片機(jī)產(chǎn)生那么多次的中斷,單片機(jī)會(huì)不會(huì)累著呢?恩,那么不好。如果在12M的晶體下,T0每次中斷不是可以產(chǎn)生最多65.336毫秒的時(shí)間嗎?那么我們讓他每50毫秒中斷一次好了!這樣我們就20次搞定一秒的時(shí)間了!

      ·爽·

      好了,講了那么多,現(xiàn)在我們來(lái)寫(xiě)個(gè)時(shí)間的程序吧!

      ^_^

      #include

      #define HI

      ((6553650000)% 256)#define _TH0_TL0_

      (65536-50000)#define M

      //(1000/25)

      /**********************************************************************************************/ unsigned hou = 12, min = 0, sec = 0;unsigned char SEG_TAB_B[] = {0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90};//0-9數(shù)字 unsigned char SEG_TAB_A[ ] = {0x40,0x79,0x24,0x30,0x19,0x12,0x02,0x78,0x00,0x10};//0.-9.數(shù)字

      /*********************************************************************************************/ void Delay(unsigned char a)//延時(shí)程序a*1MS {

      unsigned char j;

      while(a--!= 0)

      {

      for(j = 0;j < 125;j++);

      } }

      /*********************************************************************************************/ void Disp(void)//數(shù)碼管顯示 {

      P2_0 = 1;

      P1 = SEG_TAB_B[ hou / 10 ];

      Delay(5);

      P2_0 = 0;

      P2_1 = 1;

      P1 = SEG_TAB_A[ hou % 10 ];

      Delay(5);

      P2_1 = 0;

      P2_2 = 1;

      P1 = SEG_TAB_B[ min / 10 ];

      Delay(5);

      P2_2 = 0;

      P2_3 = 1;

      P1 =S EG_TAB_A[ min % 10 ];

      Delay(5);

      P2_3 = 0;

      P2_4 = 1;

      P1 = SEG_TAB_B[ sec / 10 ];

      Delay(5);

      P2_4 = 0;

      P2_5 = 1;

      P1 = SEG_TAB_B[ sec % 10 ];

      Delay(5);

      P2_5 = 0;}

      /********************************************************************************************/ void IsrTimer0(void)interrupt 1 using 1

      //定時(shí)50ms {

      static unsigned char count = 0;

      //定義靜態(tài)變量count

      count++;

      if(count == M)

      {

      count = 0;

      sec++;

      if(sec == 60)

      {

      min++;

      sec = 0;

      if(min == 60)

      {

      hou++;

      min = 0;

      if(hou == 24)

      {

      hou = 0;

      }

      }//if

      }//if

      }//if }

      /******************************************************************************************/ void Timer0Init(void)//定時(shí)器0 {

      TMOD = 0x01;

      TH0 = HI;

      TL0 = LO;

      TR0 = 1;

      ET0 = 1;

      EA = 1;

      }

      /******************************************************************************************/ void main(void)//主函數(shù) {

      Timer0Init();

      while(1)

      {

      Disp();

      } }

      簡(jiǎn)單吧,還是有點(diǎn)看不懂哦,那你自己慢慢體會(huì)吧,如果你自己能寫(xiě)個(gè)時(shí)鐘程序來(lái),那么你的51單片機(jī)也就學(xué)了80 % 了。中斷和定時(shí)/記數(shù)器器,是個(gè)很重要的東西,幾乎用到單片機(jī)的地方都會(huì)涉及到中斷和定時(shí)!所以大家要好好掌握哦!^_^

      哈哈,趕緊編譯HEX文件,搭好硬件,燒入單片機(jī),上電看看效果先!呵呵,現(xiàn)在你應(yīng)該有成就感了吧,想不到一個(gè)時(shí)鐘居然那么簡(jiǎn)單,嘿嘿!但是問(wèn)題來(lái)了!時(shí)鐘雖然做出來(lái)了,但是他的精度怎么樣呢?一兩個(gè)小時(shí),或許看不出什么誤差,但是一天或者一年呢?暈,我的天呀,要是按年來(lái)算的話(huà),那這個(gè)時(shí)鐘根本沒(méi)有實(shí)用價(jià)值!人家都說(shuō)用C寫(xiě)不出,精度高的時(shí)鐘程序來(lái)的??!是不是有點(diǎn)后悔了,去學(xué)匯編吧!但是既然選擇了C,那么就不要后悔!嘿嘿,想想C的高級(jí)語(yǔ)言,怎么會(huì)輸給匯編呢 ^_^ 呵呵!看下面這段代碼:

      static unsigned char count = 0;

      TR0 = 0;

      TL0 +=(_TH0_TL0_ + 9)% 256;

      TH0 +=(_TH0_TL0_ + 9)/ 256 +(char)CY;

      TR0 = 1;

      count++;

      在中斷處理服務(wù)程序中,我們加入上面的代碼。TR0 = 0;先關(guān)閉定時(shí)器T0,然后重新給TH0和TL0 賦值,再開(kāi)啟 TR0 = 1;燒入單片機(jī)看看效果,怎么樣,你第一次精確多了吧。但是還是有誤差!郁悶!為什么呢?那是硬件造成的誤差,我們可以用軟件來(lái)彌補(bǔ)!我們先把時(shí)鐘點(diǎn)亮,讓他走上幾個(gè)小時(shí)或者是幾天,看看到底誤差是多少!取個(gè)平均值。(這里比如我們10小時(shí)快1秒)那么可以通過(guò)以下語(yǔ)句

      if(hour % 10 = 0)

      {

      sec--;

      } 來(lái)彌補(bǔ)!這樣可能會(huì)出現(xiàn)這樣的現(xiàn)象:秒直接跳變!我們可以再通過(guò)細(xì)分來(lái)實(shí)現(xiàn),不要10小時(shí)那么大,小些的就行!具體的操作還是留給朋友們吧!

      (七)這回我們來(lái)講講鍵盤(pán),大家肯定見(jiàn)過(guò)銀行柜員機(jī)吧,取錢(qián)輸入密碼就要用到鍵盤(pán),超市購(gòu)物取回寄存物品要輸入密碼,還有你現(xiàn)在在用的PC機(jī)的鍵盤(pán)。但是鍵盤(pán)的是怎么工作的呢?一般有2種方式:(1)掃描法,不斷掃描鍵盤(pán)的狀態(tài),送CPU判斷并處理。如果鍵盤(pán)數(shù)目一大的話(huà),顯然不適合(2)線反轉(zhuǎn)法,通過(guò)行列狀態(tài)的改變來(lái)判斷有無(wú)鍵被按下!

      現(xiàn)在我們?cè)赑1口接個(gè)4*4的鍵盤(pán),P1.0--P1.3接行,P1.4---P1.7接列,再接4個(gè)4K7的上拉電阻至VCC。代碼如下:

      //----鍵盤(pán)掃描法程序-------//----用數(shù)碼管顯示相應(yīng)的鍵值-----//P1.0--P1.3接行-------//P1.4---P1.7接列-------#include

      unsigned char code tab[ ]={0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,0x7F,0x6F,0x77,0x7C,0x39,0x5E,0x79,0x71};//0到F的16個(gè)鍵植

      /******************************************************************************/ void Delayt(unsigned char t)//延時(shí)函數(shù) {

      unsigned char i;

      for(t=0;i<=t;t++)

      for(i=0;i<255;i++);}

      /******************************************************************************/ bit pkey(void)//判斷鍵的否被按下,通過(guò)返回值確定 {

      P1=0xf0;

      if(P1!=0xf0)

      {

      Delayt(25);

      if(P1!=0xf0)

      return 1;

      else

      return 0;

      }

      else

      return 0;}

      /******************************************************************************/ void main(void)//主函數(shù) {

      unsigned char key,j,k,s;

      while(1)

      {

      if(pkey()==1)

      {

      P1=0xfe;

      k=0xfe;

      for(j=0;j<4;j++)

      {

      s=P1&0xf0;

      switch(s)

      {

      case 0xe0: key=4*j+0;break;

      case 0xd0: key=4*j+1;break;

      case 0xb0: key=4*j+2;break;

      case 0x70: key=4*j+3;break;

      default:

      break;

      }

      k=(k<<1)|0x01;

      P1=k;

      }//for

      }//if

      //if((P1&0xf0)==0xf0)

      P0=tab[key];

      P2=1;

      Delayt(50);

      }//while }

      還有一種就是線反轉(zhuǎn)法,實(shí)現(xiàn)如下:

      1.和掃描法相同,把列線置低電平,行置高,讀行狀態(tài) 2.與1相反,把行置低,列置高,讀列狀態(tài)

      3.若有鍵按下,則為2次所讀狀態(tài)的結(jié)果即為鍵所在的位置,這樣2次輸出和2次讀入可以完成鍵的識(shí)別?。?/p>

      子函數(shù)如下:

      unsigned char key_vscan(void){

      unsigned char row, col;

      P1 = 0xF0;

      row = P1&0xF0;

      row = row&0xF0;

      P1 = 0x0F;

      col = P1&0x0F;

      col = col&0x0F;

      return(key_val(row|col));}

      下面我們?cè)賮?lái)介紹介紹一鍵多能的程序,即按下一個(gè)鍵,可以執(zhí)行不同的命令!

      void main(void){

      unsigned char b = 0;

      while(1)

      {

      if(P1_0 == 0)

      {

      Delay(10);

      if(P1_0 == 0)

      {

      b++;

      if(b == N)//N為鍵的功能數(shù)目

      {

      b = 0;

      }

      while(P3_2 == 0);//等待鍵松開(kāi)

      }

      }

      switch(b)

      {

      case 1: P2_0 = 0xFE;

      break;

      case 2: P2_1 = 0xfd;

      //..............add your code here!

      }

      } }

      (八)/ /以上的文字寫(xiě)于2005年5月,由于時(shí)間關(guān)系,一直未能將此完成,最近閑著無(wú)聊又接著寫(xiě)了些文字,以下寫(xiě)于2006年6月5日!

      在這里我想對(duì)上面一點(diǎn),作個(gè)簡(jiǎn)單的說(shuō)明,如果你是剛學(xué)單片機(jī),那么你寫(xiě)的代碼是VERY GOOD的,但是如果把上面的代碼應(yīng)用于產(chǎn)品的話(huà),那么我可以告訴你,上面所寫(xiě)的按鍵識(shí)別代碼全部是垃圾代碼,^_^,這下傻了吧,呵呵。為什么?我的按鍵不是可以正常工作嗎?

      請(qǐng)看這里: if(P1_0 == 0)

      {

      Delay(10);//問(wèn)題就在這里,你讓CPU在這里空轉(zhuǎn)?

      if(P1_0 == 0)

      {

      //...add your code here.} } 進(jìn)入第1個(gè)if判斷語(yǔ)句后,就進(jìn)入了Delay(10);再看Delay函數(shù),完全讓CPU執(zhí)行(;空語(yǔ)句),所以在做大的產(chǎn)品或者代碼時(shí),這個(gè)是非常耗費(fèi)單片機(jī)內(nèi)部資源的。有什么辦法嗎?呵呵,那是肯定的。

      解決方法大致有如下2種:

      1.將延時(shí)函數(shù)放在中斷中,在中斷里查詢(xún)延時(shí)的標(biāo)志位。/*不僅僅用于鍵盤(pán)識(shí)別,亦可以用于其他的延時(shí)代碼,見(jiàn)EX1*/ 2.直接在中斷中查詢(xún)按鍵的標(biāo)志位.//見(jiàn)EX2。

      EX1: unsigned char Delaytime;

      void Delay(unsigned char Delaytime)// { while(Delaytime!=0);//等在這里,直到Delaytime為0。}

      void Timer0_interrupt(void)interrupt 1 using 2 { if(Delaytime!=)

      Delaytime--;

      //...add your other code here }

      Delay函數(shù)具體延時(shí)多長(zhǎng)時(shí)間,就要看你設(shè)定的T0定時(shí)器中斷和Delaytime的乘積,比如你的定時(shí)器中斷為50MS,Delaytime為20的話(huà),那么50MS*20=1S。

      EX2:

      #define Press_key = P2 ^ 7;//定義按鍵的I/O

      void P_key(void){ char new_value,old_value;

      new_value = Press_key;

      if(new_value &&!old_value)//識(shí)別按鍵。{

      Turn_On_LEd();

      //...add your other code here.} old_value = new_value;}

      void Timer0_interrupt(void)interrupt 1 using 2 { P_key();

      //...add your other code }

      當(dāng)然在實(shí)際過(guò)程當(dāng)中,并不是如此簡(jiǎn)單簡(jiǎn)潔的,還希望大家能夠舉一反三哦...^_^。

      (九)寫(xiě)了這么多了,大家也看了這么多了,感覺(jué)怎么樣?大家也覺(jué)得不難吧。其實(shí)51也就那么簡(jiǎn)單,真的很希望大家看完這篇文字以后,很自信的說(shuō),51單片機(jī)也已經(jīng)入門(mén)。這是對(duì)我寫(xiě)怎么多文字最好的回答。時(shí)隔13個(gè)月之久再來(lái)繼續(xù)寫(xiě)這些東西,沒(méi)有以前的激情和熱情,所以就草草了事結(jié)尾,希望大家不要在背地里罵我哦,^_^。當(dāng)然以上講的只是最簡(jiǎn)單的一些東西,單片機(jī)的功能非常之強(qiáng)大,只要你能想得到,就一定可以用單片機(jī)來(lái)實(shí)現(xiàn)的。當(dāng)然單片機(jī)和外部其他的芯片還有很多,比如數(shù)字溫度傳感器DS18B20,實(shí)時(shí)時(shí)鐘芯片DS1302,還有比如訪問(wèn)AT24CXX的EEPROM存儲(chǔ)器等,更多的電路,還要靠大家在平時(shí)的學(xué)習(xí)過(guò)程當(dāng)中,慢慢掌握。

      第五篇:?jiǎn)纹瑱C(jī)C語(yǔ)言學(xué)習(xí)

      單片機(jī)C語(yǔ)言之一___________________________________________________________________ _____________________ 預(yù)處理 一》宏定義:

      1、不帶參數(shù):

      #define 標(biāo)識(shí)符 常量表達(dá)式

      /*#define是宏定義命令,宏名(標(biāo)識(shí)符)好習(xí)慣用大寫(xiě)*/ #define NIL 0x80

      2、帶參數(shù):/*相當(dāng)于小函數(shù)*/ #define 宏名(參數(shù)表)字符串

      /*不僅要時(shí)行字任串替換還要進(jìn)行參數(shù)的替換,在宏定義時(shí),宏名與帶參數(shù)的括弧之間不應(yīng)該加空格,否則將空格以后的字符串都作為替代字符串的一部分,這可是很容易出錯(cuò)的*/ 如:#define SQ(a,b)a*b 使用:x=12;y=10;area=SQ(x,y);/*則area=12*10=120*/ 二》文件包含:

      #include <文件名>或#include “文件名” /*在C中用雙引用形式更保險(xiǎn),在C51中常用物是尖括弧形式*/ 三》條件編譯:

      /*一般源程序中的所有程序行都參加編譯,但有時(shí)希望對(duì)其中一部分內(nèi)容只在滿(mǎn)足一定條件下才進(jìn)行編譯,也就是對(duì)一部分內(nèi)容指定編譯的條件。*/ #if、#elif、#else、#endif、#ifdef、#ifndef /*選擇不同的編譯范圍,產(chǎn)生不同的代碼,提供通用性。*/ /*如對(duì)8051在6MHZ與12MHZ下有*/ #ifdef cpu==8051 #define FREQ 6 /*程序段*/ #else #define FREQ 12/*程序段*/ #endif /*這樣下面的原程序不用做任何修改便可以使用于兩種時(shí)鐘頻率的單片機(jī)系統(tǒng)*/ 四》其他:

      1、#error:捕捉不可預(yù)料的編譯條件

      #if(myv!=0&&myv!=1)/*假定其值必為0或1*/ #error myv must be 1 or 0/*出錯(cuò)時(shí)顯示*/ #endif

      2、#pragma:用于在程序中向編譯器傳送各種編譯控制命令 #pragma 編譯命令序列

      /*例:想按如下命令編譯ex.c c51 ex.c debug cod large可用:*/

      #pragma DB CD LA #pragma disable /*禁止中斷*/

      單片機(jī)C語(yǔ)言之二_____________________________________________________________________________________ 一》數(shù)據(jù)類(lèi)型:

      char int long 1:unsinged 0~255 0~65535 0~4294967295 2:signed-128~127-32768~32767-2147483648~2147483647 指針:* 3字節(jié) 位標(biāo)量: sbit 特殊功能寄存器:sfr 16位特殊功能寄存器:sfr16 占2個(gè)內(nèi)存單元,0~65535 可尋址位:sbit利用他可訪問(wèn)51單片機(jī)的內(nèi)部RAM中的可尋址位或特殊功能寄存器中的可尋址位 sfr P0=0x80;sbit P0_1=P0^1;/*將P0口的口地址定義為80H,將P0.1位定義為P1_1*/ 二》數(shù)據(jù)存貯類(lèi)型

      表1.C51數(shù)據(jù)存貯類(lèi)型

      ━━━━━━━┳━━━━━━━━━━━━━━━━━━━━━━━━━━ 數(shù)據(jù)存貯類(lèi)型 ┃ 與存貯空間的對(duì)應(yīng)關(guān)系

      ━━━━━━━╋━━━━━━━━━━━━━━━━━━━━━━━━━━ data ┃ 直接尋址片內(nèi)數(shù)據(jù)存貯區(qū),訪速度快 bdata ┃ 可位尋址片內(nèi)數(shù)據(jù)存貯區(qū),允許位與字節(jié)混合訪問(wèn) idata ┃ 間接尋址片內(nèi)數(shù)據(jù)存貯區(qū),可訪問(wèn)片內(nèi)全部RAM地址空間

      pdata ┃ 分頁(yè)尋址片外數(shù)據(jù)存貯區(qū)(256字節(jié))由MOVX @R0訪問(wèn) xdata ┃ 片外數(shù)據(jù)存貯區(qū)(64K),由MOVX @DPTR訪問(wèn) code ┃ 代碼存貯區(qū)(64K),由MOVC @DPTR訪問(wèn)

      ━━━━━━━┻━━━━━━━━━━━━━━━━━━━━━━━━━━ 變量的存貯類(lèi)型定義: char data var /*字符變量var被定義為data存貯類(lèi)型,C51編譯器將把該變量定位在51單片機(jī)片內(nèi)數(shù)據(jù)區(qū)存貯區(qū)中*/ bit bdata flag /*位變量flag被定義為bdata存貯類(lèi)型,C51編譯器將把該變量定位在51單片機(jī)片內(nèi)數(shù)據(jù)區(qū)存貯區(qū)(RAM)中的位尋址區(qū):20H--2FH*/

      三》typedef:重新定義數(shù)據(jù)類(lèi)型

      typedef 已有數(shù)據(jù)類(lèi)型 新的數(shù)據(jù)類(lèi)型 typedef int word;/*將word定義為整型*/ word i,j;/*將i,j定義為整型*/ 四》位運(yùn)算符:

      ━━━━┳━━━━━┳━━━━━┳━━━━━━┳━━━━━━┳━━━━━━ ~ ┃ & ┃ | ┃ ^ ┃ << ┃ >> ━━━━╋━━━━━╋━━━━━╋━━━━━━╋━━━━━━╋━━━━━━

      按位取反┃ 按位與 ┃ 按位或 ┃ 按位異或 ┃ 左移 ┃ 右移

      ━━━━┻━━━━━┻━━━━━┻━━━━━━┻━━━━━━┻━━━━━━

      對(duì)移位:如<< ,a<<2,即為將二進(jìn)制的a左移兩位,若a=0x8f,即10001111,a=a<<2,將導(dǎo)致a=0x3c(00111100),右邊補(bǔ)零。五》條件運(yùn)算符:

      邏輯表達(dá)式? 表達(dá)式1:表達(dá)式2 六》指針與地址運(yùn)算符: *取內(nèi)容 &取地址

      七》強(qiáng)制類(lèi)型轉(zhuǎn)換:(類(lèi)型)=表達(dá)式(char *)0xb000 八》sizeof 取數(shù)據(jù)類(lèi)型、變量以及表達(dá)式的字節(jié)數(shù)的運(yùn)算符; 九》continue:中斷語(yǔ)句:結(jié)束本次循環(huán)。

      單片機(jī)C語(yǔ)言之三_____________________________________________________________________________________ 函數(shù):

      一》中斷服務(wù)函數(shù)與寄存器組定義:

      函數(shù)類(lèi)型 函數(shù)名(形式參數(shù)表)[interrupt n][using n] n為中斷號(hào),0~31:

      ━━━━┳━━━━━┳━━━━━ 中斷編號(hào)┃ 中斷向量┃ 入口地址 ━━━━╋━━━━━╋━━━━━ 0 ┃ 外中斷0 ┃ 0003H ━━━━╋━━━━━╋━━━━━ 1 ┃ 定時(shí)器0 ┃ 000BH ━━━━╋━━━━━╋━━━━━ 2 ┃ 外中斷1 ┃ 0013H

      ━━━━╋━━━━━╋━━━━━ 3 ┃ 定時(shí)器1 ┃ 001BH ━━━━╋━━━━━╋━━━━━ 4 ┃ 串行口 ┃ 0023H ━━━━┻━━━━━┻━━━━━

      后面的n指的是四個(gè)工作寄存器組的一個(gè):0~3 對(duì)函數(shù)目標(biāo)代碼影響如下:

      在函數(shù)入口處將當(dāng)前工作寄存器組保護(hù)到堆棧中;指定的工作寄存器內(nèi)容不會(huì)改變,函數(shù)返回前將被保護(hù)的工作寄存器組從堆棧中恢復(fù)!例(定時(shí)1ms):

      #include sbit P1_0=P1^0;void timer0(void)interrupt 1 using 1{ P1_0=!P1_0;TH0=-(1000/256);TL0=-(1000%256);} main(){ SP=0x60;P1_0=0;TMOD=0X01;TH0=-(1000/256);TL0=-(1000%256);EA=1;ET0=1;TR0=1;do{}while(1);} /* 注意:

      1、如果中斷函數(shù)中用到浮點(diǎn)運(yùn)算,必須保存浮點(diǎn)寄存器的狀態(tài)。(在math.h中保存浮點(diǎn)寄存器函數(shù)為pfsave, 恢復(fù)浮點(diǎn)寄存器的狀態(tài)函數(shù)為fprestore)

      2、如果在中斷函數(shù)中調(diào)用了其他函數(shù),則被調(diào)函數(shù)所使用的工作寄存器組與中斷函數(shù)的一致!*/

      單片機(jī)C語(yǔ)言之四_____________________________________________________________________________________

      一、局部變量與全局變量(外部變量):

      1、全局變量若不在開(kāi)頭定義則加extern

      2、全局變量會(huì)使代碼長(zhǎng),占用內(nèi)存多

      二、存儲(chǔ)方式:

      自動(dòng)變量(auto):缺省,函數(shù)調(diào)用存在,退出消失。

      內(nèi)部變量 靜態(tài)變量(static):static int a=5;始終存在,退出不消失,但不能訪問(wèn)。寄存器變量(register):速度最快。通常只給編譯器一個(gè)建議,由編譯器根 據(jù)實(shí)際情況確定。(見(jiàn)下)變量 全局變量(global): 外部變量

      靜態(tài)變量(static): 寄存器變量例: #include int_power(m,e)int m;register int e;{ register int temp;temp=1;for(;e;e--)temp*=m;return(temp);} main(){ ?? }

      三、函數(shù)的參數(shù)和局部變量的存儲(chǔ)器模式: 三種存儲(chǔ)器模式:small,compact,large.一個(gè)函數(shù)的存儲(chǔ)器模式確定了函數(shù)的參數(shù)和局部變量在內(nèi)存中的地址空間 small:內(nèi)部ram compact, large:外部RAM 函數(shù)類(lèi)型 函數(shù)名(形式參數(shù)表)[存儲(chǔ)器模式] 例:

      #pragma large /*默認(rèn)存儲(chǔ)器模式為large*/ extern int calc(char I,int b)small;/*指定small模式*/ extern int func(int I,float f)large;/*指定large模式*/ int large_te(int I,int k)/*未指定,按默認(rèn)的large模式處理*/ { return(mtest(I,k)+2);}

      利用存儲(chǔ)器混合模式編程,充分利用有限的存儲(chǔ)空間,還可加快程序的執(zhí)行速度!

      單片機(jī)C語(yǔ)言之五_____________________________________________________________________________________ 數(shù)組 1>初始化數(shù)組: unsigned char a[5]={0x11,0x22,0x33,0x44,0x55} 或

      unsigned char a[ ] ={0x11,0x22,0x33,0x44,0x55,0x66} 3>數(shù)組作為函數(shù)的參數(shù):不但可以由變量作為函數(shù)的參數(shù)外,還可以用數(shù)組名作為函數(shù)的參數(shù)。一個(gè)數(shù)組數(shù)組名表示該數(shù)組的首地址。用一個(gè)數(shù)組名作為函數(shù)的參數(shù)時(shí),在執(zhí)行函數(shù)調(diào)用的過(guò)程中參數(shù)傳遞方式采用的是地址傳遞。將實(shí)際參數(shù)數(shù)組首地址傳遞給被調(diào)函數(shù)中的形式參數(shù)數(shù)組,這樣一來(lái)兩個(gè)數(shù)組就占有同一段內(nèi)存單元。見(jiàn)下圖:

      a[0] a[1] a[2] a[3] a[4] a[5] a[6] a[7] a[8] a[9] 起始地址1000 b[0] b[1] b[2] b[3] b[4] b[5] b[6] b[7] b[8] b[9] 用數(shù)組名作為函數(shù)的參數(shù),應(yīng)該在主調(diào)函數(shù)和被調(diào)函數(shù)中分別進(jìn)行數(shù)組定義而不能只在一方定義數(shù)組。而且在兩個(gè)函數(shù)中定義的數(shù)組類(lèi)型必須一致,如果類(lèi)型不一致將導(dǎo)致編譯出錯(cuò)。實(shí)參數(shù)組和型參數(shù)組的長(zhǎng)度可以一致可以不一致,編譯器對(duì)形參數(shù)組的長(zhǎng)度不做檢查,直只是將實(shí)參數(shù)組的首地址傳遞給行參數(shù)組。如果希望行參數(shù)組能得到實(shí)參數(shù)組的全部元素,則應(yīng)使兩個(gè)數(shù)組的長(zhǎng)度一致。定義型參數(shù)組時(shí)可以不指定長(zhǎng)度,只在數(shù)組名后面跟一個(gè)方括號(hào)[]。這時(shí)為了在被調(diào)函數(shù)中處理數(shù)組元素的需要,應(yīng)另外設(shè)置一個(gè)參數(shù)來(lái)傳遞數(shù)組元素的個(gè)數(shù)。

      例:用數(shù)組作為函數(shù)的參數(shù),計(jì)算兩個(gè)不同長(zhǎng)度的數(shù)組中所有元素的平均值 #include float average(array,n)int n;float array[ ];{ int I;float aver,sum=array[0];for(I=1;I

      float pot_1[2]={99.9,88.8};float pot_2[3]={11,22,33.3};average(pot_1,2);average(pot_1,3);}

      單片機(jī)C語(yǔ)言之六_____________________________________________________________________________________ 軟件法去干擾:

      工程上我們?cè)诓杉瘮?shù)據(jù)時(shí)一般要求精度達(dá)到5%%,大于這個(gè)值將認(rèn)為無(wú)效。我在實(shí)際應(yīng)用中采用8535對(duì)32路數(shù)據(jù)進(jìn)行采集(8535帶10位AD,帶看門(mén)狗),發(fā)現(xiàn)數(shù)據(jù)跳動(dòng)有時(shí)達(dá)7%%,這是由于各種干擾造成的。主要來(lái)自于隨機(jī)干擾,下面就各種干擾的方法給出簡(jiǎn)單的去除方法:

      1、白噪聲:最重要的統(tǒng)計(jì)特性為平均值為0,可采取每路數(shù)據(jù)采集幾次求平均的方法;

      2、隨機(jī)干擾:該點(diǎn)明顯高于或低于附近正常采樣值,故采取中值濾波法,即對(duì)被測(cè)信號(hào)連續(xù)采樣M次,進(jìn)行大小排序,取大小居中的1/3個(gè)采樣值進(jìn)行算術(shù)平均;

      3、電源干擾:特點(diǎn)是有固定周期,故可采用定時(shí)采樣求平均的方法。

      由于各種排序與求平均算法用C易于實(shí)現(xiàn),故C常常用于采集系統(tǒng)中軟件去干擾。至于排序算法可參考上一篇文章,有一個(gè)經(jīng)典的程序。

      在實(shí)際中我們采用每路猜9個(gè)值,排序,取中間3個(gè),求平均。然后。,每路數(shù)據(jù)幾乎不動(dòng)!

      單片機(jī)C語(yǔ)言之七_(dá)____________________________________________________________________________________ 指針:可對(duì)內(nèi)存地址直接操作

      基于存貯器的指以貯器類(lèi)為參量,它在編譯時(shí)才被確定。因此為指針選擇存貯器的方法可以省掉,以這些指針的長(zhǎng)度可為1個(gè)字節(jié)(idata *,data *,pdata *)或2個(gè)這節(jié)(code *,xdata *)。char xdata *address;ADC0809具有8個(gè)模擬量輸入通道,采用中斷方式,在中斷函數(shù)中讀取8個(gè)通道的A/D轉(zhuǎn)換值,分別存儲(chǔ)在外部RAM的1000H~1007H單元。ADC0809端口地址為00F0H。

      程序定義了兩個(gè)指針變量* ADC和* ADCdata,分別指向ADC0809端口地址(00F0H)和外部RAM單元地址(1000H~1007H)

      由*ADC=I送入通道數(shù),啟動(dòng)ADC0809進(jìn)行A/D轉(zhuǎn)換,轉(zhuǎn)換結(jié)束時(shí)產(chǎn)生INT1中斷。在中斷服務(wù)函數(shù)int1()中通過(guò)temp=*ADC和*ADCdata=temp;讀取A/D轉(zhuǎn)換結(jié)果并存到外部RAM中。#include unsigned int xdata *ADC;/*定義ADC0809端口指針*/ unsigned int xdata *ADCdata;/*定義ADC0809數(shù)據(jù)緩沖器指針*/ unsigned char I;

      void main(){ ADC=0x00f0;/*定義端口地址和數(shù)據(jù)緩沖器地址*/ ADCdata=0x1000;I=8;/* ADC0809有8個(gè)模擬輸入通道*/ EA=1;EX1=1;IT1=1;/*開(kāi)中斷*/ *ADC=I;/*啟動(dòng)ADC0809*/ WHILE(I);/*等待8個(gè)通道A/D轉(zhuǎn)換完*/ } void int1()interrupt 2 { unsigned char tmp;temp=*ADC;/*讀取A/D轉(zhuǎn)換結(jié)果*/ *ADCdata=temp;/*結(jié)果值存到數(shù)據(jù)緩沖區(qū)*/ ADCdata++;/*數(shù)據(jù)緩沖區(qū)地址加1*/ i—;*ADC=I;/*啟動(dòng)下一個(gè)模擬輸入通道A/D轉(zhuǎn)換*/ } 除了用指針變量來(lái)實(shí)現(xiàn)對(duì)內(nèi)存地址的直接操作外,c51編譯器還提供一組宏,該宏定義文件為:“absacc.h”,利用它可十分方便地實(shí)現(xiàn)對(duì)任何內(nèi)存空間的直接操作,改寫(xiě)上面的程序: #include #include /*包含絕對(duì)地址操作預(yù)定義頭文件*/ #define ADC 0x00f0;/*定義ADC0809端口地址*/ #define ADCdata 0X1000 /*定義數(shù)據(jù)緩沖器地址*/ unsigned char I;void main(){ I=8;/ *ADC0809有8個(gè)模擬輸入通道*/ EA=1;ex1=1;it1=1;/ *開(kāi)中斷*/ XBYTE[ADC]=I;/*啟動(dòng)0809 */ While(i);/*等待8個(gè)通道轉(zhuǎn)換完畢*/ } void int1()interrupt2 { unsigned char tmp;tmp=XBYTE[ADC];/*讀取A/D轉(zhuǎn)換結(jié)果*/ i--;XBYTE[ADCdata+I]=tmp;/**結(jié)果值存儲(chǔ)到數(shù)據(jù)緩沖器*/ XBYTE[ADC]=I;/*啟動(dòng)下一個(gè)模擬輸入通道A/D轉(zhuǎn)換*/ } 兩指針相減-----計(jì)算字符串的長(zhǎng)度 #include main(){

      char *s=”abcdef”;int strlen(char *s);printf(“n length of ‘%%s’=%%dn”,s,strlen(s));} int strlen(char *s){ char *p=s;while(*p!=’