[루오 구 P4602] CTSC2018 혼합 과일 주스

문제 설명

R은 작은 어두운 요리, 특히 혼합 과일 주스를 할 싶어. 저장소는 N 과일 주스를 가지고 0, 1, 2,, N 번째 -... 1. 맛있는 주스의 I 번호는 파이의 리터 당 가격, 디입니다. 혼합 과일 주스의 생산에 작은 R, 즉 주스 병 혼합 특별한 규정이, 난 단지 주스 리 리터 번호를 추가 할 수 있습니다. 이제 그들은 주스 한 병에 혼합 약간의 R 저장소 주스를 만들기 위해 모든 희망, m 어린 아이들을 찾고은 R 혼합 된 과일 주스 음료에 와서있다. j 번째 얻은 주스를 혼합하는 것이 바람직 자신의 아이들은 총 가격 GJ, 이하 엘 제이 이외의 부피보다 크지된다. 이러한 제한에서, 아이들은 또한 가능한 한 높은 같은 과일 주스의 맛있는 혼합을 원하는 맛있는 혼합 과일 주스 한 병은 참여하는 모든 주스 혼합 맛도 최소 값과 같습니다. 각 아동의 과일 주스 혼합 음료의 가장 맛있는 맛을 계산하십시오.

입력 형식

파일에 juice.in에서 데이터를 읽습니다.

첫 번째 줄의 입력, 두 개의 양의 정수 N, m을 포함하는 아이의 수와 과일 주스의 종류의 수를 나타냅니다.

주스 병에 상한을 첨가 다음 N 라인 세 양수 디, PI는 리튬, 나 과일 주스 DI 수, PI 리터당 가격의 맛을을 나타내고, 각각의 라인은 리 내지.

다음 m 라인이 순차적으로 모든 아이를 설명 : 두 양의 정수의 각 행 GJ 번호를, 엘 제이 아이를 기술, 그가 주스의 적어도 엘 제이 리터를 원하는 그는 달러를 GJ까지 지불했다.

출력 형식

파일로 출력 Juice.out.

모든 어린이를위한 순차적으로 출력 : 각 자녀를 들면, 맛있는 주스의 가장 맛있는 혼합 학위를 마시 나타내는 정수를 포함하는 출력 한 줄. 당신이 자신의 요구를 충족 할 수없는 경우, 다음 출력 -1.

샘플 입력

3 4
1 3 5
2 1 3
3 2 5
6 3
5 3
10 10
20 10

샘플 출력

3
(2)
-1
1

설명

시험 된 모든 데이터는 N, m ≤ ≤ 디 100000,1, PI, 리튬 5,1 ≤ 10 ^ ≤ GJ LJ, ≤ 10 ^ 18을 보장하기 위해.

해결

재생 테이블과 형이상학의 방법으로 일련의 단조 답을 찾을 수 있습니다. 반 d를, 우리는보다 크거나 같은 D 주스를 선택할 수 있습니다. 이어서보다 큰 모든 D에 대해 설정 또는 다음 세그먼트 트리 목표 체중, 각 노드는 전체 부피 및 가격을 저장 주스의 가격 같다. 이 방법은 우리가 림의 오른쪽 절반에 트리 라인의 값을 사용할 수 있습니다.

하지만 다시 한 번 각 절반의 성과. 우리는이 문제를 해결하기 위해 지속성을 사용할 수있는 트리의 회장을 구축 할 수 있습니다.

코드

#include <iostream>
#include <cstdio>
#include <algorithm>
#define int long long
#define N 100002
#define T 100000
using namespace std;
struct ChairmanTree{
    int l,r,suml,sump;
}t[N*40];
struct juice{
    int d,p,l;
}a[N];
int n,m,i,g[N],L[N],root[N],p;
int read()
{
    char c=getchar();
    int w=0;
    while(c<'0'||c>'9') c=getchar();
    while(c<='9'&&c>='0'){
        w=w*10+c-'0';
        c=getchar();
    }
    return w;
}
int my_comp(const juice &x,const juice &y)
{
    return x.d<y.d;
}
int insert(int pre,int l,int r,int L,int P)
{
    p++;
    int num=p;
    t[p]=t[pre];
    t[p].suml+=L;t[p].sump+=L*P;
    if(l<r){
        int mid=(l+r)/2;
        if(P<=mid) t[p].l=insert(t[pre].l,l,mid,L,P);
        else t[p].r=insert(t[pre].r,mid+1,r,L,P);
    }
    return num;
}
int ask(int p,int l,int r,int L)
{
    if(l==r) return l*L;
    int mid=(l+r)/2;
    if(L<=t[t[p].l].suml) return ask(t[p].l,l,mid,L);
    return t[t[p].l].sump+ask(t[p].r,mid+1,r,L-t[t[p].l].suml);
}
signed main()
{
    n=read();m=read();
    for(i=1;i<=n;i++) a[i].d=read(),a[i].p=read(),a[i].l=read();
    for(i=1;i<=m;i++) g[i]=read(),L[i]=read();
    a[0].d=-1;
    sort(a+1,a+n+1,my_comp);
    for(i=n;i>=1;i--) root[i]=insert(root[i+1],1,T,a[i].l,a[i].p);
    for(i=1;i<=m;i++){
        int l=1,r=T,mid,ans=0;
        while(l<=r){
            mid=(l+r)/2;
            if(L[i]<=t[root[mid]].suml&&ask(root[mid],1,T,L[i])<=g[i]){
                ans=mid;
                l=mid+1;
            }
            else r=mid-1;
        }
        printf("%lld\n",a[ans].d);
    }
    return 0;
}

추천

출처www.cnblogs.com/LSlzf/p/11878957.html