MATLAB課程設(shè)計(jì)
《MATLAB課程設(shè)計(jì)》由會(huì)員分享,可在線閱讀,更多相關(guān)《MATLAB課程設(shè)計(jì)(28頁(yè)珍藏版)》請(qǐng)?jiān)谘b配圖網(wǎng)上搜索。
1、 課 程 設(shè) 計(jì)(論 文) 題目:用MATLAB語(yǔ)言程序開發(fā)湊五子棋游戲 專 業(yè): 信息與計(jì)算科學(xué) 指導(dǎo)教師: 張大海 學(xué)生姓名: 謝艷濤 班級(jí)-學(xué)號(hào): 信計(jì)131-30 學(xué)生姓名: 黃元福 班級(jí)-學(xué)號(hào): 信計(jì)131-26 學(xué)生姓名: 辛 安 班級(jí)-學(xué)號(hào): 信計(jì)131-22 2016年 11月 摘 要 湊五子棋是一種兩人對(duì)弈的純策略型棋類游戲,應(yīng)用MATLAB語(yǔ)言編寫程序可以在計(jì)算機(jī)上實(shí)現(xiàn)二人對(duì)弈湊五子棋功能。二人
2、對(duì)弈湊五子棋程序由歡迎界面顯示、游戲界面生成、光標(biāo)移動(dòng)與落子、判斷勝負(fù)、悔棋功能、提供音效等子程序構(gòu)成;程序中應(yīng)用了結(jié)構(gòu)體、數(shù)組、全局變量、按鍵處理和圖形編程等元素和語(yǔ)句。程序通過棋盤和棋子圖像生成、二人移子與落子和判斷勝負(fù)等功能的實(shí)現(xiàn),在計(jì)算機(jī)上實(shí)現(xiàn)了二人湊五子棋對(duì)弈。 目 錄 摘 要 2 第1章:需求分析 3 1.1湊五子棋背景 3 1.2 湊五子棋需求分析和流程設(shè)計(jì) 4 第2章:概要設(shè)計(jì) 7 2.1 各類頭文件和全局變量 7 2.2 畫面顯示模塊 8 第3章:詳細(xì)設(shè)計(jì) 11 3.1 玩家操作模塊 11 3
3、.2音效提供模塊 11 3.3 勝負(fù)判斷模塊 12 第4章:調(diào)試分析 13 4.1 圖形模塊 13 4.2 玩家操作模塊 13 4.3 勝負(fù)判斷模塊 14 第5章:用戶手冊(cè) 14 第6章:小組分工 15 第7章:結(jié)論與心得 16 第8章 :源程序代碼 16 第1章:需求分析 1.1湊五子棋背景 傳統(tǒng)湊五子棋的棋具與圍棋相同,棋子分為黑白兩色,棋盤為1818,棋子放置于棋盤線交叉點(diǎn)上。兩人對(duì)局,各執(zhí)一色,輪流下一子,先將橫、豎或斜線的5個(gè)或5個(gè)以上同色棋子連成不間斷的一排者為勝。 因?yàn)閭鹘y(tǒng)湊五子棋在落子后不能移動(dòng)或拿掉,所以也可以用紙和筆來(lái)進(jìn)行游戲。
4、 1.2 湊五子棋需求分析和流程設(shè)計(jì) 本程序設(shè)計(jì)為人與人對(duì)弈,一方執(zhí)黑棋,一方執(zhí)白棋,輪流走棋,每方都試圖在游戲結(jié)束前讓自己的棋子五子相連,首先實(shí)現(xiàn)五子相連的一方獲勝。程序執(zhí)行過程中,要求棋盤、棋子時(shí)時(shí)可見,游戲界面有提示信息輪到何方下棋,人可以通過按鍵盤按鍵移動(dòng)光標(biāo),再點(diǎn)擊enter鍵擺放棋子,并且每落一子都有系統(tǒng)聲音,創(chuàng)新之處是可以提供悔棋功能。 1.2.1 程序需求分析 根據(jù)功能需求,將程序分為畫面顯示、玩家操作、音效提供、勝負(fù)判斷五個(gè)模塊,以下分析各模塊的需求。 畫面顯示模塊:程序開始運(yùn)行時(shí),顯示制作者和給出歡迎及退出界面;游戲開始后要求生成1818的棋盤圖
5、像,并在棋盤上方顯示歡迎信息“歡迎play our湊五子棋”,棋盤下方游戲顯示應(yīng)該輪到甲方或者乙方落子,棋盤左右顯示雙方操作方式,進(jìn)行過程中,要求實(shí)時(shí)顯示棋盤上已落下的棋子,甲方為白球,乙方為白圈;分出勝負(fù)后,要求給出游戲結(jié)束畫面,并且詢問用戶是否需要繼續(xù)游戲。 玩家操作模塊:程序開始時(shí),需玩家確定選擇“人人對(duì)戰(zhàn)”后開始游戲;游戲過程中,兩個(gè)玩家通過不同的按鍵移動(dòng)光標(biāo),選擇落子;游戲進(jìn)行過程中,當(dāng)前玩家下棋后,另一位玩家下棋前,當(dāng)前玩家可以悔棋。悔棋提示在棋盤右下方,為按鍵“b”。游戲結(jié)束時(shí),有玩家選擇是否開始新游戲。 音效提供模塊:玩家每落一子,系統(tǒng)提供音效一聲,增加下棋的趣味性。
6、 勝負(fù)判斷模塊:實(shí)時(shí)監(jiān)測(cè)棋盤上棋子,一旦某一色棋子出現(xiàn)五子連線,終止游戲程序,并著色連成一線的五子,棋盤下方彈出該色玩家勝出信息。 1.2.2程序流程設(shè)計(jì) 根據(jù)程序需求分析結(jié)果,可以得出程序的總體結(jié)構(gòu)圖如圖1,程序總體流程圖如圖2。 五子棋游戲 湊五子棋 模塊二: 玩家操作 模塊三: 音效提供 模塊四: 勝負(fù)判斷 模塊一: 畫面顯示 圖1 湊五子棋總體結(jié)構(gòu)圖 開始 制作者展示
7、 進(jìn)入菜單界面 N 人人對(duì)戰(zhàn)? 退出游戲 Y 是否繼續(xù)新游戲 ? 開始游戲 ESMATLAB Y 確認(rèn)退出? b 悔棋 甲方判斷 N Enter 甲方獲勝? 退出游戲 顯示甲方獲勝消息 Y 確認(rèn)退出? N 乙方判斷 ESMATLAB b 悔棋 Y Enter N 顯示乙方獲勝消息 乙方獲勝? Y N 圖2 程序總體流程圖 第2章:概要設(shè)計(jì) 2.1 各類
8、頭文件和全局變量
#inmatlablude
9、.2 畫面顯示模塊 畫面顯示模塊由歡迎界面,游戲棋盤界面,確認(rèn)是否退出對(duì)話框界面,以及感謝使用界面組成。 畫面顯示模塊函數(shù)如下: void Welmatlabome() //歡迎界面 void Draw() //繪畫游戲棋盤界面 void MATLABlean() //清除—→運(yùn)動(dòng)的軌跡 void menu_matlabhoose(matlabhar press) //選擇是否退出游戲?qū)υ捒? void PutDown() //顯示落子函數(shù) void goto_xy(int x, int y) //光標(biāo)移動(dòng)函數(shù)
10、 畫面效果圖如圖 第3章:詳細(xì)設(shè)計(jì) 3.1 玩家操作模塊 棋子的移動(dòng)與落子有鍵盤上按鍵控制,本程序選取甲乙雙方按鍵都為W、S、↑、↓、←、→和回車鍵,“b”,“ESMATLAB”,分別代表上移、下移、左移、右移光標(biāo)和落子,悔棋,退出。在光標(biāo)移動(dòng)的過程中,光標(biāo)按照玩家按鍵移動(dòng);在玩家按下落子按鍵后,程序自動(dòng)調(diào)用棋子顯示子程序和判斷勝負(fù)子程序。當(dāng)前玩家下棋后,另一位玩家下棋前,當(dāng)前玩家可以悔棋?;谄逄崾驹谄灞P右下方,為按鍵“b”。甲乙的落子后,程序會(huì)為落子處的數(shù)組元素賦一個(gè)特定值(玩家甲的棋子賦為1,玩家乙的棋子賦為2),用于判定勝負(fù)和悔棋。 玩家操作模塊主
11、要由以下函數(shù)構(gòu)成: void Rematlabord() //記錄棋子的情況 void go_bamatlabk(int x1,int y1) //悔棋函數(shù) void Play(matlabhar matlabh) //讀取鍵盤的操作 移動(dòng)光標(biāo) 下棋和悔棋操作 3.2音效提供模塊 為了提高游戲的趣味性,我們?yōu)楸居螒蛱峁┝撕?jiǎn)單系統(tǒng)音效。程序語(yǔ)句很簡(jiǎn)單 printf("\a"); //\a表示蜂鳴聲 3.3 勝負(fù)判斷模塊 勝負(fù)判斷模塊是程序的關(guān)鍵,該模塊的設(shè)計(jì)直接關(guān)系到程序的運(yùn)行速率和運(yùn)行結(jié)果的正確與否。本函數(shù)根據(jù)每次落子
12、的位置,分別向上、下、左、右、左上、左下、右上、右下八個(gè)方向判斷是否有相同顏色的棋子連成五子,如果成立,游戲就結(jié)束,并顯示提示信息,否則繼續(xù)落子。 以下簡(jiǎn)析本程序流程:,由獲勝條件可以知,通過判斷行、列、斜邊、反斜邊方向上是否有連續(xù)的5個(gè)子即可得出是否獲勝結(jié)果。在游戲開始時(shí),將棋盤初始化,即將棋盤抽象為一個(gè)18*18的數(shù)組,數(shù)組中每個(gè)元素?cái)?shù)值設(shè)為0。甲方落子時(shí),將數(shù)組內(nèi)相應(yīng)坐標(biāo)處元素賦值為2;乙方落子時(shí),將數(shù)組內(nèi)相應(yīng)坐標(biāo)處元素賦值為1。通過循環(huán)掃描棋盤數(shù)組,經(jīng)掃描后,如發(fā)現(xiàn)在行、列、斜邊、反斜邊方向上有五個(gè)連續(xù)的2,甲方獲勝;如發(fā)現(xiàn)在行、列、斜邊、反斜邊方向上有五個(gè)連續(xù)的1,乙方獲勝。 勝
13、負(fù)判斷模塊主要由一個(gè)函數(shù)構(gòu)成: int Judge() //判斷勝負(fù)函數(shù) 第4章:調(diào)試分析 4.1 圖形模塊 1.在圖形模塊中,因?yàn)槭堑谝淮问褂?,所以剛開始時(shí)對(duì)于棋盤創(chuàng)建的位置把握有些欠缺。 解決方案:參考書本以及google,找出最合適的位置坐標(biāo)。 2. 在構(gòu)建棋子時(shí)候,發(fā)現(xiàn)MATLAB語(yǔ)言中似乎對(duì)顏色的處理有些錯(cuò)誤,當(dāng)棋譜線的顏色為白色時(shí),無(wú)法構(gòu)建黑色棋子,只能畫出白色棋子。 解決方案:用白圈區(qū)別于白球,類似白子和黑子。 4.2 玩家操作模塊 1. 在玩家操作模塊中,出現(xiàn)的最大問題之一就是棋盤已經(jīng)有棋子的地方還可以覆蓋另一個(gè)棋子。
14、解決方案:通過在PutDown()函數(shù)中添加if條件語(yǔ)句,判定如果所在位置對(duì)應(yīng)的數(shù)組值不等于0時(shí),不能落子。 2. 另一個(gè)問題就是之前提到的,操作定位框的時(shí)候會(huì)將定位框移到棋盤之外造成溢出。 解決方案: 通過if語(yǔ)句判定,如果操作框超出范圍則移動(dòng)到對(duì)應(yīng)相反位置,例如移動(dòng)棋盤最上端,若繼續(xù)向上移動(dòng),則移動(dòng)至棋盤最下端對(duì)應(yīng)位置。 3. 還有一個(gè)就是悔棋模塊中,通過將現(xiàn)有棋子覆蓋與棋盤底色相同的顏色來(lái)覆蓋后,棋譜線條部分也會(huì)被覆蓋。 解決方案:在go_bamatlabk();即悔棋函數(shù)。用棋譜線來(lái)覆蓋棋子(例如:┌ └ ├等)。 4.3 勝負(fù)判斷模塊 1. 在勝負(fù)判斷中一直沒能想到好的辦
15、法來(lái)數(shù)據(jù)化判斷哪方玩家獲得勝利。 解決方案:通過參考書籍并加以優(yōu)化,得出將棋譜做成數(shù)組,定義甲方落下為1,乙方落下為2,初始為0,這樣即不會(huì)造成沖突,也很好的解決了判斷問題。 2. 另一個(gè)問題在于一直不能優(yōu)化代碼做到不每次都掃描整個(gè)棋盤來(lái)判斷勝負(fù)。 解決方案:至今尚未解決,嘗試過局部掃描,但失敗了。 第5章:用戶手冊(cè) 1.進(jìn)入演示程序后,即顯示歡迎界面,幾秒后,按任何鍵進(jìn)入菜單界面,再選擇人人對(duì)戰(zhàn)可以進(jìn)入主界面開始游戲或者選擇退出鍵。 2.棋子的移動(dòng)與落子有鍵盤上按鍵控制,本程序選取甲乙方都為↑、↓、←、→和回車鍵,分別代表上移、下移、左移、右移光標(biāo)和落子。在光標(biāo)移動(dòng)的過程中,光標(biāo)
16、按照玩家按鍵移動(dòng);在玩家按下落子按鍵后,程序自動(dòng)調(diào)用棋子顯示子程序和判斷勝負(fù)子程序。 3. 在當(dāng)前玩家按下落子按鍵后,程序自動(dòng)調(diào)用棋子顯示子程序和判斷勝負(fù)子程序。當(dāng)前玩家下棋后,另一位玩家下棋前,當(dāng)前玩家可以悔棋?;谄逄崾驹谄灞P右下方,為按鍵“b”(即bamatlabkspamatlabe)。 4.游戲中Esmatlab鍵可以直接退出游戲。 5.游戲過程中,如果玩家1或者玩家2有一方獲得勝利后,程序自動(dòng)將提示哪一方獲得了勝利,并可以選擇是否繼續(xù)新游戲。 6.游戲結(jié)束且玩家選擇不再繼續(xù)后,顯示謝謝使用界面,再按任意鍵退出游戲。 第6章:小組分工 組長(zhǎng):謝艷濤 組員:黃元福,辛安
17、具體分工: 組員 任務(wù)分工 謝艷濤 報(bào)告書寫 程序調(diào)試 展示成果 黃元福 勝負(fù)判斷設(shè)計(jì) 主函數(shù)設(shè)計(jì) 辛安 界面制作 程序調(diào)試 第7章:結(jié)論與心得 通過對(duì)各子程序的設(shè)計(jì)與優(yōu)化,本程序完成了湊五子棋軟件的主體的設(shè)計(jì)與制作,基本達(dá)到了使用湊五子棋軟件的核心要求。然而程序還有一些不足之處,首先,程序的界面過于簡(jiǎn)陋,其次,判斷勝后沒有顯示連成一線的棋子是哪些,用戶使用不便。最后就是程序法實(shí)現(xiàn)人機(jī)對(duì)戰(zhàn),缺乏可玩性。 第8章 :源程序代碼 //湊五子棋小游戲 function [ ]
18、 = five() global a h m1 n1 m2 n2 t h1 h2 h3 color score hsc ha ss hf=figure(resize,off,name,five,... position,[360 280 560 420],numbertitle,off); ha=axes; set(gcf,menubar,none,color,[0.3 0.3 0.3]) set(gca,position,[0.2300 0.1100 0.7750 0.8150]) set(gca,xlim,[0,9],ylim,[0,9]
19、) set(ha,xtick,[],ytick,[],box,on) set(ha,color,[0.7 0.6,0.6]) set(ha,DataAspectRatio,[1 1 1],PlotBoxAspectRatio,[1 1 1]) x=repmat([0;9],1,9); y=[1:9;1:9]; line(x,y,color,k) line(y,x,color,k) hst=uicontrol(style,text,string,Score,fontsize,30,... units,normal,position,[0.02,0.55,0.26,0.1
20、4],parent,hf,... ForegroundColor,w,backgroundcolor,[0.3 0.3 0.3],... fontweight,bold); hsc=uicontrol(style,text,string,0,fontsize,24,... units,normal,position,[0.02,0.4,0.26,0.14],parent,hf,... ForegroundColor,w,backgroundcolor,[0.3 0.3 0.3],... fontweight,bold); hbt=uicon
21、trol(style,pushbutton,string,Restart,fontsize,18,... units,normal,position,[0.02,0.16,0.26,0.14],parent,hf,... fontweight,bold,callback,@restart); color=[... 1 1 0; 1 0 1; 0 1 1; 1 0 0; 0 1 0; 0 0 1; 0.7 0.3 0; ]; h1=annotation(ellipse,[0.04,0.84,0
22、.06,0.08],facecolor,k); h2=annotation(ellipse,[0.12,0.84,0.06,0.08],facecolor,k); h3=annotation(ellipse,[0.2,0.84,0.06,0.08],facecolor,k); set(ha,buttondownfcn,@select2) initialize function initialize() global a h m1 n1 m2 n2 t h1 h2 h3 color score hsc ss a=zeros(9); h=zeros(9)*NaN; m1=[];
23、 n1=[]; m2=[]; n2=[]; score=0; ss=0; k=rs(1:81,5); t=ceil(rand(1,5)*7); a(k)=t; [m,n] = ind2sub([9,9],k); y=9.5-m; x=n-0.5; for p=1:5 h(k(p))=line(x(p),y(p),marker,o,markersize,24,... markerfacecolor,color(t(p),:),markeredgecolor,none,... buttondownfcn,@select1); e
24、nd t=ceil(rand(1,3)*7); set(h1,facecolor,color(t(1),:)) set(h2,facecolor,color(t(2),:)) set(h3,facecolor,color(t(3),:)) function [k]=rs(s,n); for m=1:n t=ceil(rand*length(s)); k(m)=s(t); s(t)=[]; end function select1(src,eventdata) global a h m1 n1 n1=ceil(get(src,xdata));
25、m1=ceil(9-get(src,ydata)); set(h(~isnan(h)),markeredgecolor,none) set(src,markeredgecolor,w) function select2(src,eventdata) global a h m1 n1 m2 n2 t h1 h2 h3 color score hsc ha ss if isempty(m1) || isempty(n1) return end cp=get(src,currentpoint); n2=ceil(cp(1,1)); m2=ceil(9-cp(1,2));
26、 if a(m2,n2) return end b=~a; b(m1,n1)=1; b=bwlabel(b,4); if b(m1,n1)~=b(m2,n2) return end a(m2,n2)=a(m1,n1); a(m1,n1)=0; h(m2,n2)=h(m1,n1); h(m1,n1)=NaN; set(h(m2,n2),xdata,n2-0.5,ydata,9.5-m2,markeredgecolor,none) m1=[]; n1=[]; judgement; if sum(sum(~a))<3 hgo=text(1,
27、4.5,Game Over,fontsize,36,fontweight,... bold,parent,src); pause(3) delete(hgo); delete(h(~isnan(h))) set(hsc,string,0) initialize; return end if ~ss new; end function judgement global a h m1 n1 m2 n2 t h1 h2 h3 color score hsc ha ss b=logical(zeros(
28、9,9)); ss=0; left=0; right=0; up=0; down=0; lu=0; rd=0; ld=0; ru=0; while n2-left-1>0 && a(m2,n2-left-1)==a(m2,n2) left=left+1; end while n2+right+1<10 && a(m2,n2+right+1)==a(m2,n2) right=right+1; end while m2-up-1>0 && a(m2-up-1,n2)==a(m2,n2) up=up+1; end while m2+dow
29、n+1<10 && a(m2+down+1,n2)==a(m2,n2) down=down+1; end while n2-lu-1>0 && m2-lu-1>0 && a(m2-lu-1,n2-lu-1)==a(m2,n2) lu=lu+1; end while n2+rd+1<10 && m2+rd+1<10 && a(m2+rd+1,n2+rd+1)==a(m2,n2) rd=rd+1; end while n2-ld-1>0 && m2+ld+1<10 && a(m2+ld+1,n2-ld-1)==a(m2,n2) ld=ld+1;
30、 end while n2+ru+1<10 && m2-ru-1>0 && a(m2-ru-1,n2+ru+1)==a(m2,n2) ru=ru+1; end if left+right+1>=5 b(m2,n2-left:n2+right)=1; end if up+down+1>=5 b(m2-up:m2+down,n2)=1; end if lu+rd+1>=5 ind=sub2ind([9,9],m2-lu:m2+rd,n2-lu:n2+rd); b(ind)=1; end if ld+ru+1>=5 ind
31、=sub2ind([9,9],m2+ld:-1:m2-ru,n2-ld:n2+ru); b(ind)=1; end if sum(sum(b)) a(b)=0; delete(h(b)); h(b)=NaN; score=score+sum(sum(b)); set(hsc,string,num2str(score)) ss=1; end function new global a h m1 n1 m2 n2 t h1 h2 h3 color score hsc ha k=rs(find(~a),3); a(k
32、)=t; [mt,nt] = ind2sub([9,9],k); y=9.5-mt; x=nt-0.5; for p=1:3 h(k(p))=line(x(p),y(p),marker,o,markersize,24,... markerfacecolor,color(t(p),:),markeredgecolor,none,... buttondownfcn,@select1); end for p=1:3 m2=mt(p); n2=nt(p); judgement; end if sum(sum(~
33、a))==0 hgo=text(1,4.5,Game Over,fontsize,36,fontweight,... bold,parent,ha); pause(3) delete(hgo); delete(h(~isnan(h))) set(hsc,string,0) initialize; return end t=ceil(rand(1,3)*7); set(h1,facecolor,color(t(1),:)) set(h2,facecolor,color(t(2),:)) set(h3,facecolor,color(t(3),:)) function restart(src,eventdata) global a h m1 n1 m2 n2 t h1 h2 h3 color score hsc ha ss delete(h(~isnan(h))) set(hsc,string,0) initialize;
- 溫馨提示:
1: 本站所有資源如無(wú)特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請(qǐng)下載最新的WinRAR軟件解壓。
2: 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請(qǐng)聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
3.本站RAR壓縮包中若帶圖紙,網(wǎng)頁(yè)內(nèi)容里面會(huì)有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
5. 裝配圖網(wǎng)僅提供信息存儲(chǔ)空間,僅對(duì)用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對(duì)用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對(duì)任何下載內(nèi)容負(fù)責(zé)。
6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請(qǐng)與我們聯(lián)系,我們立即糾正。
7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時(shí)也不承擔(dān)用戶因使用這些下載資源對(duì)自己和他人造成任何形式的傷害或損失。
最新文檔
- 建筑施工重大危險(xiǎn)源安全管理制度
- 安全培訓(xùn)資料:典型建筑火災(zāi)的防治基本原則與救援技術(shù)
- 企業(yè)雙重預(yù)防體系應(yīng)知應(yīng)會(huì)知識(shí)問答
- 8 各種煤礦安全考試試題
- 9 危險(xiǎn)化學(xué)品經(jīng)營(yíng)單位安全生產(chǎn)管理人員模擬考試題庫(kù)試卷附答案
- 加壓過濾機(jī)司機(jī)技術(shù)操作規(guī)程
- 樹脂砂混砂工藝知識(shí)總結(jié)
- XXXXX現(xiàn)場(chǎng)安全應(yīng)急處置預(yù)案
- 某公司消防安全檢查制度總結(jié)
- 1 煤礦安全檢查工(中級(jí))職業(yè)技能理論知識(shí)考核試題含答案
- 4.燃?xì)獍踩a(chǎn)企業(yè)主要負(fù)責(zé)人模擬考試題庫(kù)試卷含答案
- 工段(班組)級(jí)安全檢查表
- D 氯化工藝作業(yè)模擬考試題庫(kù)試卷含答案-4
- 建筑起重司索信號(hào)工安全操作要點(diǎn)
- 實(shí)驗(yàn)室計(jì)量常見的30個(gè)問問答題含解析