You are on page 1of 24

輸出埠之應用

本章內容豐富,主要包括兩部分:

硬 體 部 分:
認識 8x51 的輸出入埠。
熟悉 LED、蜂鳴器、繼電器、七節顯示器的設計技巧。

程 式 與 實作部分:
驅動蜂鳴器實驗。
驅動繼電器實驗。
霹靂燈及七節顯示器之設計與應用。
3-2 例說 89S51-C 語言

認 識 MCS-51 之 輸 出 埠
3-1 輸出埠之應用

MCS-51 迷 人 的 地 方 之 一 , 就 在 其 四 個 輸 出 入 埠 ! 這 四 個 輸 出 入 埠 之 結
構,大致相同,但各有特別之處,如下說明:

PORT 0 為 8 位元、可位元定址的輸出入埠,以針腳式包裝的 8x51 為例,P0^0


為 39 腳、P0^1 為 38 腳,以此類推,而 P0^7 為 32 腳,如圖 1 所示為其中任
一個位元之內部結構,PORT 0 的特色說明如下:

圖1 PORT 0 內部電路結構(1 個位元)

 PORT 0 的 8 位元皆為開洩極式輸出(Open Drain,簡稱 OD),千萬不要誤


解為圖騰柱輸出,而每支接腳可驅動 8 個 LS 型 TTL 負載。
 PORT 0 內 部 無 提 升 電 阻,執 行 輸 出 功 能 時,外 部 必 須 接 提 升 電 阻 (10k
歐 姆 即 可 )。
 若 要 執 行 輸 入 功 能 , 必 須 先 輸 出 高 準 位 (1), 以 避 免 被 Q 1 干 擾 , 方 能
正確讀取該埠所連接的外部資料。
 若系統連接外部記憶體,則 PORT 0 可做為位址匯流排(A0~A7)及資料匯流
排(D0~D7)之多工接腳,此時內部具有提升電阻,不用外接。

PORT 1 為 8 位元、可位元定址的輸出入埠,以針腳式包裝的 8x51 為例,


P1^0 為 1 腳、P1^1 為 2 腳,以此類推,而 P1^7 為 8 腳,如圖 2 所示為其
中一個位元之內部結構,PORT 1 的特色說明如下:

 PORT 1 內 建 約 30k提 升 電 阻,執 行 輸 出 功 能 時,不 須 外 接 提 升 電 阻。


第三章 輸出埠之應用 3-3

 PORT 1 的 8 位 元 類 似 開 洩 極 式 輸 出 (OD), 但 已 內 接 提 升 電 阻 , 每 支
接 腳 可 驅 動 4 個 LS 型 TTL 負 載 。
 若 要 執 行 輸 入 功 能 , 必 須 先 輸 出 高 準 位 (1), 以 避 免 被 Q 1 干 擾 , 方 能
正確讀取該埠所連接的外部資料。
 若是 8052/8032,則 P1^0 兼具有 Timer 2 的外部脈波輸入功能(即 T2)、P1^1
兼具有 Timer 2 的捕捉/重新載入之觸發輸入功能(即 T2EX)。
 若是 89S51/89S52,進行線上燒錄(ISP)時,其中的 P1^5 做為 MOSI 之用、P1^6
做為 MISO 之用、P1^7 做為 SCK 之用。

圖2 PORT 1 內部電路結構(1 個位元)

PORT 2 為 8 位元、可位元定址的輸出入埠,以針腳式包裝的 8x51 為例,


P2^0 為 21 腳、P2^1 為 22 腳,以此類推,而 P2^7 為 28 腳,如圖 3 所示為
其中一個位元之內部結構,PORT 2 的特色說明如下:

圖3 PORT 2 內部電路結構(1 個位元)


3-4 例說 89S51-C 語言

 PORT 2 內 建 約 30k提 升 電 阻,執 行 輸 出 功 能 時,不 須 外 接 提 升 電 阻。


 PORT 2 的 8 位 元 類 似 開 洩 極 式 輸 出 (OD), 但 已 內 接 提 升 電 阻 , 每 支
接 腳 可 驅 動 4 個 LS 型 TTL 負 載 。
 若 要 執 行 輸 入 功 能 , 必 須 先 輸 出 高 準 位 (1), 以 避 免 被 Q 1 干 擾 , 方 能
正確讀取該埠所連接的外部資料。
 若 系 統 連 接 外 部 記 憶 體,而 外 部 記 憶 體 的 位 址 線 超 過 8 條 時,則 PORT
2 可 做 為 位 址 匯 流 排 (A8~ A15)接 腳 。

圖4 PORT 3 內部電路結構(1 個位元)

PORT 3 為 8 位元、可位元定址的輸出入埠,以針腳式包裝的 8x51 為例,


P3^0 為 10 腳、P3^1 為 11 腳,以此類推,而 P3^7 為 17 腳,如圖 4 所示為
其中一個位元之內部結構。PORT 3 的特色說明如下:

表1 Port 3 之其它功能

PORT 3 其它功能 說 明
P3^0 RXD 串列埠的接收接腳
P3^1 TXD 串列埠的傳送接腳
P3^2 INT0 INT0 中 斷 輸 入
P3^3 INT1 INT1 中 斷 輸 入
P3^4 T0 Timer/Counter 0 輸 入
P3^5 T1 Timer/Counter 1 輸 入
P3^6 WR 寫入外部記憶體控制接腳
P3^7 RD 讀取外部記憶體控制接腳

 PORT 3 的 8 支 接 腳 各 有 其 它 功 能 , 如 表 1 所 示 。
 PORT 3 內 建 約 30k提 升 電 阻,執 行 輸 出 功 能 時,不 須 外 接 提 升 電 阻。
