USACO Milking Cows

Three farmers rise at 5 am each morning and head for the barnto milk three cows. The first farmer begins milking his cow at time300 (measured in seconds after 5 am) and ends at time 1000. Thesecond farmer begins at time 700 and ends at time 1200. The thirdfarmer begins at time 1500 and ends at time 2100. The longestcontinuous time during which at least one farmer was milking a cowwas 900 seconds (from 300 to 1200). The longest time no milking wasdone, between the beginning and the ending of all milking, was 300seconds (1500 minus 1200).

Your job is to write a program that will examine a list ofbeginning and ending times for N (1 <= N <= 5000) farmersmilking N cows and compute (in seconds):

  • The longest time interval at least one cow was milked.
  • The longest time interval (after milking starts) during whichno cows were being milked.

PROGRAM NAME: milk2

INPUT FORMAT

Line 1: The single integer
Lines 2..N+1: Two non-negative integers lessthan 1,000,000, respectively the starting and ending time in secondsafter 0500

SAMPLE INPUT (file milk2.in)

3
300 1000
700 1200
1500 2100

OUTPUT FORMAT

A single line with two integers that represent the longestcontinuous time of milking and the longest idle time.

SAMPLE OUTPUT (file milk2.out)

900 300

 -----------------------------------------------------------------------------------------------------------------


这道题典型的栈的思想。


把开始和结束操作放在一起排序,成为时间线,而开始和结束操作都位于时间线上某一点,因此可以维护一个保存开始操作的栈,程序按时间线走,遇到开始就把开始压入栈,遇到结束就弹出一个开始。

(每一个结束必定在它的开始后,所以栈永远不为负。)

题目就转化为求栈为空和不为空的最长时间。

维护一个栈底变量,当全部弹出时栈为空,此时时间减去最开始的时间就是这次栈不为空的持续时间;

维护一个最后栈为空时刻的变量,当压入开始操作时若栈为空,则这个开始的时间减去上一次弹出的时间,即为这次栈为空的持续时间。


还有一个问题是有可能两个人的开始和结束位于同一个时间点,造成栈为负的情况。解决办法可以在qsort的cmp函数里把入栈放在前面,也可以在遍历时间线时判断前后的时间值,如果时间值相同且操作相反,直接continue。


/*
ID: windroid
LANG: C++
TASK: milk2
*/
#include<iostream>
#include<fstream>
#include<list>
#include<algorithm>
using namespace std;

int cmp(const void* p1, const void* p2){
    return (*(pair<int,int>*)p1).first - (*(pair<int,int>*)p2).first;
}
pair<int ,bool> t[10005];
int main(){
    ifstream fin("milk2.in");
    ofstream fout("milk2.out");
    int n;

    fin>>n;
    for(int i=0;i<2*n;i+=2){
        int b1,e1;

        fin>>b1>>e1;
        t[i].first = b1;
        t[i].second = true;
        t[i+1].first = e1;
        t[i+1].second = false;
    }
    qsort(t,2*n,sizeof(t[0]),cmp);
//    for(int i=0;i<2*n;i++){
//        fout<<t[i].first<<"-"<<t[i].second<<endl;
//    }
    //stack<int> st;
    int st = 0;
    int maxt = 0, maxi = 0;
    //栈 压入b
    int buttom = 0;
    int lastend = t[0].first;
    for(int i=0;i<2*n;i++){
        if(i != 2*n-1 && t[i].first == t[i+1].first && t[i].second != t[i+1].second){
            i++;
            continue;
        }
        if(t[i].second == true){
            if(st == 0){
                if(t[i].first - lastend > maxi){
                    maxi = t[i].first - lastend;
                }
                buttom = t[i].first;
            }
            //st.push(t[i].first);
            st++;
        }else{
            //st.pop();
            st--;
            if(st == 0){
                cout<<"end-buttom  "<<t[i].first<<" - "<<buttom<<" = "<<t[i].first - buttom<<endl;
                if(t[i].first - buttom > maxt){
                    maxt = t[i].first - buttom;
                }
                lastend = t[i].first;
            }
        }
        cout<<"t[i] "<<t[i].first<<"  "<<t[i].second<<endl;
        cout<<"st "<<st<<endl;
    }
    cout<<maxt<<" "<<maxi<<endl;
    fout<<maxt<<" "<<maxi<<endl;
    return 0;
}



发布了26 篇原创文章 · 获赞 6 · 访问量 4万+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章