久久久久久久999_99精品久久精品一区二区爱城_成人欧美一区二区三区在线播放_国产精品日本一区二区不卡视频_国产午夜视频_欧美精品在线观看免费

專注電子技術(shù)學(xué)習(xí)與研究
當(dāng)前位置:單片機(jī)教程網(wǎng) >> MCU設(shè)計(jì)實(shí)例 >> 瀏覽文章

一個(gè)程序順序引發(fā)的血案(關(guān)于軟件PWM編程)

作者:huqin   來源:本站原創(chuàng)   點(diǎn)擊數(shù):  更新時(shí)間:2014年04月15日   【字體:

四段不同順序的程序會(huì)有如此巨大的差別!

程序段一:

__interrupt  interrupt_isr(void)

{      

         if(FTC0IRQ==1)                                     //0.02ms

         {

                   FTC0IRQ  = 0;          

                   if(PWM_Flag==0)

                   {      

                            num++;

                            sum++;                                                 

                            if(sum >= 100)                    //2ms

                            {

                                     num=0;

                                     sum=0;

                                     INPUT1=1;//低電平輸出結(jié)束,引腳輸出高電平

                                     INPUT2=1;

                            }

                            if(num >= work)               

                            {

                                     INPUT1=0;//高電平輸出結(jié)束,引腳輸出低電平

                                     INPUT2=0;

                            }

                            Tim_1S++;

                            if(Tim_1S==50000)

                            {

                                     PWM_Flag=1;

                            }               

                   }

                   if(PWM_Flag==1)

                   {      

                            INPUT1=0;//高電平輸出結(jié)束,引腳輸出低電平

                            INPUT2=0;               

                            Tim_1S--;

                            if(Tim_1S==0)

                            {

                                     PWM_Flag=0;

                                     num=0;

                                     sum=0;

                            }               

                   }                                                                                                                      

         }

}

顯然這個(gè)程序的功能是引腳輸出一個(gè)可調(diào)的PWM波形,然后輸出一個(gè)低電平的波形,PWM的波形和這個(gè)低電平的波形持續(xù)的時(shí)間都是1S鐘,程序段一是正確的程序.

下面分析下面的三個(gè)程序的問題:

程序段二:

__interrupt  interrupt_isr(void)

{      

         if(FTC0IRQ==1)                                     //0.02ms

         {

                   FTC0IRQ  = 0;          

                   if(PWM_Flag==0)

                   {                                                              

                            if(++sum >= 100)               //2ms

                            {

                                     num=0;

                                     sum=0;

                                     INPUT1=1;//低電平輸出結(jié)束,引腳輸出高電平

                                     INPUT2=1;

                            }

                            if(++num >= work)           

                            {               

                                     INPUT1=0;//高電平輸出結(jié)束,引腳輸出低電平

                                     INPUT2=0;

                            }

                            Tim_1S++;

                            if(Tim_1S==50000)

                            {

                                     PWM_Flag=1;

                            }               

                   }

                   if(PWM_Flag==1)

                   {      

                            INPUT1=0;//高電平輸出結(jié)束,引腳輸出低電平

                            INPUT2=0;               

                            Tim_1S--;

                            if(Tim_1S==0)

                            {

                                     PWM_Flag=0;

                                     num=0;

                                     sum=0;

                            }               

                   }                                                                                                                      

         }

}

 

程序段二:

現(xiàn)在假設(shè)系統(tǒng)初始化,sum和num都是0,現(xiàn)在假設(shè)work=20,系統(tǒng)初始化后開始疊加運(yùn)算,等到num變?yōu)?0后會(huì)有高電平輸出結(jié)束,引腳輸出低電平,占空比為20%,系統(tǒng)正常運(yùn)行,但等到sum加到100后sum,num會(huì)置為0,然后num會(huì)加1變?yōu)?,此時(shí)下一個(gè)周期到來了,但是初始化卻和第一個(gè)周期不一樣了,這時(shí)num總會(huì)比sum大1,也就是最后輸出的占空比總是比設(shè)定的值會(huì)小1,比如設(shè)置work值為100,那么從起始狀態(tài)開始分析,起始狀態(tài)下num和sum都是0,等sum變?yōu)?00的時(shí)候會(huì)先將num置為0,然后num的值會(huì)做想應(yīng)的加1然后下一個(gè)周期來了,sum和num有了不同的初始值sum的初始值為0而num的初始值卻變?yōu)?,這樣話,時(shí)過境遷,num會(huì)首先變?yōu)?00,這時(shí)sum才是99,這時(shí)就會(huì)了出現(xiàn)一個(gè)短暫的低電平,這個(gè)低電平的持續(xù)時(shí)間剛好是一個(gè)周期,這樣就和我們的初衷相違背了,這時(shí)輸出的占空比不是100%,而是99%.同樣的道理這樣的問題不僅會(huì)出現(xiàn)有占空比為100%的情況,比如此里的占空比是設(shè)置的是20%,那么從初始狀態(tài)到sum變?yōu)?0,然后緊接著num又會(huì)加1變?yōu)?,那么從下一個(gè)周期開始兩個(gè)數(shù)據(jù)又會(huì)出現(xiàn)不同步的情況,從而直接導(dǎo)致下一次等到sum變?yōu)?9的候,num己經(jīng)是100了,從而又直接導(dǎo)致下一個(gè)周期的起始狀態(tài)又變成了sum=0,而num=1.周而復(fù)始,從而真正得到地占空比變?yōu)?9%.

 