第三章 輸出埠之應用 3-5

 PORT 3 的 8 位 元 類 似 開 洩 極 式 輸 出 (OD), 但 已 內 接 提 升 電 阻 , 每 支
接 腳 可 驅 動 4 個 LS 型 TTL 負 載 。
 若 要 執 行 輸 入 功 能 , 必 須 先 輸 出 高 準 位 (1), 以 避 免 被 Q 1 干 擾 , 方 能
正確讀取該埠所連接的外部資料。

輸出電路設計
3-2 輸出埠之應用

AT89S51 的輸出埠可直接連接數位電路,也可用來驅動 LED、蜂鳴器、繼


電器或固態繼電器等負載,以下就來探討如何與這些負載過招。

3-2-1 驅 動 LED

發 光 二 極 體 (Light-Emitting Diode,
LED)之體積小、低耗電,常被用在微電
腦與數位電路指示裝置。近來 LED 技術
突飛猛進,除紅色、綠色、黃色外,高亮
度的藍色與白色 LED 成為新亮點,進而
取代傳統鎢絲燈泡,成為照明、交通號誌
(紅綠燈)的主流發光元件;而汽車的尾
燈、頭燈,也流行採用 LED。 圖5 LED 特性曲線

圖6 輸出 LED 之連接
3-6 例說 89S51-C 語言

基本上,LED 具有二極體的特色,逆向偏壓或電壓太低時,LED 將不發光;


順向偏壓時,LED 將發光;以紅色 LED 為例,順向偏壓時 LED 兩端約有 1.7V 左
右的壓降(比二極體大),如圖 5 所示為其特性曲線。隨通過 LED 順向電流的增加,
LED 將更亮,但其壽命將縮短,通常採 10m 到 15mA 為宜。89S51 的輸出入埠都類
似開洩極式的輸出,其中的 P1、P2 與 P3 內建 30k提升電阻,不可能從 P1、P2
或 P3 流出 10m 到 15mA!但 AT89S51 的 Port,可吸入大電流。

如 圖 6 之 右 圖,當 輸 出 低 態 時,輸 出 端 的 FET 導 通,輸 出 端 電 壓 約 0V;


而 LED 順 向 電 壓 V D 約 1.7V,所 以 限 流 電 阻 R 兩 端 約 3.3V(即 5-1.7)。若 要 限
制 流 過 LED 的 電 流 I D 為 10mA, 則 此 限 流 電 阻 R 為 :

5  1.7
R  330 
10m

若想要 LED 亮一點,可使 ID 提高至 15mA,則限流電阻 R 改為:

5  1.7
R  220 
15m

對於 TTL 準位的數位電路或微電腦電路,LED 所串接的限流電阻,大多為 200


~470,電阻值越小,LED 越亮。若 LED 為非連續負載(例如 PWM、掃瞄電路或
閃爍燈),則電流還可大一點,甚至採用 50~100之限流電阻即可。

3-2-2 驅動蜂鳴器

圖7 12mm 蜂鳴器之外觀與尺寸

在 微 處 理 電 路 上 常 用 的 發 聲 裝 置 稱 為 蜂 鳴 器 (buzzer), 蜂 鳴 器 類 似 小 型 喇
叭。市售蜂鳴器分為自激式(或主動式)與外激式(或被動式)兩類,自激式蜂鳴器
是一種送電就會輸出固定頻率的裝置;被動式蜂鳴器則必須加入脈波才會發出
聲響,且其聲音的頻率,就是加入脈波的頻率,在此採用外激式蜂鳴器,如圖 7
所示為 12mm 被動式蜂鳴器(編號為 1205)之外觀與尺寸。
第三章 輸出埠之應用 3-7

蜂鳴器所需驅動電流並不大,10mA 綽綽有餘。AT89S51 產生指定頻率的脈波


後,再應用小型雙極性電晶體(Bipolar Junction Transistor, BJT)放大電路,以飽和
/截止的方式驅動蜂鳴器。而可分為高態驅動(active high)與低態驅動(active low),
如下說明:

所謂高態驅動是指輸入高態信號時,可輸出較大電流(飽和),以驅動負載;
輸入低態信號時,不會輸出電流(截止)。

如圖 8 所示,應用 NPN 電晶體構成高態驅動電路,


常用的 NPN 電晶體(如 2N3904、CS9013 等, 約
200),最大輸出電流(icmax)可達 200mA,足以驅動
大部分電路板上的負載。不過,為了讓電晶體能夠
工作在飽和與截止,不管是 AT89S51 裡無內建提
升電阻的 P0,或內建提升電阻的 P1~P3,其提供
的電流都不足以讓 NPN 電晶體飽和,必須外接一
個 10k提供提升電阻,AT89S51 的 Port 輸出高態
時,才能由此提升電阻提供接近 0.5mA 的較大基
圖8 高態驅動電路
極電流(ib ),即可輸出約 100mA 電流(ic)。

圖9 低態驅動電路

所謂低態驅動是指輸入低態信號時,可輸出較大電流(飽和),以驅動負載;輸
入高態信號時,不會輸出電流(截止)。如圖 9 所示,應用 PNP 電晶體構成低態
驅動電路,常用的 PNP 電晶體(如 2N3906、CS9012 等,  約 200、icmax 約
200mA),足以驅動大部分電路板上的負載。不過,為了讓電晶體能夠工作在
3-8 例說 89S51-C 語言

