回 帖 发 新 帖 刷新版面

主题:[讨论]猴子分桃问题 (要求用队列方法)  急用!

[color=FF00FF][size=4]«问题描述:(要求用队列方法)
动物园里的n 只猴子编号为1,2,…,n,依次排成一队等待饲养员按规则分桃。动物
园的分桃规则是每只猴子可分得m 个桃子,但必须排队领取。饲养员循环地每次取出1 个,
2 个,…,k 个桃放入筐中,由排在队首的猴子领取。取到筐中的桃子数为k 后,又重新从
1 开始。当筐中桃子数加上队首猴子已取得的桃子数不超过m 时,队首的猴子可以全部取出
筐中桃子。取得桃子总数不足m 个的猴子,继续到队尾排队等候。当筐中桃子数加上队首猴
子已取得的桃子数超过m 时,队首的猴子只能取满m个,然后离开队列,筐中剩余的桃子由
下一只猴子取用。上述分桃过程一直进行到每只猴子都分到m 个桃子。
«实验任务:
对于给定的n,k和m,模拟上述猴子分桃过程。
«数据输入:
由文件input.txt 给出输入数据。第1 行中有3 个正整数n,k 和m,分别表示有n 只猴
子,每次最多取k个桃到筐中,每只猴子最终都分到m个桃子。
«结果输出:
将分桃过程中每只猴子离开队列的次序依次输出到文件output.txt。
输入文件示例 输出文件示例
input.txt    output.txt
5 3 4       1 3 5 2

回复列表 (共5个回复)

沙发

我们首先假设num(tag),每经过15轮所有的num就会相等,并且此时tag回到初始序列!
0(1) 0(2) 0(3) 0(4) 0(5) 
0(2) 0(3) 0(4) 0(5) 1(1) 
0(3) 0(4) 0(5) 1(1) 2(2) 
0(4) 0(5) 1(1) 2(2) 3(3) 
0(5) 1(1) 2(2) 3(3) 1(4) 
1(1) 2(2) 3(3) 1(4) 2(5) 
2(2) 3(3) 1(4) 2(5) 4(1) 
3(3) 1(4) 2(5) 4(1) 3(2) 
1(4) 2(5) 4(1) 3(2) 5(3) 
2(5) 4(1) 3(2) 5(3) 4(4) 
4(1) 3(2) 5(3) 4(4) 3(5) 
3(2) 5(3) 4(4) 3(5) 6(1) 
5(3) 4(4) 3(5) 6(1) 6(2) 
4(4) 3(5) 6(1) 6(2) 6(3) 
3(5) 6(1) 6(2) 6(3) 6(4) 
6(1) 6(2) 6(3) 6(4) 6(5) 
所以,如果以上的过程符合题意那么到num=36时,见再次出现相等的情况:
36(1) 36(2) 36(3) 36(4) 36(5) +1  r=0
36(2) 36(3) 36(4) 36(5) 37(1) +2  r=0
36(3) 36(4) 36(5) 37(1) 38(2) +3  r=0
36(4) 36(5) 37(1) 38(2) 39(3) +1  r=0
36(5) 37(1) 38(2) 39(3) 37(4) +2  r=0
37(1) 38(2) 39(3) 37(4) 38(5) +3  r=0
1 38(2) 39(3) 37(4) 38(5)     +1  r=0
  39(3) 37(4) 38(5) 39(2)     +2  r=0
3 37(4) 38(5) 39(2)           +3  r=1
4 38(5) 39(2)                 +1  r=1
5 39(2)                       +2  r=0
2

[quote]
input.txt    output.txt
5 3 40       1 3 5 2
[/quote]
所以我认为output.txt不正确

板凳


struct Monkey
{
    int peachesInHand;
    int MonkeyNo;
    Monkey(int p, int n) : peachesInHand(p), MonkeyNo(n) {}
    void increasePeach(int inc) { peachesInHand += inc; }
};
class Peach
{
public:
    Peach(int n, int k, int m) : nMonkey(n), round(k), sum(m) { assert(nMonkey != 0 && round != 0 && sum != 0); }
    queue<int> dividePeach();
private:
    int n, k, m;
};

Peach::dividePeach()
{
    int basket = 0;
    queue<int> result;
    queue<Monkey> Monkeys;
    for (int index = 1; index <= n; ++index)
        Monkeys.push(Monkey(0, index);
    while (!Monkeys.empty())
    {
        for (int i = 1; i <= round; ++i)
        {
            Monkey& front = Monkeys.front();
            front.inceasePeach(i + basket);
            basket = 0;
            if (front.peachesInHand >= sum)    //monkey leaves queue
            {
                basket = front.peachesInHand - sum;
                Monkeys.pop();
                result.push(front);
                if (Monkeys.empty())
                    break;
            }
            else    //go back to the end of queue
            {
                Monkeys.pop();
                Monkeys.push(front);
            }
        }
    }
    return result;
}

3 楼


呵呵,output确实错了,40应该为4,还有没有更好的C语言队列 的方法可以解这题啊

4 楼


#include"stdio.h"
#include"malloc.h"

void main()
{
    int n,k,m;
    int i,j;
    int sub=0,p=0,flag=0; 
    int *queue;
    freopen("input.txt", "r", stdin);
    freopen("output.txt", "w", stdout);
    scanf("%d %d %d",&n,&k,&m);
    queue=(int *)malloc(n*sizeof(int));
    for(i=0;i<n;i++)
        queue[i]=0;
     /*sub是用来存放多余的桃子。flag是用来控制循环用的。*/
    while(flag<n)
    {
        for(j=0;j<n;j++)
        {
            if(queue[j]>=m) /*这只猴子已经领满m个桃子。*/
                continue;
            else if((queue[j]+p%k+1<m)&&(sub==0))
            /*这只猴子还要继续领取他的桃子。*/
            {
                queue[j]=queue[j]+p%k+1;
                p++;
            }
            else if((sub==0)&&(queue[j]+p%k+1>=m))
            /*这只猴子刚领满m个桃子。*/
            {
                sub=queue[j]+(p%k)+1-m;
                queue[j]=m;
                p++;
                flag++;
                printf("%d ",j+1);
            }
            else if((sub+queue[j]<m)&&(sub!=0))
            /*这只猴子还要继续领取他的桃子。*/
            {
                queue[j]=queue[j]+sub;
                sub=0;
            }
            else if((queue[j]+sub>=m)&&(sub!=0))
            /*这只猴子刚领满m个桃子。*/
            {
                sub=sub+queue[j]-m;
                queue[j]=m;
                flag++;
                printf("%d ",j+1);
            }
        }
    }
}




5 楼

不会是一个系的人吧
这是作业啊~~~~~~~~~~~~

我来回复

您尚未登录,请登录后再回复。点此登录或注册