有30個同學圍成一個圈,從1開始報數,報到3的同學退出圓圈,請問最後剩下的是哪個同學?並輸出所有出圈同學的順序。這是經典的約瑟夫環問題,也是C語言學習中常見的算法練習。
使用數組模擬圓圈,通過標記已退出的同學(設置為0),利用計數器實現報數邏輯。當計數器達到指定數字(此處為3)時,將對應位置標記為0,並重置計數器,繼續下一輪報數,直到只剩下一位同學。
int main(void)
{
// 圍圈報數
int a[100] = {0};
int m, n, t = 0;
int i, j, k = 0;
scanf("%d%d", &m, &n);
for (i = 1; i <= m; i++) {
a[i-1] = i;
}
// 每人附上序號
while (t < m - 1) {
for (j = 0; j < m; j++) {
if (a[j] != 0) {
k++;
if (k == n) {
a[j] = 0;
t++;
k = 0;
}
}
}
}
for (i = 0; i < m; i++) {
if (a[i] != 0) {
printf("%d\n", a[i]);
}
}
return 0;
}
該算法時間複雜度為O(m×n),對於小規模數據完全足夠。若需處理大規模數據,可考慮使用鏈表或數學遞推公式優化至O(m)或O(log m)。