PKU 2886 反素数+线段树
来源:互联网 发布:csol三米优化刀 编辑:程序博客网 时间:2024/04/30 05:48
Description
N children are sitting in a circle to play a game.
The children are numbered from 1 to N in clockwise order. Each of them has a card with a non-zero integer on it in his/her hand. The game starts from the K-th child, who tells all the others the integer on his card and jumps out of the circle. The integer on his card tells the next child to jump out. Let A denote the integer. If A is positive, the next child will be the A-th child to the left. If A is negative, the next child will be the (−A)-th child to the right.
The game lasts until all children have jumped out of the circle. During the game, the p-th child jumping out will get F(p) candies where F(p) is the number of positive integers that perfectly divide p. Who gets the most candies?
Input
Output
Output one line for each test case containing the name of the luckiest child and the number of candies he/she gets. If ties occur, always choose the child who jumps out of the circle first.
Sample Input
4 2Tom 2Jack 4Mary -1Sam 1
Sample Output
Sam 3
Source
[Submit] [Go Back] [Status] [Discuss]
Home Page Go Back To top
题目大意:几个孩子围成一圈,从第K个孩子开始跳出,每个孩子的手里有一张牌,上面写着非零的正整数,从第K个孩子开始,他跳出后,如果手里的牌上的数字是正数,那么从他左边开始越过牌上正整数的人数来得到下一个要跳出的人。如果手上的牌是负数,那么从他的右边开始越过负数的绝对值的人数得到下一个要跳出的人,没一个人跳出之后所得到的糖果数都是 他跳出的序号的约数个数,求得到糖果最多的孩子 以及他得到的糖果数。
先说这个题目要用到的第一个知识点,线段树。先创建一个1---n的线段树,每个区间的附加信息为当前区间的人数,如果序号为p的人要跳出,那么,如果tree[rt<<1]>=p,那么证明要跳出的人的序号在左边的区间,否则,要跳出的人在右边的区间,序号为p-tree[rt<<1]。从根节点一直向下处理,直到编号为p的人跳出即可。每次Update操作的时候,对应的区间的人数都要减掉1,因为每次操作一定会跳出一个,这样在update的函数中把pushup函数的要求也就实现了。。。。
另一个 知识点就是反素数,定义是如果小于等于N的任意数的因子个数都少于N的因子个数,那么N为反素数,即1---N的区间内N的因子数最多 。所以,如果有n个人,那么我们要找的得到最多糖果数就是n以内的最大反素数的因子数。至于得到最多糖果的人是谁,我们在找最大反素数的过程中,对应的那个人便是的到糖果最多的人。
至于求最大反素数以及对应的最大因子数的算法我还在实现中,写好了立刻贴上来
题目的代码如下:
#include<cstdio>#include<cstring>#include<cmath>#include<algorithm>#define maxn 555555#define lson l , m, rt<<1#define rson m+1, r, rt<<1|1using namespace std;int n,k;int tree[maxn<<2];const int antiprime[]={1,2,4,6,12,24,36,48,60,120,180,240,360,720,840,1260,1680,2520,5040,7560,10080,15120,20160,25200,27720,45360,50400,55440,83160,110880,166320,221760,277200,332640,498960,554400,665280};const int factorNum[]={1,2,3,4,6,8,9,10,12,16,18,20,24,30,32,36,40,48,60,64,72,80,84,90,96,100,108,120,128,144,160,168,180,192,200,216,224};typedef struct node{char name[15];int value;}JD;JD person[maxn];void build(int l,int r,int rt){tree[rt]=r-l+1;if(l==r)return ;int m=(l+r)>>1;build(lson);build(rson);}int update(int k,int l,int r,int rt){tree[rt]--;if(l==r){return l;}int m=(l+r)>>1;if(k<=tree[rt<<1]) return update(k,lson);else{k-=tree[rt<<1];return update(k,rson);}}int main(void){int i;int n,k,&mod=tree[1];while(scanf("%d%d",&n,&k)==2){for(i=1;i<=n;i++)scanf("%s%d",person[i].name,&person[i].value);build(1,n,1);int cnt=0;while(cnt<35 && antiprime[cnt]<=n)cnt++;cnt--;int pos=0;person[pos].value=0;for(i=0;i<antiprime[cnt];i++){if(person[pos].value>0)k=((k+person[pos].value-2)%mod+mod)%mod+1;elsek=((k+person[pos].value-1)%mod+mod)%mod+1;pos=update(k,1,n,1);}printf("%s %d\n",person[pos].name,factorNum[cnt]);}return 0;}
- PKU 2886 反素数+线段树
- poj 2886(线段树+反素数)
- poj 2886 线段树+反素数
- POJ 2886 反素数+线段树
- 线段树 + 反素数 poj2886
- poj2886 线段树+反素数
- poj2886线段树+反素数
- 模板___反素数 + poj2286 (反素数+线段树)
- poj 2886 线段树 (用反素数)
- 线段树点更新+反素数+poj2777
- poj2886反素数与线段树
- 线段树单点更新+反素数 poj-2886-Who Gets the Most Candies
- POJ 2886 Who Gets the Most Candies? (约瑟夫环+反素数+线段树)
- [poj 2886] Who Gets the Most Candies[线段树][约瑟夫环][反素数]
- POJ 2886 Who Gets the Most Candies?(线段树单点更新+反素数)
- POJ 2886 Who Gets the Most Candies?(线段树 + 约瑟夫环 + 反素数)
- poj 2886 Who Gets the Most Candies?(线段树单点更新+反素数)真难。。。
- POJ 2886 Who Gets the Most Candies?(线段树+反素数)
- 路径参数函数:路径的获取(GetModuleFileName)和拆分(_splitpath)
- Android 使用多个Intent 进行activity跳转 而没有finish的情况,如何直接退出系统
- PAT_1041: Be Unique
- common-io之Comparator阅读
- javascript检查表单数据是否改变
- PKU 2886 反素数+线段树
- Exception when run load test use visual studio.
- PHP中set_time_limit
- 智慧可以求生
- 挂起一个进程
- sqlserver是用触发器来实现 insert 后 返回自增 行的id号
- VS2008学习
- POJ-2985-The k-th Largest Group
- UML中的泛化,关联,依赖