以下是问题的链接:https://www.spoj.com/problems/ACTIV/
这里是代码:它给出了超过时间限制,但我一直处于nlogn的限制内。我首先根据开始时间进行排序,然后对介于0到i之间的作业进行排序,选择该作业的索引,该索引的完成时间恰好在第i个作业的开始时间之前(因此基本上包括第i个作业),然后与i-1相加指示是否选择了第一个作业。
#include <iostream>
#include <stdio.h>
#include <algorithm>
#include <vector>
#include <utility>
#include <cstring>
#define ll long long int
#define mod 100000000
using namespace std;
int latest(vector <pair<int, int> > arr, int s, int i){
int f=arr[i].first;
while(s<=i){
int mid=s+(i-s)/2;
if(arr[mid].second==f){
s=mid;
break;
}
if(arr[mid].second<f){
if(f<=arr[mid+1].second){
return mid+1;
}else{
s=mid+1;
}
}
else if(arr[mid].second>f){
if(mid==0){
return -1;
}
else if(f>=arr[mid-1].second){
return mid-1;
}else{
i=mid-1;
}
}
}
return s;
}
int main() {
int n;
while(cin>>n){
if(n==-1){
break;
}
int i;
vector <pair<int, int> > arr(n);
for(i=0;i<n;i++){
int x,y;
cin>>x>>y;
arr[i].first=x;
arr[i].second=y;
}
ll dp[n+1];
dp[0]=1;
sort(arr.begin(), arr.end());
for(i=1;i<=n;i++){
dp[i]=dp[i-1]+dp[latest(arr, 0, i-1)+1];
}
printf("%08lld\n", dp[n]-1);
}
return 0;
}