• 圆圈中最后剩下的数字 【微软面试100题 第十八题】


    题目要求:

      0,1,...,n-1这n个数排成一个圆圈,从数字0开始每次从这个圆圈里删除第m个数字。求出这个圆圈里剩下的最后一个数字。

      例如,0、1、2、3、4这5个数字组成一个圆圈,从数字0开始每次删词第3个数字,则删除的前四个数字一次是2、0、4、1,因此最后剩下的数字是3.

      参考资料:剑指offer第45题

    题目分析:

      方法1:用环形链表模拟圆圈,链表可以用c++的STL库中的list来表示,删除链表其中一个结点之后,链表还是连续的。

      方法2:定义f(n,m),表示每次在n个数字0,1,...,n-1中每次删除第m个数字最后剩下的数字。

        先给出关系公式:

        

        可以这样理解:从序列f(n):0~n-1中删除第m个数后,剩下为序列m,m+1,..,n-1,0,1,...,m-2,即序列f(n-1)+m.因此f(n,m) = [f(n-1,m)+m]%n,是采用的映射关系来递推的。

    代码实现:

    #include <iostream>
    #include <list>
    
    using namespace std;
    
    int LastRemaining(unsigned int n,unsigned int m);
    int LastRemaining2(unsigned int n,unsigned int m);
    int main(void)
    {
        //cout << LastRemaining(5,3) << endl;
        cout << LastRemaining2(5,3) << endl;
        return 0;
    }
    //方法1
    int LastRemaining(unsigned int n,unsigned int m)
    {
        if(n<1 || m<1)
            return -1;
    
        unsigned int i = 0;
        list<int> nums;
        for(i= 0;i<n;i++)
            nums.push_back(i);
        list<int>::iterator cur = nums.begin();
        while(nums.size()>1)
        {
            for(int i = 1;i<m;i++)
            {
                cur++;
                if(cur==nums.end())
                    cur = nums.begin();
            }
            list<int>::iterator next = ++cur;
            if(next == nums.end())
                next = nums.begin();
    
            --cur;
            nums.erase(cur);
            cur = next;
        }
        return *cur;    
    }
    //方法2
    int LastRemaining2(unsigned int n,unsigned int m)
    {
        if(n<1 || m<1)
            return -1;
        int last = 0;
        for(int i = 2;i<=n;i++)
            last = (last+m)%i;
    
        return last;
    }
    View Code
  • 相关阅读:
    sql server 中替换字符串
    查询sql server数据库中字段内容长度的方法
    解决 Iis7.5 中的“ISAPI 和 CGI 限制”错误
    C# MVC3 中实现网银在线支付功能心得
    正则表达式验证数字和小数
    使用arttemplate js模板引擎,直接用模板渲染,减少字符串拼接。
    复选框判断全选与否以及选中删除
    内存泄漏问题
    用js闭包,在ul 里点击 li,输出对应的下标
    css 文字竖直排列
  • 原文地址:https://www.cnblogs.com/tractorman/p/4057624.html
Copyright © 2020-2023  润新知