2019 cattle off in Game 7 --C (Governing sand)

Governing sand

Portal: https://ac.nowcoder.com/acm/contest/887/C
Source: Cattle-off network

The meaning of problems: n to the trees, the trees of each number is the p [i], a height is h [i], each tree cut down cost is c [i]. Requirements tallest trees are more restricted than half of the total number, ask to cut some trees makes the conditions of minimum cost.
 
Ideas: The first question to see the range of data thought to enumerate every tree as the tallest tree, so it is bound to be higher than the first cut of all, after this sequence can be drained and resolved by a suffix,
Then cut is smaller than some of his trees, the conditions are met.
Because the suffix has been processed and the number of trees cut down, and the total number of all known tree, then it is clear that the number of trees cut down
K=sum-2*x+1
Finally, the minimum cost of processing trees cut, according to the direct cost of each tree size it should be inserted into position, so that the cost of the point on the array is a monotonic tree, binary tree to find several of Kandao .
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
const int N=2e5+5;
const ll inf=0x3f3f3f3f3f3f3f;
struct node
{
    ll w;
    int pos,h,p;
}a[N];
map<int,ll>m;
map<int,int>zz;
int n,b[N];
ll sum[N],num[N],cnt[N],C,W[N];
ll ask_w(int x)
{
    ll ans=0;
    for(;x;x-=x&(-x)) ans+=sum[x];
    return ans;
}
ll ask_num(int x)
{
    ll ans=0;
    for(;x;x-=x&(-x)) ans+=num[x];
    return ans;
}
void add_w(int x,ll y)
{
    for(;x<=n;x+=x&(-x)) sum[x]+=y;
}
void add_num(int x,ll y)
{
    for(;x<=n;x+=x&(-x)) num[x]+=y;
}
bool cmp(node x,node y)
{
    return x.w<y.w;
}
bool cmp2(node x,node y)
{
    return x.h<y.h;
}
int main()
{
    while(~scanf("%d",&n))
    {
        memset(num,0,sizeof num);
        memset(sum,0,sizeof sum);
        memset(W,0,sizeof W);
        memset(cnt,0,sizeof cnt);
        m.clear();
        C=0;
        for(int i=1;i<=n;i++)
        {
            scanf("%d%lld%lld",&a[i].h,&a[i].w,&a[i].p);
            a[i].pos=i;
        }
        sort(a+1,a+1+n,cmp);
        for(int i=1;i<=n;i++) b[a[i].pos]=i;
        sort(a+1,a+1+n,cmp2);
        for(int i=1;i<=n;i++)
        {
            zz[b[a[i].pos]]=i;
        }
        ll ans=inf;
        ll las=0;
        for(int i=n;i>=1;i--)
        {
            m[a[i].h]+=a[i].p;
            if(i!=n&&a[i].h==a[i+1].h)
            {
                cnt[i]=cnt[i+1];
                W[i]=W[i+1];
                las+=a[i].p*a[i].w;
            }
            else
            {
                cnt[i]=cnt[i+1]+m[a[i+1].h];
                W[i]=W[i+1]+las;
                las=a[i].p*a[i].w;
            }
            C+=a[i].p;
        }
        for(int i=1;i<=n;i++)
        {
            int l=0,r=n;
            ll tmp=W[i],k=max(0ll,C-cnt[i]-2*m[a[i].h]+1);
            if(a[i].h==a[i-1].h)
            {
                add_w(b[a[i].pos],a[i].w*a[i].p);
                add_num(b[a[i].pos],a[i].p);
                continue;
            }
            while(l<r)
            {
                int mid=(l+r)/2;
                if(ask_num(mid)>=k)
                {
                    r=mid;
                }
                else l=mid+1;
            }
            tmp+=ask_w(max(0,l-1));
            k-=ask_num(max(0,l-1));
            tmp+=k*a[zz[l]].w;
            ans=min(ans,tmp);
            add_w(b[a[i].pos],a[i].w*a[i].p);
            add_num(b[a[i].pos],a[i].p);
        }
        printf("%lld\n",ans);
    }
    return 0;
}

 

 

Guess you like

Origin www.cnblogs.com/Suiyue-Li/p/11323522.html