飽和與截止,不管是 AT89S51 裡的哪個 Port,當輸出低態時,都可吸入大電


流(2~8mA)。這個電流足以讓 PNP 電晶體飽和,而為了讓電晶體能快速從飽
和狀態,恢復為截止狀態,在此可使用一個 2.2k的洩放電阻,提供 CB 間少
數載子的洩放路徑,以加速切換。

 由上述可得知,低態驅動方式比高態驅動方式,更容易使
電晶體進入飽和狀態,效率更高。
 在此直接驅動蜂鳴器,負載並沒有串聯限流電阻。設計程
式時,應讓不驅動蜂鳴器時,電晶體保持為截止狀態(高態
驅動電路時,輸出最後低態;低態驅動電路時,輸出最後
高態),才不會浪費電,否則蜂鳴器會發熱。

3-2-3 驅動繼電器

圖10 繼電器之照片、接腳位置圖與尺寸

當 AT89S51 用來控制不同電壓或更大電流的負載時,可應用繼電器(Relay)。電
子電路所使用的繼電器(架構在電路板上),其體積都不大,如圖 10 所示為常用的繼
電器,其上標 示 使 用 的 電 壓 , 如 DC12V、 DC9V、 DC6V、 DC5V 等 。 其 中 c-b
之間為常閉接點(Normal Closed, NC 接點)、c-a 之間為常開接點(Normal Opened, NO 接
點),而只有一組 a-b-c 稱為 1P,兩組則為 2P。這種繼電器很便宜,採公制尺寸,可
直接應用在電路板上,但接腳位置並不適用於麵包板。
第三章 輸出埠之應用 3-9

圖11 電路板上所使用之繼電器及其接腳圖

如圖 11 所示之長條形的繼電器,此為英制尺寸,其接腳配置可直接使用在麵包
板上,屬於精細的電路板用繼電器。其上也會標示使用的電壓,如 DC12V、DC9V、
DC6V、DC5V 等,也可能會繪製其接腳圖。

上述繼電器之激磁電流並不大,約在 10mA 到數十 mA,光靠 AT89S51 輸


出埠的電流恐怕不夠,還需要驅動電路,如圖 12 所示,與驅動蜂鳴器一樣,有
高態驅動與低態驅動之分。不過,驅動繼電器線圈的電感效應明顯,所以在繼
電器線圈兩端,並接一個反相二極體,稱為飛輪二極體,以保護電晶體。

圖12 左為高態驅動電路,右為低態驅動電路

3-2-4 驅動固態繼電器

固態繼電器(Solid State Relay, SSR)與繼電器類似,可由小的信號來控制較大


負載。而 SSR 沒有實體接點,切換接點時不會產生火花與機械式動作。基本上,
SSR 是由光耦合裝置輸入控制信號,而另一端則是較大容量的驅動裝置,如 SCR、
TRIAC 或 IGBT 等,如圖 13 所示為常見的 SSR,其輸出端為 AC250V/10A、採
TRIAC 輸出。
3-10 例說 89S51-C 語言

圖13 固態繼電器之照片與內部電路

SSR 的輸入端是 LED,所以其驅動 SSR 的方法,與驅動 LED 一樣。不過,需要


較大的電壓和電流,才能讓使輸出端的 TRIAC 徹底導通。如圖 14 所示,分別為高態
驅動 SSR 與低態驅動。

圖14 固態繼電器之驅動電路(左為高態驅動、右為低態驅動)

3-2-5 驅動七節顯示器

七 節 顯 示 器 是 利 用 七 個 LED 組 合 而 成 的 顯 示 裝 置,用 以 顯 示 0 到 9 等 10
個 數 字 , 如 圖 15 所 示 :
第三章 輸出埠之應用 3-11

圖15 七節顯示器

七 節 顯 示 器 可 分 為 共 陽 極 與 共 陰 極 兩 種 , 共 陽 極 就 是 把 所 有 LED 的 陽 極
連 接 到 共 同 接 點 com,而 每 個 LED 的 陰 極 分 別 為 a、b、c、d、e、f、g 及 dp(decimal
point,小 數 點 );同 樣 地,共 陰 極 就 是 把 所 有 LED 的 陰 極 連 接 到 共 同 接 點 com,
而 每 個 LED 的 陽 極 分 別 為 a、b、c、d、e、f、g 及 dp,如 圖 16 之 左 圖 所 示 ,
而右圖分別為其外觀與尺寸。

圖16 七節顯示器之結構(左)、外觀(右上)與尺寸(右下)

當我們要使用共陽極(Common Anode, CA)七節顯示器時,首先把 com 腳接


+VCC,再將每支陰極接腳各接一個限流電阻,如圖 17 之左圖所示。在數位或微
電腦電路裡,限流電阻可使用 200 到 330 歐姆,電阻值越大,亮度越弱、電阻值
越小,電流越大。若 a 連接 8x51 輸出埠之最低位元(LSB)、dp 連接 8x51 輸出
埠之最高位元(MSB),驅動信號編碼如表 2 所示。
3-12 例說 89S51-C 語言

圖17 共陽極七節顯示器(左)與共陰極七節顯示器(右)之應用

