• PAT甲题题解-1016. Phone Bills (25)-模拟、排序


    博主欢迎转载,但请给出本文链接,我尊重你,你尊重我,谢谢~
    http://www.cnblogs.com/chenxiwenruo/p/6789229.html
    特别不喜欢那些随便转载别人的原创文章又不给出链接的
    所以不准偷偷复制博主的博客噢~~

    给出一天24小时内,每个小时内,每分钟的通话费用
    给出n个记录,on-line表示通话的开始,off-line表示通话的结束
    如果on-line/off-line没有对应的另一个,忽略即可

    先按人名排序,名称一样的按时间排序,这里时间统一按分钟来算,即一天有24*60分钟,那么01:01:05就是0*24*60+1*60+5
    然后找出彼此配对的on-line和off-line,存入phone数组
    然后接下来就是求出每个通话时间的费用即可

    (主要是如何计算出费用比较细节麻烦一点,推荐做一下)

    #include <iostream>
    #include <cstdio>
    #include <algorithm>
    #include <cstring>
    #define ONLINE 0
    #define OFFLINE 1
    using namespace std;
    const int maxn=1000+5;
    const int DAYMINUTE=24*60;
    const int HOURMINUTE=60;
    int toll[24];
    int n;
    struct Record{
        char name[25];
        int time;
        int month;
        int day;
        int hour;
        int minute;
        int mark;
        bool operator<(const Record tmp)const{
            if(strcmp(name,tmp.name)==0)
                return time<tmp.time;
            else if(strcmp(name,tmp.name)<0)
                return true;
            else
                return false;
        }
    }record[maxn];
    
    struct Phone{
        char name[25];
        int month;
        int d1,h1,m1;
        int d2,h2,m2;
        int time1,time2;
    }phone[maxn];
    int cnt=0;
    /**
    求出第i个配对的通话时间费用
    */
    int cal(int i){
        int sum=0;
        int start=phone[i].time1; //起始时间
        int ends=phone[i].time2;  //结束时间
        int tmp=0; //统计每个小时的时间段内,通话的分钟
        int idx; //对应时间段toll的索引
        for(int t=start;t<=ends;t++){
            if(t%60==0){
                if(t%DAYMINUTE==0)
                    idx=(DAYMINUTE-1)/60;  //如果模为0,就应该是DAYMINUTE
                else
                    idx=(t%DAYMINUTE-1)/60; //因为可能会有连续通话了好几天,所以得取模一下
                sum+=tmp*toll[idx];  //通话的分钟*该时间段的费用
                tmp=1; //为了方便起见,像01:06:00这种整时的,算作下一小时的
            }
            else
                tmp++;
        }
        if(tmp){
            //比如说1:08:03,由于1:08:00的时候算作8-9之间的,实际上统计的tmp=4,所以要-1
            sum+=(tmp-1)*toll[(ends%DAYMINUTE)/60];
        }
        return sum;
    }
    int main()
    {
        char word[10];
        for(int i=0;i<24;i++)
            scanf("%d",&toll[i]);
        scanf("%d",&n);
        for(int i=0;i<n;i++){
            scanf("%s %d:%d:%d:%d %s",record[i].name,&record[i].month,&record[i].day,&record[i].hour,&record[i].minute,word);
            record[i].time=(record[i].day-1)*DAYMINUTE+record[i].hour*HOURMINUTE+record[i].minute;
            if(word[1]=='n')
                record[i].mark=ONLINE;
            else
                record[i].mark=OFFLINE;
        }
        sort(record,record+n);
        int last=-1; //之前最近的一个on-line的索引
        //找出配对的on-line和off-line,存入phone数组,方便后序处理
        for(int i=0;i<n;i++){
            if(record[i].mark==ONLINE){
                last=i;
            }
            if(record[i].mark==OFFLINE && last!=-1){
                if(strcmp(record[i].name,record[last].name)==0){
                    strcpy(phone[cnt].name,record[i].name);
                    phone[cnt].month=record[i].month;
                    phone[cnt].d1=record[last].day;
                    phone[cnt].h1=record[last].hour;
                    phone[cnt].m1=record[last].minute;
                    phone[cnt].time1=record[last].time;
                    phone[cnt].d2=record[i].day;
                    phone[cnt].h2=record[i].hour;
                    phone[cnt].m2=record[i].minute;
                    phone[cnt].time2=record[i].time;
                    cnt++;
                    last=-1;
                }
            }
        }
        int tot=0,sum=0;
        for(int i=0;i<cnt;i++){
            if(i==0){
                printf("%s %02d
    ",phone[i].name,phone[i].month);
                sum=cal(i);
                tot+=sum;
                int len=phone[i].time2-phone[i].time1;
                double cost=sum*1.0/100;
                printf("%02d:%02d:%02d %02d:%02d:%02d %d $%.2lf
    ",phone[i].d1,phone[i].h1,phone[i].m1,phone[i].d2,phone[i].h2,phone[i].m2,len,sum*1.0/100);
            }
            else{
                if(strcmp(phone[i].name,phone[i-1].name)!=0){
                    printf("Total amount: $%.2lf
    ",tot*1.0/100);
                    printf("%s %02d
    ",phone[i].name,phone[i].month);
                    tot=0;
                }
                sum=cal(i);
                tot+=sum;
                int len=phone[i].time2-phone[i].time1;
                int cost=sum*1.0/100;
                printf("%02d:%02d:%02d %02d:%02d:%02d %d $%.2lf
    ",phone[i].d1,phone[i].h1,phone[i].m1,phone[i].d2,phone[i].h2,phone[i].m2,len,sum*1.0/100);
            }
        }
        if(tot){
            printf("Total amount: $%.2lf
    ",tot*1.0/100);
        }
        return 0;
    }
    View Code
  • 相关阅读:
    gdb php
    redis启动过程
    php protobuf 安装使用2
    php protobuf 安装使用
    服务治理
    base64编码
    redis-quicklist
    redis-ziplist
    redis-zset数据结构探索
    su root 出现 su: Authentication failure
  • 原文地址:https://www.cnblogs.com/chenxiwenruo/p/6789229.html
Copyright © 2020-2023  润新知