阿摩線上測驗 登入

申論題資訊

試卷:105年 - 105 地方政府特種考試_三等_資訊處理:程式語言#58715
科目:程式語言
年份:105年
排序:0

題組內容

七、請回答下列問題: (每小題 5 分,共 10 分)

申論題內容

⑴給定一個整數陣列 S[n],請寫出一個副程式 int SelectionK(int *S, int n),此函數可 以回傳(return)第 K 大的數值。

詳解 (共 1 筆)

詳解 提供者:hchungw

#include <iostream> #include <algorithm> // 引入 std::swap

int partition(int* S, int left, int right, int pivotIndex) { int pivotValue = S[pivotIndex]; std::swap(S[pivotIndex], S[right]); // 將 pivot 移動到結尾 int storeIndex = left;

for (int i = left; i < right; i++) { if (S[i] > pivotValue) { // 這裡是大於號,因為我們要找第 K 大的數 std::swap(S[i], S[storeIndex]); storeIndex++; } }

std::swap(S[storeIndex], S[right]); // 將 pivot 移動到它的最終位置 return storeIndex; }

int quickselect(int* S, int left, int right, int K) { if (left == right) { // 只有一個元素時 return S[left]; }

// 選擇 pivot 索引 int pivotIndex = left + (right - left) / 2;

pivotIndex = partition(S, left, right, pivotIndex);

if (K == pivotIndex) { return S[K]; } else if (K < pivotIndex) { return quickselect(S, left, pivotIndex - 1, K); } else { return quickselect(S, pivotIndex + 1, right, K); } }

int SelectionK(int* S, int n, int K) { return quickselect(S, 0, n - 1, K - 1); }

int main() { int S[] = {3, 2, 1, 5, 6, 4}; int n = sizeof(S) / sizeof(S[0]); int K = 2; // 我們想找到第 2 大的數值

std::cout << "第 " << K << " 大的數值是 " << SelectionK(S, n, K) << std::endl; return 0; }

主要步驟說明:

  1. Partition 函數

    • 將陣列分區,使得 pivot 值左邊的元素都大於 pivot 值,右邊的元素都小於或等於 pivot 值。
  2. Quickselect 函數

    • 選擇一個 pivot,使用 Partition 函數進行分區。
    • 判斷 pivot 的位置是否就是第 K 大的數。
    • 如果是,則返回該數;否則,根據 pivot 的位置遞歸地在相應的子陣列中查找第 K 大的數。
  3. SelectionK 函數

    • 調用 Quickselect 函數,找到第 K 大的數。

這個算法高效地找到了第 K 大的數,並且通過遞歸方式逐步縮小查找範圍,使得平均時間複雜度為 O(n)O(n)O(n)