110 高普考高考三級 資訊處理 資料結構 考古題詳解

110 年・高普考・高考三級・資訊處理
試題代碼 資料結構

第 一 題25 分

AA 為 8×48\times4 矩陣、BB 為 4×104\times10 矩陣、CC 為 10×310\times3 矩陣、DD 為 3×203\times20 矩陣、EE 為 20×420\times4 矩陣。

(一) 請列出此 5 個矩陣相乘 A×B×C×D×EA\times B\times C\times D\times E 所有可能的乘法順序(請用括號表示乘法順序)。(5 分)

(二) 請使用 Dynamic Programming(動態規劃)的技巧,計算出此五個矩陣相乘 A×B×C×D×EA\times B\times C\times D\times E 的最佳乘法順序(請用括號表示乘法順序),使得五個矩陣相乘所需要花費的乘法數量最少。(15 分)

(三) 請列出此五個矩陣相乘所需要花費的最少乘法數量。(5 分)

注意:未說明 Dynamic Programming 的計算過程,不予計分。

登入後即可作答並保存紀錄。

這一題的完整詳解

核心觀念

本題考「矩陣鏈乘法」(Matrix-Chain Multiplication)。矩陣乘法具有結合律,因此 A×B×C×D×EA\times B\times C\times D\times E 可以有多種加括號方式;只要不改變矩陣的先後順序,乘積結果相同,但所需的純量乘法次數可能不同。

若矩陣 MiM_i 的大小為 pi−1×pip_{i-1}\times p_i,則相乘 Mi⋯MjM_i\cdots M_j 時,令 m[i,j]m[i,j] 表示所需的最少純量乘法次數,可用下列動態規劃遞迴式計算:

m[i,i]=0m[i,i]=0 m[i,j]=min⁡i≤k<j{m[i,k]+m[k+1,j]+pi−1pkpj}m[i,j]=\min_{i\le k<j} \left\{ m[i,k]+m[k+1,j]+p_{i-1}p_kp_j \right\}

其中 kk 表示最後一次乘法的切割位置;pi−1pkpjp_{i-1}p_kp_j 是將左側結果與右側結果相乘的成本。

本題的維度序列為:

(p0,p1,p2,p3,p4,p5)=(8,4,10,3,20,4)(p_0,p_1,p_2,p_3,p_4,p_5)=(8,4,10,3,20,4)

解題方法

由只有一個矩陣的子鏈開始,依序計算長度為 2、3、4、5 的子鏈。每一格都列出不同切割位置的成本,再取最小值;最後依各子鏈的最佳切割位置還原括號順序。

(一)所有可能的乘法順序