表2 七節顯示器驅動信號編碼
數字 (dp)gfedcba 16 進 位 (dp)gfedcba 16 進 位 顯示
共陽極編碼 共陰極編碼
0 11000000 0xc0 00111111 0x3f
1 11111001 0xf9 00000110 0x06
2 10100100 0xa4 01011011 0x5b
3 10110000 0xb0 01001111 0x4f
4 10011001 0x99 01100110 0x66
5 10010010 0x92 01101101 0x6d
6 10000011 0x83 00111100 0x3c
7 11111000 0xf8 00000111 0x07
8 10000000 0x80 01111111 0x7f
9 10011000 0x98 01100111 0x37

當 我 們 要 使 用 共 陰 極 (Common Cathode, CC 或 CK)七 節 顯 示 器 時,先 將 com


腳 接 地 (GND),再 將 每 支 陽 極 接 腳 各 接 一 個 限 流 電 阻,如圖 17 之右圖所示,
驅動信號編碼如表 2 所示。很 明 顯 地,共 陽 極 七 節 顯 示 器 的 驅 動 信 號 與 共
陰極七節顯示器的驅動信號相反,我們只要使用其中一組驅動信號編碼
即可,若所使用的編碼與七節顯示器的極性不符,只要在程式裡的輸出
指令中,加一個反相運算子即可。
第三章 輸出埠之應用 3-13

實例演練
3-3 輸出埠之應用

在 本 單 元 裡 將 應 用 前 面 所 介 紹 的 LED、蜂 鳴 器、繼 電 器、七 節 顯 示 器 等 ,


並動手驗證這些裝置的驅動方法。

3-3-1 驅動蜂鳴器實驗

圖18 蜂鳴器實驗電路

1. 如 圖 18 所 示 , 由 P3^7 經 電 晶 體 驅 動 蜂 鳴 器 (完 全 配 合 KT89S51 線 上
燒 錄 實 驗 板 之 蜂 鳴 器 位 置 )。
2. 聲音是由蜂鳴器的振動而產生,蜂鳴器就像是個電磁鐵,電流流過即可激
磁,則蜂鳴器裡發聲的簧片將被吸住;電流消失時,簧片將被放開。若要
產生 f 的頻率,則需於 T 時間內(其中 T=1/f),進行吸、放各一次。換言之,
激磁、斷磁的時間各為 T/2,稱為半週期。例如要產生 1kHz 的頻率,則半
週期為 0.5ms,P3^7 所送出之信號,0.5ms 為高態、0.5ms 為低態。
3. 若 0.5ms 為高態與 0.5ms 為低態為一組信號,總共約 1ms,人類的耳朵無
法反應 1ms 的聲音。因此,須重複送出 100 組(1ms100=100ms),以產生
1kHz 的聲音約 0.1 秒。緊接著,停止動作(靜音)約 0.1 秒後,再連續送出
100 組 0.5ms 為高態與 0.5ms 為低態信號,則可聽到「嗶、嗶」兩聲。
4. 若要 P3^7 輸出高態,可利用「P3^7=1;」指令;同理,若要 P3^7 輸出低態,
3-14 例說 89S51-C 語言

可利用「P3^7=0;」指令。另外,可利用 delay500us()函數產生 0.5ms 之延遲。


5. 使 用 for(i=0;i<count;i++)的 敘 述 , 即 可 執 行 count 組 驅 動 信 號 。
6. 在 此 將 產 生 1kHz 信 號 持 續 0.1 秒 , 停 0.5 秒 , 再 產 生 1kHz 信 號 持 續
0.1 秒 , 停 0.5 秒 。 然 後 從 頭 開 始 執 行 , 即 可 產 生 連 續 的 嗶 聲 。

ch3-3-1.c
/* ch3-3-1.c - 蜂 鳴 器 實 驗 程 式 */
//==宣 告 區 ====================================
#include <reg51.h> // 包 含 8051 暫存器之標頭檔
sbit buzzer = P3^7 ; // 宣 告 蜂 鳴 器 的 位 置 為 Port 3 之 bit 7
void delay500us(int x); // 宣 告 解 析 度 為 0.5ms 之 延 遲 函 數
void pulse_BZ(int count, int TH, int TL); // 宣 告 蜂 鳴 器 發 聲 函 數
//==主 程 式 ====================================
main() // 主 程 式 開 始
{ while(1) // 無 窮 迴 圈 ,程 式 一 直 跑
{ pulse_BZ(100,1,1);
// 蜂 鳴 器 發 聲 100(0.5m+0.5m)=0.1s
delay500us(1000); // 延 遲 10000.5m=0.5 秒
} // while 迴 圈 結 束
} // 主 程 式 結 束
/* 延 遲 函 數 開 始 ,延 遲 x0.5ms */
void delay500us(int x) // 延 遲 函 數 開 始
{ int i,j; // 宣 告 整 數 變 數 i,j
for (i=0;i<x;i++) // 計 數 x 次 ,延 遲 約 x0.5ms
for (j=0;j<60;j++); // 計 數 60 次 , 延 遲 約 0.5ms
} // 延 遲 函 數 結 束
/* 蜂 鳴 器 發 聲 函 數 ,count=計 數 次 數 ,TH=高 態 時 間 ,TL=低 態 時 間 */
void pulse_BZ(int count,int TH,int TL) // 蜂 鳴 器 發 聲 函 數 開 始
{ int i; // 宣 告 整 數 變 數 i
for(i=0;i<count;i++) // 計 數 count 次
{ buzzer=0; // 輸 出 低 態 (低 態 驅 動 )
第三章 輸出埠之應用 3-15

delay500us(TL); // 延 遲 TL0.5ms
buzzer=1; // 輸出高態
delay500us(TH); // 延 遲 TH0.5ms
} // for 迴 圈 結 束
} // 蜂鳴器發聲函數結束