程序段三:

__interrupt  interrupt_isr(void)

{      

         if(FTC0IRQ==1)                                     //0.02ms

         {

                   FTC0IRQ  = 0;          

                   if(PWM_Flag==0)

                   {      

                            num++;

                            sum++;                                                                    

                            if(num >= work)               

                            {               

                                     INPUT1=0;//高電平輸出結(jié)束,引腳輸出低電平

                                     INPUT2=0;

                            }

                            if(sum >= 100)           //2ms

                            {

                                     num=0;

                                     sum=0;

                                     INPUT1=1;//低電平輸出結(jié)束,引腳輸出高電平

                                     INPUT2=1;

                            }

                            Tim_1S++;

                            if(Tim_1S==50000)

                            {

                                     PWM_Flag=1;

                            }               

                   }

                   if(PWM_Flag==1)

                   {      

                            INPUT1=0;//高電平輸出結(jié)束,引腳輸出低電平

                            INPUT2=0;               

                            Tim_1S--;

                            if(Tim_1S==0)

                            {

                                     PWM_Flag=0;

                                     num=0;

                                     sum=0;

                            }               

                   }                                                                                                                      

         }

}

關(guān)于第三種情況:

第三種情況倒不存在num和sum不同步的問題,但是有一個(gè)小問題就是當(dāng)work是100

的時(shí)候num會(huì)首先加到100輸出一個(gè)低電平,而這里的期望占空比是100%,也就是沒這里會(huì)有一個(gè)非常短暫的低電平,用示波器也是發(fā)現(xiàn)不了的,因?yàn)槭静ㄆ鞯姆直婺芰是沒有單片機(jī)執(zhí)行指令的速度快,所以說這個(gè)誤差可以忽略不計(jì),不過在邏輯是還是不完美的.

程序段四:

__interrupt  interrupt_isr(void)

{      

         if(FTC0IRQ==1)                                     //0.02ms

         {

                   FTC0IRQ  = 0;          

                   if(PWM_Flag==0)

                   {                                                                       

                            if(++num >= work)           

                            {               

                                     INPUT1=0;//高電平輸出結(jié)束,引腳輸出低電平

                                     INPUT2=0;

                            }

                            if(++sum >= 100)               //2ms

                            {

                                     num=0;

                                     sum=0;

                                     INPUT1=1;//低電平輸出結(jié)束,引腳輸出高電平

                                     INPUT2=1;

                            }

                            Tim_1S++;

                            if(Tim_1S==50000)

                            {

                                     PWM_Flag=1;

                            }               

                   }

                   if(PWM_Flag==1)

                   {      

                            INPUT1=0;//高電平輸出結(jié)束,引腳輸出低電平

                            INPUT2=0;               

                            Tim_1S--;

                            if(Tim_1S==0)

                            {

                                     PWM_Flag=0;

                                     num=0;

                                     sum=0;

                            }               

                   }                                                                                                                      

         }

}

關(guān)于第四種情況:

         第四種情況和第三種情況累似,也不存在num和sum不同步的問題,同樣的問題也會(huì)出現(xiàn)一個(gè)非常短暫的低電平,同樣存在邏輯上的不完美.可以發(fā)現(xiàn)這兩個(gè)程序都有一個(gè)共同的特點(diǎn),就是num=0;和sum=0;都在程序的后面,就是這么一個(gè)小小的程序順序上的差別,都能直接導(dǎo)致num和sum的同步和不同步.這個(gè)問題雖然不是很嚴(yán)重,也就是說這個(gè)問題只會(huì)出現(xiàn)在work=100;的時(shí)候.也就是在其他的情況下沒有這個(gè)問題.不過我還是不想讓他出現(xiàn)這個(gè)問題.

