洛谷P2085 最小函数值 堆

题目链接:https://www.luogu.com.cn/problem/P2085

根据题目,我们可以很容易知道,一个函数F(x),F(1)一定数所有函数值里最小的并且,F(1)<F(2)<F(3)<…<F(n)。我们先将所有函数的F(1)放入堆中,按函数值从小到大排序,然后每次取出堆顶heap[1],放入F(x+1),更新小根堆,重复m次即可。
代码如下(这里手写堆,优先队列也可以)

#include <bits/stdc++.h>
using namespace std;
const int maxn=1e4+5;
struct node
{
    long long a,b,c;
    long long x,y;
}heap[maxn];
bool cmp(node t1,node t2)
{
    return t1.y<t2.y;
}
long long func(node t)
{
    long long y=t.a*t.x*t.x+t.b*t.x+t.c;
}
void Swap(node &t1,node &t2)
{
    node temp=t1;
    t1=t2;
    t2=temp;
}
int n,m;
int main()
{
    scanf("%d %d",&n,&m);
    for(int i=1;i<=n;i++)
    {
        scanf("%lld %lld %lld",&heap[i].a,&heap[i].b,&heap[i].c);
        heap[i].x=1;
        heap[i].y=heap[i].a+heap[i].b+heap[i].c;
    }
    sort(heap+1,heap+1+n,cmp);
    for(int i=1;i<=m;i++)
    {
        printf("%lld ",heap[1].y);
        heap[1].x++;
        heap[1].y=func(heap[1]);
        int j=1;
        while((j<<1)<=n)//更新小根堆
        {
            int temp=j<<1;
            if(temp<n&&heap[temp].y>heap[temp+1].y)
            temp++;
            if(heap[temp].y<heap[j].y)
            {
                Swap(heap[temp],heap[j]);
                j=temp;
            }
            else
            break;
        }
    }
    return 0;
}

猜你喜欢

转载自blog.csdn.net/weixin_44491423/article/details/104515094