1. 在 Keil C 裡 撰 寫 程 式 , 並 進 行 建 構 (按 鈕,或 鍵 ), 以 產 生
*.HEX 檔。若 有 下 方 的 建 構 輸 出 視 窗 出 現 錯 誤,則 按 其 指 示 的 位 置 檢
視原始程式,並修正之,並將它記錄在實驗報告裡。
2. 在此使用 KT89S51 線上燒錄實驗板,先連接 KT89S51 線上燒錄實驗板與
電腦之 USB 纜線,再啟動 s51_pgm 程式,按其中的 鈕,指定載入
本實驗所產生的 hex 程式檔,最後,按 鈕(或 鍵)即可快速燒
錄。完成燒錄後,KT89S51 線上燒錄實驗板即產生連續的嗶聲。
3. 若非使用 KT89S51 線上燒錄實驗板,則先按圖 18 連接線路,並使用 8051
的燒錄器,載入剛才產生的*.HEX,並燒錄到 AT89S51,再把該 AT89S51
置入實體電路。最後,送電看看是否正常?
4. 撰 寫 實 驗 報 告 。

 若 希 望 產 生 1kHz 聲 音 0.2 秒 、 暫 停 0.05 秒 、 500Hz 聲 音 0.1


秒 、 暫 停 0.2 秒 , 應 如 何 修 改 ?
 在 此 使 用 delay500us 函 數 , 其 解 析 度 為 0.5ms, 可 產 生 的 生 音
頻 率 最 高 為 1kHz。delay500us 函 數 利 用 計 數 0~59,而 產 生 0.5ms
延 遲 , 若 改 為 計 數 0~11, 應 可 產 生 約 0.1ms 延 遲 。
 中 音 Do 的 頻 率 為 523Hz、 Re 的 頻 率 為 587Hz、 Mi 的 頻 率 為
659Hz,請 設 計 一 個 程 式 能 產 生 Do、Re、Mi,每 個 音 長 0.5 秒 ,
產生三個音後,靜音 1 秒後,重新開始。

3-3-2 驅動繼電器實驗

1. 如 圖 19 所 示 , 由 P3^7 經 電 晶 體 驅 動 蜂 鳴 器 , 而 P3^6 經 電 晶 體 驅 動
繼電器。
2. 基本上,繼電器的工作原理與蜂鳴器的工作原理(詳見 3-2 節)類似,若要繼
電器激磁時,可利用「P3^6=1;」指令,使 P3^6 輸出高態即可;若要繼電
器斷磁時,可利用「P3^6=0;」指令,使 P3^6 輸出低態即可。
3-16 例說 89S51-C 語言

3. 繼電器與蜂鳴器不同之處,在於蜂鳴器的操作頻率較高,而繼電器的操作
頻率較低。另外,繼電器所操作的接點,可控制外接電路,例如外接 AC110V
的電燈泡等負載。當然,一定要看清楚繼電器上所標示的接點容量,以圖
11 的繼電器(3-8 頁)為例,其上面標示「0.5A,120VAC RES.」或「1A, 24VDC
RES.」或「0.3A 60VDC RES.」,表示該接點可控制 0.5A/120VAC 電阻性
負 載 , 或 1A/24VDC 電 阻 性 負 載 , 或 0.3A/60VDC 電 阻 性 負 載 。 以
0.5A/120VAC 電阻性負載為例,即一般插座(AC110V),而 0.5A 負載電流
可驅動 55W 電阻性負載,所以這個小小的繼電器可用來控制 40W 或 50W
電燈泡沒問題!
4. 在 本 實 驗 的 目 的 是 讓 P3^6 所 連 接 的 繼 電 器,每 0.5 秒 鐘 開 關 一 次,而
開 關 10 次 後 , 蜂 鳴 器 「 嗶 、 嗶 」 兩 聲 ; 然 後 從 頭 開 始 執 行 。

圖19 繼電器實驗電路

ch3-3-2.c
/* ch3-3-2.c - 繼 電 器 實 驗 程 式 */
//==宣 告 區 ========================================
#include <reg51.h> // 包 含 8051 暫 存 器 之 標 頭 檔
sbit buzzer = P3^7; // 宣 告 蜂 鳴 器 的 位 置
sbit relay = P3^6; // 宣 告 繼 電 器 的 位 置
void delay500us(int x); // 宣 告 延 遲 函 數
void pulse_BZ(int count,int TH,int TL); // 宣 告 蜂 鳴 器 發 聲 函 數
void pulse_RL(int count,int TH,int TL); // 宣 告 繼 電 器 控 制 函 數
//==主 程 式 ========================================
main() // 主 程 式 開 始
第三章 輸出埠之應用 3-17

