[bzoj1588][HNOI2002]营业额统计

Description

给出n个数,求每个数和它前面每个数的差值绝对值的最小值之和。
n<=32767

Solution

很显然求前驱后驱。
可以离散化后用权值线段树二分找。
也可以直接用splay找。
或者还可以离线排完序用双向链表找。
你喜欢就好喽。。。

Orz bzoj上rank1 0ms踩所有人

Code

#include<cstdio>
#include<cstring>
#include<algorithm>
#define fo(i,a,b) for(int i=a;i<=b;i++)
#define N 50005
using namespace std;
const int inf=0x7fffffff;
int n,x,a,b,ans,tot,root,t[N][2],f[N],key[N];
void insert(int &v,int y,int fa) {
    if (!v) {v=++tot;key[v]=y;f[v]=fa;return;}
    if (key[v]>y) insert(t[v][0],y,v);
    else insert(t[v][1],y,v);
}
int son(int x) {return t[f[x]][1]==x;}
void rotate(int x) {
    int y=f[x],z=son(x);f[x]=f[y];
    if (f[x]) t[f[x]][son(y)]=x;
    if (t[x][1-z]) f[t[x][1-z]]=y;
    f[y]=x;t[y][z]=t[x][1-z];t[x][1-z]=y;
}
void splay(int x,int y) {
    while (f[x]!=y) {
        if (f[f[x]]!=y)
            if (son(x)==son(f[x])) rotate(f[x]);
            else rotate(x);
        rotate(x);
    }
    if (!y) root=x;
}
int pre(int x) {
    x=t[x][0];
    while (x) {
        if (t[x][1]) x=t[x][1];
        else break;
    }
    return x;
}
int suf(int x) {
    x=t[x][1];
    while (x) {
        if (t[x][0]) x=t[x][0];
        else break;
    }
    return x;
}
int main() {
    scanf("%d",&n);
    scanf("%d",&x);
    insert(root,x,0);ans=x;
    fo(i,2,n) {
        scanf("%d",&x);
        insert(root,x,0);splay(tot,0);
        int l=pre(root);if (l) a=x-key[l];else a=inf;
        int r=suf(root);if (r) b=key[r]-x;else b=inf;
        ans+=min(a,b);
    }
    printf("%d",ans);
}
BZOJ 2908 题目是一个数据下载任务。这个任务要求下载指定的数据文件,并统计文件中小于等于给定整数的数字个数。 为了完成这个任务,首先需要选择一个合适的网址来下载文件。我们可以使用一个网络爬虫库,如Python中的Requests库,来帮助我们完成文件下载的操作。 首先,我们需要使用Requests库中的get()方法来访问目标网址,并将目标文件下载到我们的本地计算机中。可以使用以下代码实现文件下载: ```python import requests url = '目标文件的网址' response = requests.get(url) with open('本地保存文件的路径', 'wb') as file: file.write(response.content) ``` 下载完成后,我们可以使用Python内置的open()函数打开已下载的文件,并按行读取文件内容。可以使用以下代码实现文件内容读取: ```python count = 0 with open('本地保存文件的路径', 'r') as file: for line in file: # 在这里实现对每一行数据的判断 # 如果小于等于给定整数,count 加 1 # 否则,不进行任何操作 ``` 在每一行的处理过程中,我们可以使用split()方法将一行数据分割成多个字符串,并使用int()函数将其转换为整数。然后,我们可以将该整数与给定整数进行比较,以判断是否小于等于给定整数。 最后,我们可以将统计结果打印出来,以满足题目的要求。 综上所述,以上是关于解决 BZOJ 2908 数据下载任务的简要步骤和代码实现。 希望对您有所帮助。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值