Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -0,0 +1,86 @@
# AI_LOG - 二分搜尋效能 (Binary Search Efficiency)

## 指令 1:修復中文字體顯示問題

### 我問 AI 什麼

> 「matplotlib 生成的雷達圖中文文字顯示為方格,怎麼修復?」

### AI 給了什麼

> 給了 matplotlib 字體設置方案:設定 `plt.rcParams['font.sans-serif']` 優先使用中文字體(SimHei、Microsoft YaHei)。

### 我改了什麼

**判斷過程:**
1. 確認問題根源是 matplotlib 預設字體(DejaVu Sans)無法顯示中文
2. AI 提示需要在匯入後立即設置字體配置
3. 在 `solution.py` 開頭加入字體設置代碼:
```python
plt.rcParams['font.sans-serif'] = ['SimHei', 'Microsoft YaHei', 'DejaVu Sans']
plt.rcParams['axes.unicode_minus'] = False
```

**執行結果:** ✓ 中文文字正常顯示,不再出現方格。

---

## 指令 2:修改雷達圖維度

### 我問 AI 什麼

> 「維度能換一些嗎」

### AI 給了什麼

> 提供了 3 個可選方案:
> 1. 比較次數、執行時間、縮放性能、最壞情況
> 2. 時間複雜度、空間複雜度、穩定性、實作難度
> 3. 執行時間、平均性能、最壞性能、緩存效率

### 我改了什麼

**判斷過程:**
1. 選擇第 3 方案:「執行時間、平均性能、最壞性能、緩存效率」
- 更貼近實際效能評估
- 包含「平均」與「最壞」對比,展示算法的完整性能特性

2. 修改 `plot_radar_chart()` 函數中的維度計算:
- **執行時間**:實際 timeit 量測結果
- **平均性能**:線性搜尋 100 次 vs 二分搜尋 7 次比較
- **最壞性能**:線性最壞 100 次 vs 二分最壞 log₂(100) ≈ 7 次
- **緩存效率**:
- 線性搜尋 0.3(順序存取但頻繁跳躍)
- 二分搜尋 0.9(二分邏輯更好的快取局部性)

3. 更新分數計算邏輯:
```python
linear_worst = arr_size # 線性最壞情況:全部比較
binary_worst = int(np.log2(arr_size)) + 1 # 二分最壞情況:log n
```

**執行結果:** ✓ 雷達圖成功更新,新維度更準確反映演算法性能差異。

---

## 測試驗證

**數據對比(目標 K=138,陣列大小 100):**

| 指標 | 線性搜尋 | 二分搜尋 |
|---|---|---|
| 比較次數 | 100 | 7 |
| 執行時間 | 0.000003 s | 0.000001 s |
| 最壞情況 | 100 | 7 |
| 結果 | NOT FOUND | NOT FOUND |

✓ 所有 4 個測試案例都通過(4/4 green)

---

## 完成狀態

- ✅ 中文字體問題修復
- ✅ 雷達圖維度優化
- ✅ 代碼文檔完成
- ✅ AI_LOG 記錄完整
Original file line number Diff line number Diff line change
@@ -0,0 +1,206 @@
# 題目分析:二分搜尋效能(Binary Search Efficiency)- 第四題

## 📋 題目概述
- **分值**:20分
- **難度**:C題(進階)
- **相關資源**:week-17/in_class/0618-search-lab.md、0618-search-eval.md、0617-starter/
- **技術重點**:線性搜尋、二分搜尋、比較次數統計、timeit 效能比較、雷達圖視覺化

---

## 🎯 題目敘述

### 題目描述
本題要比較「線性搜尋」與「二分搜尋」在同一組已排序整數陣列上的效能差異。你需要產生資料、執行兩種搜尋方式、統計比較次數,並用 `timeit` 比較兩者執行時間,最後再畫出雷達圖來整理結果。

### 核心任務
對指定目標值 `K = 138`,依序完成:
1. **產生資料** - 建立一個升冪排序的整數陣列
2. **執行搜尋** - 分別使用線性搜尋與二分搜尋尋找 `K`
3. **統計比較次數** - 輸出搜尋結果與比較次數
4. **效能比較** - 用 `timeit` 比較兩種方法誰較快
5. **視覺化結果** - 畫出雷達圖比較不同維度

---

## 📥 輸入說明

```
m
m 個升冪整數
```

