首页 > 其他 > 详细

PTA 1055 集体照

时间:2020-09-11 18:56:19      阅读:100      评论:0      收藏:0      [点我收藏+]

拍集体照时队形很重要,这里对给定的 N 个人 K 排的队形设计排队规则如下:

  • 每排人数为 /(向下取整),多出来的人全部站在最后一排;

  • 后排所有人的个子都不比前排任何人矮;

  • 每排中最高者站中间(中间位置为 /,其中 m 为该排人数,除法向下取整);

  • 每排其他人以中间人为轴,按身高非增序,先右后左交替入队站在中间人的两侧(例如5人身高为190、188、186、175、170,则队形为175、188、190、186、170。这里假设你面对拍照者,所以你的左边是中间人的右边);

  • 若多人身高相同,则按名字的字典序升序排列。这里保证无重名。

现给定一组拍照人,请编写程序输出他们的队形。

输入格式:

每个输入包含 1 个测试用例。每个测试用例第 1 行给出两个正整数 N(≤,总人数)和 K(≤,总排数)。随后 N 行,每行给出一个人的名字(不包含空格、长度不超过 8 个英文字母)和身高([30, 300] 区间内的整数)。

输出格式:

输出拍照的队形。即K排人名,其间以空格分隔,行末不得有多余空格。注意:假设你面对拍照者,后排的人输出在上方,前排输出在下方.

输入

Bob Tom Joe Nick
Ann Mike Eva
Tim Amy John

输出

10 3
Tom 188
Mike 170
Eva 168
Tim 160
Joe 190
Ann 168
Bob 175
Nick 186
Amy 160
John 159

从简单开始想起:

首先排序。我这里是从小到大排。

由题目可以知道除了最后一排的每排人数为rs=N/K, 最后一排的个数为lastrs=N/K+N%(N/K)

这意味着 最后一排的对象在数组中的位置为 N-lastrs+1~N,

    倒数第二排的对象在数组中的位置为 N-lastrs+1-rs~N-lastrs

 

    倒数第n排的对象在数组中的位置为 N-lastrs+1-rs*(n-1)~N-lastrs-rs*(n-2)

现在我们已经得到了每行的数据都是啥,接下来就是给每行数据进行重排。

为了将题目简化,我们可以理解为对于某一行对象从l到r的重排, 对象个数为len=r-l+1

当len为奇数的时候:

技术分享图片

黑色笔迹的是题意的思路。从大到小插入,然后输出, 但是这样很不方便。

红色和蓝色笔迹是另一种思路。把每一次插入都计数num。当是奇数的时候往蓝色部分插入,当是偶数的时候往红色部分插入。输出的时候红色部分直接按照插入的顺序输出,蓝色部分需要倒序输出。

因此我们可以在num为偶数的时候读到红色部分就直接输出,num为奇数的时候存到一个栈里面,数据读完后弹出所有的内容。

当len为偶数时:

技术分享图片

思路同上。但是红色部分变为当num为奇数,蓝色部分变为num为偶数。

 

代码

 1 #include<iostream>
 2 #include<cstring>
 3 #include<fstream>
 4 #include<algorithm>
 5 #include<stack>
 6 using namespace std;
 7 typedef long long ll;
 8 const ll mx=1e4+10;
 9 typedef struct node{
10     string name;
11     ll sg;
12 }STU;
13 STU stu[mx];
14 bool cmp(const STU&a, const STU&b){
15     if(a.sg==b.sg) return a.name>b.name;
16     return a.sg<b.sg;
17 }
18 void paidui(ll l, ll r){
19     stack<string>q;
20     ll num=0, base=(r-l+1)%2==0?1:0;//len 偶数base为1 
21     bool appe=false;
22     for(ll i=l;i<=r;i++){
23         num++;
24         if(num%2==base){//红色部分 直接输出
25             if(appe) cout<<" ";
26             appe=true;
27             cout<<stu[i].name; 
28         }
29         else{
30             q.push(stu[i].name);
31         }
32     }
33     while(!q.empty()){//蓝色部分 栈弹出使其倒序输出
34         if(appe) cout<<" ";
35         cout<<q.top();
36         q.pop();
37     }
38     cout<<endl;
39 }
40 int main(){
41     ll N, K;
42     cin>>N>>K;
43     for(ll i=1;i<=N;i++){
44         cin>>stu[i].name>>stu[i].sg;
45     }
46     sort(stu+1, stu+N+1, cmp);
47 
48     ll rs=N/K, lastrs=rs+N%rs;
49     //第一行 最后一排
50     ll d=N-lastrs+1;
51     paidui(d, N);
52 
53     //其他几行
54     for(ll i=1;i<=K-1;i++){
55         paidui(d-rs*i, d-1-rs*(i-1));
56     }
57 
58     return 0;
59 }

 

PTA 1055 集体照

原文:https://www.cnblogs.com/sloth612/p/13653132.html

(0)
(0)
   
举报
评论 一句话评论(0
关于我们 - 联系我们 - 留言反馈 - 联系我们:wmxa8@hotmail.com
© 2014 bubuko.com 版权所有
打开技术之扣,分享程序人生!