题目
0, 1, …, n-1这n个数字(n>0)排成一个圆圈,从数字0开始每次从这个圆圈里删除第m个数字。
求出这个圆圈里剩下的最后一个数字。
样例
输入:n=5 , m=3
输出:3
解法一:模拟
c++中list容器用作双向链表
时间复杂度O(nm),空间复杂度O(n)
#include <list>class Solution {public:int lastRemaining(int n, int m){list<int> l;for (int i = 0; i < n; i++)l.push_back(i);int cnt = m - 1;auto it = l.begin();while (l.size() > 1) {while (cnt--) {it++;if (it == l.end()) it = l.begin();}it = l.erase(it);if (it == l.end()) it = l.begin();cnt = m - 1;}return l.front();}};
解法二:DP
dp(n, m) 表示n个人, m为号的最后结果
每次删除一个人后重新编号
那么 dp(n, m) = (dp(n - 1, m) + m) % n
因为此时0的位置是原来m的位置
时间复杂度O(n),空间复杂度O(1)
class Solution {public:int lastRemaining(int n, int m){int ans = 0;for (int i = 1; i <= n; i++) {ans += m;if (ans >= i) ans %= i;}return ans;}};// class Solution {// public:// int lastRemaining(int n, int m){// if (n == 0) return 0;// return (lastRemaining(n - 1, m) + m) % n;// }// };