- 第 1 行輸入整數 `m`
- 第 2 行輸入 `m` 個已排序的整數,代表資料陣列
- 題目會依據指定搜尋目標進行測試
- 本題示意使用的搜尋目標為 `K = 138`

---

## 📤 輸出說明

輸出格式包含三部分:
1. **搜尋結果**:`FOUND idx=... cmp=...` 或 `NOT FOUND cmp=...`
2. **timeit 結果**:線性搜尋與二分搜尋的執行時間
3. **結論**:指出哪一種方法較快

---

## 📊 範例說明(K = 138)

### Sample Input
```
10
12 37 58 80 95 101 138 160 188 210
```

### Sample Output
```
FOUND idx=6 cmp=7
FOUND idx=6 cmp=3
linear : 0.0123 s
binary : 0.0001 s
=> binary faster
```

### 詳細過程

#### 線性搜尋
資料從左到右逐一比較,直到找到 `138` 為止。

```
12 -> 比較 1 次
37 -> 比較 2 次
58 -> 比較 3 次
80 -> 比較 4 次
95 -> 比較 5 次
101 -> 比較 6 次
138 -> 比較 7 次,找到
```

**輸出**:`FOUND idx=6 cmp=7`

#### 二分搜尋
已排序陣列可用中間值逐步縮小範圍。

```
mid=4 -> 95
mid=7 -> 160
mid=6 -> 138,找到
```

**輸出**:`FOUND idx=6 cmp=3`

---

## 🔑 關鍵要點

1. **資料必須先排序** - 二分搜尋只適用於已排序資料
2. **比較次數要記錄** - 線性搜尋與二分搜尋都要統計 cmp
3. **結果格式固定** - 需明確輸出 FOUND / NOT FOUND 與 idx / cmp
4. **timeit 比較** - 需以相同條件比較兩種方法的執行時間
5. **雷達圖** - 用於整理不同維度的效能差異

---

## 💡 演算法策略

### 方案1:線性搜尋
```python
def linear_search(arr, target):
cmp = 0
for idx, value in enumerate(arr):
cmp += 1
if value == target:
return True, idx, cmp
return False, -1, cmp
```

### 方案2:二分搜尋
```python
def binary_search(arr, target):
left, right = 0, len(arr) - 1
cmp = 0
while left <= right:
mid = (left + right) // 2
cmp += 1
if arr[mid] == target:
return True, mid, cmp
elif arr[mid] < target:
left = mid + 1
else:
right = mid - 1
return False, -1, cmp
```

### 方案3:效能比較與視覺化
```python
import timeit
import matplotlib.pyplot as plt
```

- `timeit` 用來量測多次執行的平均時間
- `matplotlib` 用來畫雷達圖比較不同面向

---

## 📌 邊界情況(Edge Cases)

- **目標值在陣列最前面** - 線性搜尋最有利
- **目標值在陣列最後面** - 線性搜尋最不利
- **目標值不存在** - 需正確回傳 NOT FOUND
- **空陣列** - 不能直接進行二分搜尋
- **單一元素陣列** - 左右邊界最簡單情況
- **重複值** - 若陣列中有重複值,需明確處理找到哪一個位置
- **資料量大** - 大 `m` 時才容易看出線性與二分的差異

---

## 📚 相關資源參考

- `week-17/in_class/0618-search-lab.md` - 搜尋實作練習
- `0618-search-eval.md` - 評測說明
- `0617-starter/` - 起始檔案
- `0618 Stage 3~4` - 效能比較與視覺化

---

## ✅ 實作檢查清單

- [ ] 產生升冪排序整數陣列
- [ ] 實作線性搜尋
- [ ] 實作二分搜尋
- [ ] 統計比較次數 cmp
- [ ] 正確輸出 FOUND / NOT FOUND
- [ ] 使用 `timeit` 量測效能
- [ ] 比較兩種搜尋速度
- [ ] 繪製雷達圖
- [ ] 驗證 K = 138 的結果
- [ ] 確認輸出格式符合題意

---

## 📝 本題設定

**當前搜尋目標:K = 138**

若陣列為:
```
12 37 58 80 95 101 138 160 188 210
```
則:
- 線性搜尋:`FOUND idx=6 cmp=7`
- 二分搜尋:`FOUND idx=6 cmp=3`
- `binary faster`

---

## 📈 雷達圖可比較的維度

- 小 n 速度
- 大 n 速度
- 是否需要排序
- 實作簡易度
- 最壞情況比較次數

這些維度可用來說明為什麼二分搜尋在已排序資料與大資料量下通常更快。
Loading