五個矩陣保持原順序,加括號方式共有 1414 種:

  1. ((((AB)C)D)E)((((AB)C)D)E)
  2. (((A(BC))D)E)(((A(BC))D)E)
  3. (((AB)(CD))E)(((AB)(CD))E)
  4. ((A((BC)D))E)((A((BC)D))E)
  5. ((A(B(CD)))E)((A(B(CD)))E)
  6. (((AB)C)(DE))(((AB)C)(DE))
  7. ((A(BC))(DE))((A(BC))(DE))
  8. ((AB)((CD)E))((AB)((CD)E))
  9. ((AB)(C(DE)))((AB)(C(DE)))
  10. (A(((BC)D)E))(A(((BC)D)E))
  11. (A((B(CD))E))(A((B(CD))E))
  12. (A((BC)(DE))(A((BC)(DE)))
  13. (A(B((CD)E)))(A(B((CD)E)))
  14. (A(B(C(DE))))(A(B(C(DE))))

以上共 1414 種,亦即五個矩陣的加括號方式數量為 Catalan 數 C4=14C_4=14。

(二)動態規劃計算最佳乘法順序

子鏈長度為 2:

m[1,2]=8⋅4⋅10=320m[2,3]=4⋅10⋅3=120m[3,4]=10⋅3⋅20=600m[4,5]=3⋅20⋅4=240\begin{aligned} m[1,2]&=8\cdot4\cdot10=320\\ m[2,3]&=4\cdot10\cdot3=120\\ m[3,4]&=10\cdot3\cdot20=600\\ m[4,5]&=3\cdot20\cdot4=240 \end{aligned}

子鏈長度為 3:

m[1,3]=min⁡{0+120+8⋅4⋅3, 320+0+8⋅10⋅3}=min⁡{216,560}=216\begin{aligned} m[1,3] &=\min\{0+120+8\cdot4\cdot3,\ 320+0+8\cdot10\cdot3\}\\ &=\min\{216,560\}=216 \end{aligned}

最佳順序為 A(BC)A(BC)。

🔒

後續完整解題步驟與【答案】

免費註冊,享 3 天全站完整詳解閱覽。

免費註冊

第 二 題25 分

假設收銀機內銅板的集合為 S={50,20,20,15,10,2,1,1,1}S=\{50,20,20,15,10,2,1,1,1\},而預計找錢給顧客的金額為 W=75W=75。

(一) 請設計一個 Greedy(貪婪)的演算法,來解決找錢給顧客的問題,使得找給顧客金額 WW 所使用的銅板數量最少,並依此 Greedy 演算法列出找給顧客金額 W=75W=75 的過程。(15 分)

(二) 此 Greedy 演算法適合使用何種資料結構來完成。(5 分)

(三) 此 Greedy 演算法的解法是否能保證為最佳解?請舉例說明。(5 分)

登入後即可作答並保存紀錄。

這一題的完整詳解

核心觀念

本題考查硬幣找零的 Greedy(貪婪)策略:每一步都從尚未使用的硬幣中,選擇面額不大於剩餘金額的最大硬幣,直到找足 WW。硬幣面額若有重複,仍視為不同枚硬幣,使用後就移除。

貪婪策略每一步都做局部最佳選擇;但局部最佳不一定能導致硬幣總數最少,因此是否得到最佳解,須視硬幣面額組合而定。

解題方法與找零過程

將硬幣按面額由大到小排列,每次取不超過剩餘金額的最大面額。題目中硬幣為 50,20,20,15,10,2,1,1,150,20,20,15,10,2,1,1,1,找零金額 W=75W=75。

  1. 剩餘 7575:取 5050,剩餘 75−50=2575-50=25。
  2. 剩餘 2525:取一枚 2020,剩餘 25−20=525-20=5。
  3. 剩餘 55:15、10、215、10、2 都不超過 55 的最大面額為 22,取兩枚 22,剩餘 5−2−2=15-2-2=1。
  4. 剩餘 11:取一枚 11,剩餘 00。

因此 Greedy 找零為:

50+20+2+2+1=7550+20+2+2+1=75

共使用 55 枚硬幣。

Greedy-Change(S, W):
 將 S 依面額由大到小排序
 result ← 空集合
 remaining ← W

 依序檢查每一枚硬幣 c:
 當 c ≤ remaining:
 將 c 加入 result
 remaining ← remaining - c
 若 remaining = 0:
 回傳 result

 若 remaining > 0:
 回報無法找足金額

適用的資料結構

🔒

後續完整解題步驟與【答案】

免費註冊,享 3 天全站完整詳解閱覽。

免費註冊

第 三 題25 分

二元搜尋法(binary search)使用 divide-and-conquer(分而治之)演算法技巧,對一個已排序的(sorted)且長度為 nn 的陣列 A[0:n−1]A[0:n-1],以二元化方式進行資料值 xx 的搜尋,其最差時間複雜度(worst case time complexity)可降到 Θ(log⁡n)\Theta(\log n)。

(一) 請使用 C++ 或 Python 語言,修改此二元搜尋法,使其能對未排序的(unsorted)且長度為 nn 的陣列 A[0:n−1]A[0:n-1],進行三元化搜尋,即以 divide-and-conquer 技巧將此陣列切成三個子陣列,並在可能包含資料值 xx 的子陣列繼續進行 divide-and-conquer 技巧的搜尋;如果找到則回傳 1,如果找不到則回傳 0。(17 分)

注意:請寫一個 searching 類別,內含一個 search 功能。

(二) 請分析修改後的三元化搜尋法其最差時間複雜度(worst case time complexity),以 order 的方式表示。(8 分)

注意:不可將此陣列數值進行排序,請加註解說明程式碼作法。

登入後即可作答並保存紀錄。

這一題的完整詳解

核心觀念

二元搜尋法能排除一半搜尋範圍,依賴陣列已排序:比較中間值後,才能判定目標在左半或右半。題目要求陣列維持未排序,因此不能只靠索引位置排除區段。

改以三個子陣列分治時,必須遞迴搜尋三個子陣列,因為任何一個都可能包含 xx。三分法在此不會減少總搜尋工作量,只改變每次遞迴的切分方式。

解題方法

使用半開區間 [L,R)[L,R) 表示目前搜尋範圍,長度為 R−LR-L。將區間切成三段:

[L,M1),[M1,M2),[M2,R)[L,M_1),\quad [M_1,M_2),\quad [M_2,R)

其中 M1=L+⌊(R−L)/3⌋M_1=L+\lfloor(R-L)/3\rfloor,M2=L+⌊2(R−L)/3⌋M_2=L+\lfloor2(R-L)/3\rfloor。程式先檢查目前區間的元素是否等於 xx;若否,便遞迴搜尋三段。當區間為空時,表示沒有找到。

程式碼

🔒

後續完整解題步驟與【答案】

免費註冊,享 3 天全站完整詳解閱覽。

免費註冊

第 四 題25 分

(一) 請使用 C 語言寫一副程式:

void FindMeanAverage(int A[], int n, int *mean, int *average)\texttt{void FindMeanAverage(int A[], int n, int *mean, int *average)}

對一個未排序的(unsorted)且長度為 nn 的陣列 A[0:n−1]A[0:n-1],尋找陣列中的中位數與平均數,並分別存入 meanmean 及 averageaverage,分析其運算複雜度。(17 分)

(二) 請舉例說明此副程式最差情況(worst case)所花費的運算複雜度。(8 分)

注意:請加註解說明程式碼作法。

登入後即可作答並保存紀錄。

這一題的完整詳解

核心觀念

本題考查中位數、算術平均數的定義,以及未排序陣列的選取(selection)與時間複雜度分析。

  • 中位數:將數值依大小排序後,位於中央的數值。若 nn 為奇數,取第 (n+1)/2(n+1)/2 小的數;若 nn 為偶數,取第 n/2n/2 小與第 (n/2+1)(n/2+1) 小兩數的平均。
  • 算術平均數:所有元素總和除以元素個數,即 1n∑i=0n−1A[i]\frac{1}{n}\sum_{i=0}^{n-1}A[i]。
  • 選取(selection):在未排序資料中,找出第 kk 小的元素。若採用最差時間為 O(n)O(n) 的選取演算法,中位數可在線性時間內求得;若先排序再取中間元素,則需要 O(nlog⁡n)O(n\log n)。

題目指定 int *mean 與 int *average,以下依常見考題假設,將中位數及平均數以整數回傳;偶數筆資料的中位數與平均數採整數除法,會捨去小數部分。

解題方法

先複製陣列,避免尋找中位數時改動呼叫端的原始資料。對複本使用 median-of-medians(中位數的中位數) 選取演算法,取得所需順位的元素;其最差時間複雜度為 O(n)O(n)。

  • 若 nn 為奇數,選出第 (n+1)/2(n+1)/2 小的元素。
  • 若 nn 為偶數,分別選出第 n/2n/2 小與第 (n/2+1)(n/2+1) 小的元素,取其整數平均。

平均數則以一次走訪累加所有元素,最後除以 nn。總時間仍為 O(n)O(n),空間需求為 O(n)O(n),主要用於保存選取演算法所操作的複本。

🔒

後續完整解題步驟與【答案】

免費註冊,享 3 天全站完整詳解閱覽。

免費註冊

其他考古題