一羣猴子要選新猴王。新猴王的選擇方法是:讓N只候選猴子圍成一圈,從某位置起順序編號爲1~N號。從第1號開始報數,每輪從1報到3,凡報到3的猴子即退出圈子,接着又從緊鄰的下一隻猴子開始同樣的報數。如此不斷循環,最後剩下的一隻猴子就選爲猴王。請問是原來第幾號猴子當選猴王?
輸入格式:
輸入在一行中給一個正整數N(≤1000)。
輸出格式:
在一行中輸出當選猴王的編號。
輸入樣例:
11
輸出樣例:
7
題目思路:基本鏈表入門用法,數到3時刪除鏈表節點並進行指針操作。
代碼:
#include<stdio.h>
#include<stdlib.h>
//定義猴子鏈表,內涵元素有數字和下一節點地址
struct monkey
{
int num;
struct monkey* NextMonkey;
};
typedef struct monkey Monkey;
typedef Monkey* NextMonkey;
int main()
{
int n, i;
NextMonkey headPtr, prePtr, currentPtr;
//讀入n
scanf("%d", &n);
//鏈表初始化操作
currentPtr = (NextMonkey)malloc(sizeof(Monkey));
currentPtr->NextMonkey = NULL;
headPtr = currentPtr;
prePtr = currentPtr;
//鏈表賦值,將鏈表初始化
for (i = 0; i < n; i++)
{
currentPtr = (NextMonkey)malloc(sizeof(Monkey));
currentPtr->NextMonkey = NULL;
currentPtr->num = i;
prePtr->NextMonkey = currentPtr;
prePtr = currentPtr;
}
//初始化後,將單向鏈表轉換爲單向循環鏈表
//即將最後一個節點的下一節點地址指向第一節點
currentPtr->NextMonkey = headPtr->NextMonkey;
prePtr = currentPtr;
currentPtr = prePtr->NextMonkey;
//下循環爲核心算法,數到3時淘汰現有猴子
//循環結束條件:現節點的數據與現節點下一節點的數據相同
//也就是說,鏈表只剩下一個節點
while (currentPtr->num != currentPtr->NextMonkey->num)
{
for (i = 0; i < 2; i++)
{
prePtr = prePtr->NextMonkey;
currentPtr = currentPtr->NextMonkey;
}
//前一節點的下一節點地址指向現節點的下一節點
prePtr->NextMonkey = currentPtr->NextMonkey;
//同時釋放空間
free(currentPtr);
//將現節點位置初始化
currentPtr = prePtr->NextMonkey;
}
printf("%d", currentPtr->num+1);
free(currentPtr);
return 0;
}