{ while(1) // 無 窮 迴 圈 ,程 式 一 直 跑
{ pulse_RL(10,1000,1000);
// 繼 電 器 使 燈 亮 滅 各 10 次 ,各 10000.5m=0.5s
pulse_BZ(100,1,1);
// 蜂 鳴 器 第 1 聲 嗶 ,約 100*(0.5m+0.5m)=0.1s
delay500us(200); // 延 遲 2000.5ms=0.1s
pulse_BZ(100,1,1);
// 蜂 鳴 器 第 2 聲 嗶 ,約 100*(0.5m+0.5m)=0.1s
delay500us(200); // 延 遲 2000.5ms=0.1s
} // while 迴 圈 結 束
} // 主 程 式 結 束
// 延 遲 函 數 , 延 遲 約 x*0.5ms
void delay500us(int x) // 延 遲 函 數 開 始
{ int i,j; // 宣 告 整 數 變 數 i,j
for (i=0;i<x;i++) // 計 數 x 次 ,延 遲 約 x0.5ms
for (j=0;j<60;j++); // 計 數 60 次 , 延 遲 約 0.5ms
} // 延 遲 函 數 結 束
/* 蜂 鳴 器 發 聲 函 數 ,count=計 數 次 數 ,TH=高 態 時 間 ,TL=低 態 時 間 */
void pulse_BZ(int count,int TH,int TL) // 蜂 鳴 器 發 聲 函 數
{ int i; // 宣 告 整 數 變 數 i
for(i=0;i<count;i++) // 計 數 count 次
{ buzzer=0; // 輸 出 低 態 (低 態 驅 動 )
delay500us(TL); // 延 遲 TL0.5ms
buzzer=1; // 輸 出 高 態
delay500us(TH); // 延 遲 TH0.5ms
} // for 迴 圈 結 束
} // 蜂 鳴 器 發 聲 函 數 結 束
/* 繼 電 器 控 制 函 數 ,count=計 數 次 數 ,TH=激 磁 時 間 ,TL=消 磁 時 間 */
void pulse_RL(int count,int TH,int TL) // 繼 電 器 控 制 函 數 開 始
{ int i; // 宣 告 整 數 變 數 i
for(i=0;i<count;i++) // 計 數 count 次
{ relay=1; // 輸 出 高 態 ,繼 電 器 激 磁 (燈 亮 )
delay500us(TH); // 延 遲 TH0.5ms
relay=0; // 輸 出 低 態 ,繼 電 器 消 磁 (燈 滅 )
delay500us(TL); // 延 遲 TL0.5ms
} // for 迴 圈 結 束
} // 繼 電 器 控 制 函 數 結 束
3-18 例說 89S51-C 語言

1. 在 Keil C 裡 撰 寫 程 式 , 並 進 行 建 構 (按 鈕,或 鍵 ), 以 產 生
*.HEX 檔。若 有 下 方 的 建 構 輸 出 視 窗 出 現 錯 誤,則 按 其 指 示 的 位 置 檢
視原始程式,並修正之,並將它記錄在實驗報告裡。
2. 在此使用 KT89S51 線上燒錄實驗板,先連接 KT89S51 線上燒錄實驗板與
電腦之 USB 纜線,並在麵包板上按圖 19 連接一個電晶體驅動繼電器的電
路。若不想外接電晶體驅動繼電器的電路。以 P1^6 的 LED 代替繼電器,
只要將程式中的「sbit relay=P3^6;」,改為「sbit relay=P1^6;」,再按
鍵重新建構。
3. 啟動 s51_pgm 程式,按其中的 鈕,指定載入本實驗所產生的 hex
程式檔,最後,按 鈕(或 鍵)即可快速燒錄。完成燒錄後,
KT89S51 線上燒錄實驗板上的 DS2 LED,將閃 10 下後,嗶兩聲,再重新
開始。
4. 撰 寫 實 驗 報 告 。

 在 此 使 用 兩 層 式 計 數 迴 圈 的 delay1ms 函 數,其 解 析 度 為 1ms,


最 多 可 產 生 32,767ms(約 32 秒 )延 遲。若 改 為 三 層 式 計 數 迴 圈,
最 內 層 仍 為 1ms 延 遲,中 間 層 計 數 迴 圈 計 數 0~999,則 解 析 度
變 為 1s, 最 多 可 產 生 32,767s(約 9 小 時 )延 遲 。
 若 要 讓 繼 電 器 10 秒 後 激 磁 , 並 嗶 一 聲 ; 經 1 分 鐘 後 斷 磁 , 再
嗶一聲,如此週而復始。
第三章 輸出埠之應用 3-19

3-3-3 霹靂燈實例演練

圖20 霹靂燈實驗電路

1. 如 圖 20 所 示 , 由 P1 驅 動 8 個 LED, 當 輸 出 0 時 , LED 亮 、 輸 出 1
時 , LED 不 亮 。
2. 所謂「霹靂燈」是指在一排 LED 裡(在此使用 8
個),任何時間只有一個 LED 亮,而亮燈的順利
為由左而右、再由右而左,感覺上就像一個 LED
由左跑到右、再由右跑到左,如圖 21 所示。

3. 在程式設計上,有很多方法可以達到這個目的,
例如採用計數迴圈方式,首先左移 7 次,再右移
7 次,如此循環不停。左移可採用「LED<<1;」
指令,右移可採用「LED>>1;」指令。而計次迴 圖21 霹靂燈動作示意圖
圈方式,則以 for 敘述即可達到目的。

4. LED 之初始值為 11111110(1 不亮、0 亮),左移時,右邊將移入 0,變成


11111100,所以,必須將最右邊位元改為 1。所以,在左移後利用 OR 運
算(即「LED=(LED<<1)|0x01;」指令),將 11111110 變成 11111101。同理,
在進行右移時,可應用「LED=(LED>>1)|0x80;」指令。
5. 另 外 , 也 可 以 採 用 判 斷 的 方 式 , 依 左 移 為 例 , 原 本 為 LED 的 內 容 為
3-20 例說 89S51-C 語言

