sort的用法
二维字符数组为空,一整行为空
二位字符数组赋值,一整行赋值
【代码是错的,以后改,如果有uu愿意帮忙的话,能不能看看是哪错了啊】
【现在已经改过来了,看第二个】
#include<cstdio>
#include<iostream>
#include<cstring>
#include<algorithm>
using namespace std;
#define N 1010
struct People
{
char id[30]={0};
int month=0,day=0,hour=0,minute=0;//月份
char state[30]={0};
}people[N],temp[N];//people对应每一个输入的数据,temp对应整理好1个人的n次通话数据的数据,即中间变量,用于输出
int map[26]={0};//24个小时中每小时对应的通话费用
char id[N][30]={0};//多少种人
void minute(People a,int &t,double &money)//一次通话花费的时长,和金钱,a前,b后 初始时间是1:0:0
{
if(a.day!=1)
{
t=(a.day-1)*24*60;
for(int i=0;i<=24;i++)
money+=map[i]*60;
}
if(a.hour!=0)
{
t+=a.hour*60;
for(int i=0;i<a.hour;i++)
money+=map[i]*60;
}
if(a.minute!=0)
{
t+=a.month;
money+=map[a.hour]*a.minute;
}
}
bool cmp(People a,People b)//按照时间给每个人的通话排一下序列
{
if(a.month!=b.month) return a.month<b.month;
if(b.day!=a.day)return a.day<b.day;
if(a.hour!=b.hour) return a.hour<b.hour;
return a.minute<b.minute;
}
int main()
{
//存放24小时中每小时对应的通话费用
for(int i=0;i<24;i++) cin>>map[i];
int n=0;
cin>>n;//总的通话数
for(int i=0;i<n;i++)
{
scanf("%s %02d:%02d:%02d:%02d %s",people[i].id,&people[i].month,&people[i].day,&people[i].hour,&people[i].minute,people[i].state);
}
//筛选出一共有多少种人
int k=1;
strcpy(id[0],people[0].id);
for(int i=0;i<n;i++)
{
int b=0;//标志 代表此人不在数组中
int j=0;
for( j=0;strlen(id[j])!=0;j++)//判定字符串数组为空NULL
{
if(strcmp(people[i].id,id[j])!=0) continue;//比较两个字符数组的是否相同
else
{
b=1;
break;
}
}
if(b==0) {strcpy(id[j],people[i].id);k++;}//添加新的人员 字符数组赋值 strcpy
}
//将名字按照字典序排列
// sort(&id[0],&id[k],cmp1);//sort的用法
//输出每个人的开销
for(int i=0;i<k;i++)
{
int k1=0;//中间变量,记录temp中存的数据
for(int j=0;j<n;j++)
{
if(strcmp(id[i],people[j].id)==0) temp[k1++]=people[i];
}
sort(&temp[0],&temp[k1],cmp);//按照时间顺序给一个人的n次通话记录进行排序
cout<<temp[0].id<<" "<<temp[0].month<<endl;
double sum=0;//存放一个人n次通话的总开销
//一个人第j次通话花费多少
for(int j=0;j<k1;)
{
int t1=0,t2=0;
double money1=0,money2=0;
minute(temp[j],t1,money1);
printf("%02d:%02d:%02d ",temp[j].day,temp[j].hour,temp[j].minute);
j++;
minute(temp[j],t2,money2);
printf("%02d:%02d:%02d ",temp[j].day,temp[j].hour,temp[j].minute);
j++;
sum+=money2-money1;
t1=t2-t1;
printf("%d %lf\n",t1,sum*0.01);
}
}
}
以下是经过“略微”修改的代码,有测试点2,3,4的备注,这道题思路不难,就是代码有点多,有个大佬的代码不到60行,但介于我还没学map,所以没怎么看,附上大佬的链接59行代码
#include<cstdio>
#include<iostream>
#include<algorithm>
#include <cstring>
using namespace std;
int map[26]={0};
struct ID
{
char name[50]={0};
int m=0,dd=0,hh=0,mm=0;//月,日,时,分
char state[30]={0};
}id[1010],temp[1010],temp1[1010];//id是输入的,temp是中间变量
char name[1010][30]={0};//总共有多少个用户
bool cmp1(char a[30],char b[30])
{
int l1=strlen(a);
int l2=strlen(b);
for(int i=0;i<l1||i<l2;i++)
{
if(a[i]==b[i]) continue;
else return a[i]<b[i];
}
}
bool cmp(ID a,ID b)//按照时间给每个人的通话排一下序列
{
if(a.m!=b.m) return a.m<b.m;
if(a.dd!=b.dd) return a.dd<b.dd;
if(a.hh!=b.hh) return a.hh<b.hh;
if(a.mm!=b.mm) return a.mm<b.mm;
}
int minute(ID a,int &time,double &money)//time 和money分别为从1:0:0开始计算得时间和金钱
{
time=0;
money=0;
if(a.dd !=1)
{
time+=(a.dd-1)*24*60;
for(int i=0;i<24;i++)
{
money+=map[i]*60;
}
money=(a.dd-1)*money;
}
if(a.hh!=0)
{
time+=a.hh*60;
for(int i=0;i<a.hh;i++)
{
money+=map[i]*60;
}
}
if(a.mm!=0)
{
time+=a.mm;
money+=map[a.hh]*a.mm;
}
}
int main()
{
for(int i=0;i<24;i++) cin>>map[i];
int n=0;//共有多少条记录
cin>>n;
for(int i=0;i<n;i++) scanf("%s %02d:%02d:%02d:%02d %s",&id[i].name,&id[i].m,&id[i].dd,&id[i].hh,&id[i].mm,&id[i].state);
//寻找总共有多少个用户,存入name【】【】中
int k=0;//记录用户的数量
for (int i = 0; i < n; i++)
{
if (i == 0) strcpy(name[k++], id[i].name);//初始赋值名字
//循环判断name【】中是否有id[i].name
else
{
int b=0;//此人不在name【】中
for(int j=0;j<k;j++)
{
if(strcmp(name[j],id[i].name)!=0) continue;//此人不在
else b=1;//此人在
}
if(b==0) strcpy(name[k++], id[i].name);
}
}
//将用户按照字典序列进行排序
for(int i=0;i<k;i++)
{
for(int j=i+1;j<k;j++)
{
if(cmp1(name[i],name[j])) continue;
else
{
char name1[30]={0};
strcpy(name1,name[i]);
strcpy(name[i],name[j]);
strcpy(name[j],name1);
}
}
}
//输出每个人的开销
for(int i=0;i<k;i++)
{
int k1=0;//中间变量,记录temp中存的数据
for(int j=0;j<n;j++)
{
if(strcmp(name[i],id[j].name)==0) temp[k1++]=id[j];
}
//将通话记录按照发生的先后顺序排序
sort(&temp[0],&temp[k1],cmp);//按照时间顺序给第i个人的k1次通话记录进行排序
//进行 on-off的匹配
int k2=0;//k2指的是最终的通话记录,保证是偶数个
for(int j=0;j<k1-1;j++)//
{
if (strcmp(temp[j].state, "on-line") == 0&&strcmp(temp[j+1].state, "off-line") == 0)//对应测试点4 之前比较两个状态不同就进行输出是不可以的哦
{
temp1[k2++] = temp[j];
temp1[k2++] = temp[j+1];
j++;
}
}
double total=0;
if(k2!=0)printf("%s %02d\n",temp1[0].name,temp1[0].m);
else continue;//对应测试点 2,3 如果on-off没有匹配成功则跳过该用户
for(int j=0;j<k2;j++)
{
int time1=0,time2=0;
double money1=0,money2=0;
minute(temp1[j],time1,money1);
printf("%02d:%02d:%02d ",temp1[j].dd,temp1[j].hh,temp1[j].mm);
j++;
minute(temp1[j],time2,money2);
printf("%02d:%02d:%02d ",temp1[j].dd,temp1[j].hh,temp1[j].mm);
printf("%d $%.2lf\n",time2-time1,(money2-money1)*0.01);
total+=money2-money1;
}
printf("Total amount: $%.2lf\n",total*0.01);
}
}
太开心了,这道题折磨了我好几天呜呜,所以凑不要脸的我附上AC的截图,偶吼吼吼吼
【其实主要还是自己懒,好几次点开clion都不能调试,有时候出现这种问题重启就好了,今天特别生气,两次重启还是不能调试,默默点开vs发现可以,于是乎,我不干了,推翻重来,重写了一遍代码,所以第二段代码跟第一段在参数上的形式有些许不同,但都差不多】