關(guān)于這個(gè)程序的改進(jìn)

         上面的程序可以進(jìn)行如下的改進(jìn),沒有必要使用兩個(gè)變量來分別對(duì)時(shí)間來進(jìn)先計(jì)數(shù),可以只用一個(gè)變量,這樣也可以將計(jì)數(shù)的不同步問題得到根本的上的解決,同時(shí)這個(gè)程序的PWM波的周期也不可調(diào)節(jié),改進(jìn)的程序應(yīng)增加對(duì)PWM波形的調(diào)節(jié)能力,廢話不多話直接上程序.

__interrupt  interrupt_isr(void)

{

         if(FTC0IRQ==1)                                     //0.02ms

         {

                   FTC0IRQ  = 0;

                   if(PWM_Flag==0)                        //輸出PWM波形的狀態(tài)

                   {

                            num++;

                            if(num >= work)

                            {

                                     INPUT1=0;//高電平輸出結(jié)束,引腳輸出低電平

INPUT2=0;

                            }

                            if(num>=sum)//周期為sum

            {

                 num=0;//計(jì)數(shù)器清0,重新開始計(jì)數(shù),

                 INPUT1=1;//高電平輸出結(jié)束,引腳輸出高電平

INPUT2=1;

            }

                            Tim_1S++;

                            if(Tim_1S==50000)

                            {

                                     PWM_Flag=1;

                            }

                   }

                   if(PWM_Flag==1)                        //輸出低電平波形的狀態(tài)

                   {

                            INPUT1=0;//高電平輸出結(jié)束,引腳輸出低電平

                            INPUT2=0;

                            Tim_1S--;

                            if(Tim_1S==0)

                            {

                                     PWM_Flag=0;

                                     num=0;

                                     sum=0;

                            }

                   }

         }

}

         這個(gè)改進(jìn)版的程序輸入有兩個(gè)有效的參數(shù),一個(gè)為work,一個(gè)為sum,sum用來控制PWM波形的周期,work用來控制PWM波形的占空比,簡單粗暴,異常性感.當(dāng)然可以把這個(gè)程序移殖到應(yīng)廣單片機(jī)上啊,這個(gè)是松瀚單片機(jī)的源程序,這個(gè)過程是很簡單的.

         總而言之,這個(gè)改進(jìn)版的程序有以下三個(gè)方面的明顯提升:

1.      計(jì)數(shù)的變量由兩個(gè)變量變?yōu)榱艘粋(gè)變量.

2.      而且原來的程序的PWM波的周期不可調(diào),現(xiàn)在的程序的周期可調(diào).

3.      實(shí)現(xiàn)了模塊化的編程,就像函數(shù)的模式,有兩個(gè)輸入?yún)?shù),沒有輸出參數(shù).
         還可以想一想如果用<=的方式能不能,構(gòu)建一個(gè)完美的程序,這個(gè)問題有時(shí)間再想.先想到這里吧.這個(gè)問題有想過,會(huì)有一點(diǎn)小小的不完美.具體細(xì)節(jié)以后再說.

關(guān)閉窗口

相關(guān)文章

主站蜘蛛池模板: 欧美激情在线播放 | 91欧美激情一区二区三区成人 | 少妇特黄a一区二区三区88av | 99精品视频免费观看 | 亚洲国产精品99久久久久久久久 | 亚洲网站在线观看 | 久久国产亚洲精品 | 99re在线视频 | 成人精品国产一区二区4080 | 久久久成人网 | 久草影视在线 | 国产片侵犯亲女视频播放 | 色综合一区二区三区 | 青草视频在线 | 中文字幕视频在线看5 | 中文字幕不卡在线观看 | 九九精品在线 | 91高清视频在线观看 | 国产精品久久99 | 91麻豆精品国产91久久久资源速度 | 日本在线播放 | 欧美日韩一区二区电影 | 在线看片福利 | 日日夜夜免费精品 | 天天操夜夜爽 | 97视频精品 | 国产永久免费 | 精品亚洲一区二区三区 | 免费啪啪 | 精品视频免费 | 国产一区二区三区日韩 | 美女久久 | 91手机精品视频 | 欧美1区2区 | 成人午夜影院 | 美女在线国产 | 欧美三级视频 | 欧美亚洲视频 | 日韩在线播放第一页 | 久久精品亚洲精品国产欧美 | 1级黄色大片 |