「 11111110」 , 左 移 7 次 後 變 成 為 「 01111111」 。 因 此 , 發 現 LED


的 內 容 為 「 01111111」 時 , 表 示 要 改 變 為 右 移 。 同 樣 地 , 右 移 7 次
後 又 變 成 為 「 11111110」 , 這 又 是 進 行 左 移 的 判 斷 條 件 。 如 此 循 環
執行,即為霹靂燈。

ch3-3-3.c
/* ch3-3-3.c - 霹 靂 燈 實 驗 程 式 */
//==宣 告 區 ============================================
#include <reg51.h> // 包 含 8051 暫 存 器 之 標 頭 檔
#define LED P1 // 定 義 LED 接 至 Port 1
void delay1ms(int x); // 宣 告 延 遲 函 數
//==主 程 式 ============================================
main() // 主 程 式 開 始
{ char i; // 宣告變數 i
LED=0xfe; // 初 值 =1111 1110,只 有 最 右 1 燈 亮
while(1) // 無 窮 迴 圈 ,程 式 一 直 跑
{ for(i=0;i<7;i++) // 左 移 7 次
{ delay1ms(250); // 延 遲 2501m=0.25s
LED=(LED<<1)|0x01; // 左 移 1 位 ,並 設 定 最 低 位 元 為 1
} // 左 移 結 束 ,只 有 最 左 1 燈 亮
for(i=0;i<7;i++) // 右 移 7 次
{ delay1ms(250); // 延 遲 2501m=0.25s
LED=(LED>>1)|0x80; // 右 移 1 位 ,並 設 定 最 高 位 元 為 1
} // 結 束 右 移 ,只 有 最 右 1 燈 亮
} // while 迴 圈 結 束
} // 主 程 式 結 束
/* 延 遲 函 數 ,延 遲 約 x1ms */
void delay1ms(int x) // 延 遲 函 數 開 始
{ int i,j; // 宣 告 整 數 變 數 i,j
for (i=0;i<x;i++) // 計 數 x 次 ,延 遲 x1ms
for (j=0;j<120;j++); // 計 數 120 次 , 延 遲 1ms
} // 延 遲 函 數 結 束
第三章 輸出埠之應用 3-21

1. 在 Keil C 裡 撰 寫 程 式 , 並 進 行 建 構 (按 鈕,或 鍵 ), 以 產 生
*.HEX 檔。若 有 下 方 的 建 構 輸 出 視 窗 出 現 錯 誤,則 按 其 指 示 的 位 置 檢
視原始程式,並修正之,並將它記錄在實驗報告裡。
2. 在此使用 KT89S51 線上燒錄實驗板,先連接 KT89S51 線上燒錄實驗板與
電腦之 USB 纜線即可。
3. 啟動 s51_pgm 程式,按其中的 鈕,指定載入本實驗所產生的 hex
程式檔,最後,按 鈕(或 鍵)即可快速燒錄。完成燒錄後,
KT89S51 線上燒錄實驗板上的 8 個 LED,將單燈左右跑。
4. 撰 寫 實 驗 報 告 。

 請修改該程式,讓它變成雙燈的霹靂燈功能。
 請 以「 判 斷 」的 方 式,重 新 撰 寫 單 燈 的 霹 靂 燈 程 式,並 驗 證 其
功能。
 請 修 改 單 燈 的 霹 靂 燈 程 式,讓 左 右 移 一 趟 後,嗶 一 聲,再 重 新
開始。

3-3-4 驅動七節顯示器實驗

圖22 七節顯示器實驗電路
3-22 例說 89S51-C 語言

1. 如 圖 22 所 示 , 由 P0 驅 動 七 節 顯 示 器 , 其 中 使 用 330 歐 姆 電 阻 器 做
為限流電阻。
2. 七 節 顯 示 器 上 所 顯 示 的 數 字 , 從 0 開 始 , 每 隔 0.5 秒 增 加 1, 直 到 9
之後,再從 0 開始,如此循環不停。
3. 在本實驗的程式裡,將利用陣列方式儲存驅動信號的編碼,再逐一
將 陣 列 裡 的 資 料 輸 出 到 Port 2 即 可 。

ch3-3-4.c
/* ch3-3-4.c - 七 節 顯 示 器 實 驗 程 式 */
//==宣 告 區 =====================================
#include <reg51.h> // 包 含 8051 暫 存 器 之 標 頭 檔
#define SEG P0 // 定 義 七 節 顯 示 器 接 至 Port 0
/* 宣 告 七 節 顯 示 器 驅 動 信 號 陣 列 (共 陽 ) */
char code TAB[10]={ 0xc0, 0xf9, 0xa4, 0xb0, 0x99, // 數 字 0-4 編 碼
0x92, 0x83, 0xf8, 0x80, 0x98 }; // 數 字 5-9 編 碼
void delay1ms(int); // 宣 告 延 遲 函 數
//==主 程 式 =====================================
main() // 主 程 式 開 始
{ char i; // 宣 告 字 元 變 數 i
while(1) // 無 窮 迴 圈 ,程 式 一 直 跑
for(i=0;i<10;i++) // 顯 示 0-9,共 10 次
{ SEG=TAB[i]; // 顯 示 數 字
delay1ms(500); // 延 遲 5001m=0.5 秒
} // for 迴 圈 結 束
} // 主 程 式 結 束
/* 延 遲 函 數 ,延 遲 約 x1ms */
void delay1ms(int x) // 延 遲 函 數 開 始
{ int i,j; // 宣 告 整 數 變 數 i,j
for (i=0;i<x;i++) // 計 數 x 次 ,延 遲 x1ms
for (j=0;j<120;j++); // 計 數 120 次 , 延 遲 1ms
} // 延 遲 函 數 結 束
第三章 輸出埠之應用 3-23

圖23 KDM 實驗組之接線(隨書光碟中的投影片有彩圖動態展示)

1. 在 Keil C 裡 撰 寫 程 式 , 並 進 行 建 構 (按 鈕,或 鍵 ), 以 產 生
*.HEX 檔。若 有 下 方 的 建 構 輸 出 視 窗 出 現 錯 誤,則 按 其 指 示 的 位 置 檢
視原始程式,並修正之,並將它記錄在實驗報告裡。
2. 在此使用 KDM 實驗組(KT89S51 線上燒錄實驗板與 KDM 板之組合),請按
圖 23 連接線路,再以 USB 纜線連接 KT89S51 線上燒錄實驗板與電腦即可。
3. 啟動 s51_pgm 程式,按其中的 鈕,指定載入本實驗所產生的 hex
程式檔,最後,按 鈕(或 鍵)即可快速燒錄。完成燒錄後,
KDM 板上的七節顯示器將循序有 0 到 9,週而復始地顯示。
4. 撰 寫 實 驗 報 告 。

 在 此 以「 SEG=TAB[i];」指 令,依 序 遞 增 i,七 節 顯 示 器 將 可 順


序 顯 示 0 到 9。 換 言 之 , 依 序 遞 減 i, 七 節 顯 示 器 將 可 逆 序 顯
示 0 到 9。
 應 用「 for(i=0;i<10;i++)」計 數 迴 圈,即 可 讓 i 由 0 順 序 遞 增 到
9;利 用「 for(i=9;i>=0;i--)」指 令 計 數 迴 圈,即 可 讓 i 由 9 順 序
遞 減 到 0。
 請 修 改 本 實 驗 裡 的 程 式,讓 七 節 顯 示 器 從 0 開 始 顯 示,遞 增 到
9; 再 從 頭 開 始 七 節 顯 示 器 從 9 開 始 顯 示 , 遞 減 到 0。
3-24 例說 89S51-C 語言

即時練習
3-4 輸出埠之應用

在本章裡,介紹了 8x51 的輸出入埠、輸出電路的設計等硬體部分;在軟體方


面,更進行四項週邊裝置的控制實驗。請試著回答下列問題,以驗證學習成效。

( )1. 在 8x51 的 輸 出 入 埠 裡 , 哪 個 輸 出 入 埠 執 行 在 輸 出 功 能 時 沒 有 內 建 提
升 電 阻 ? (A) P0 (B) P1 (C) P2 (D) P3 。
( )2. 在 Keil C 的程式裡,若要指定 Port 0 的 bit 3,如何撰寫?
(A) P0.3 (B) Port 0.3 (C) P0^3 (D) Port 0^3。
( )3. 8x51 的 Port 0 採用哪種電路結構? (A) 開集極式輸出 (B) 開洩極式輸
出 (C) 開射極式輸出 (D) 圖騰柱輸出 。
( )4. 在 8x51 裡,若 要 擴 充 外 部 記 憶 體 時,資 料 匯 流 排 連 接 哪 個 輸 出 入 埠 ?
(A) P0 (B) P1 (C) P2 (D) P3 。
( )5. 點 亮 一 般 的 LED, 所 耗 用 的 電 流 約 為 多 少 ? (A) 1 至 5 微 安
(B) 10 至 20 微 安 (C) 1 至 5 毫 安 (D) 10 至 20 毫 安 。
( )6. 基 本 上 , 蜂 鳴 器 屬 於 哪 種 負 載 ? (A) 電 阻 性 負 載 (B) 電 感 性 負 載
(C) 電 容 性 負 載 (D) 不 導 電 負 載 。
( )7. 關 於 SSR 的 敘 述,下 列 何 者 正 確 ? (A) 便 宜 (B) 不 會 發 熱 (C) 沒
有 噪 音 (D) 壽 命 較 短 。
( )8. 在繼電器裡,所謂 NO 接點是一種什麼接點? (A) 不使用的接點 (B) 不
存在的接點 (C) 激磁後即開路的接點 (D) 常開接點 。
( )9. 所謂 2P 的繼電器,代表什麼意思? (A) 只有 2 個接點 (B) 兩相的負載
(C) 兩組電源 (D) 2 組 c 接點。
( )10. 共 陽 極 七 節 顯 示 器 之 驅 動 信 號 有 何 特 色 ?
(A) 低 態 點 亮 (B) 低 態 不 亮 (C) 高 態 點 亮 (D) 以 上 皆 非 。

1. 試 述 P0 與 P2 接 腳 的 其 它 功 能 ?
2. 試 述 P3 接 腳 的 其 它 功 能 ?
3. 試 問 繼 電 器 與 SSR 固 態 繼 電 器 的 差 異 ?
4. 在 電 晶 體 驅 動 繼 電 器 的 電 路 裡 , 繼 電 器 的 線 圈 兩 端 並 接 一 個 逆 向 二 極 體 ,
其功能為何?
5. 試 撰 寫 一 個 約 1 分 鐘 的 延 遲 函 數 ?

You might also like