AtCoderBeginnerContest127 EF题

本文介绍了AtCoder Beginner Contest 127的E题和F题。F题涉及函数f(x)的更新与查询,通过考虑绝对值函数在数轴上的表现,利用对顶堆解决。E题则探讨了在n*m网格中选取k个格子,计算所有可能组合的曼哈顿距离之和的策略,最终得出解决方案。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

AtCoder Beginner Contest 127 EF

https://atcoder.jp/contests/abc127

F题:
题意:
有函数f(x)初始为0,有两个操作,
1是给f(x)加上|x−a|+b,
2是询问函数的最小值及x

思路:
查询的时候,b累加就好了,前面就是多个绝对值的函数这样
|x - a1| + |x - a2| + |x - a3|这样 ,想到就是数轴上x到点的距离,就比较清晰了。就是对顶堆有点忘了稍微复习了下。

	int t,n,m;
priority_queue<int> down;
priority_queue<int,vector<int>,greater<int>> up;
int main(){
    scanf("%d",&n);
    int op,a,b;
    ll tmpb = 0;
    ll downsum = 0,upsum = 0;
    for(int i=1;i<=n;i++){
        scanf("%d",&op);
        if(op == 1){
            scanf("%d%d",&a,&b);
            if(down.empty() || a <= down.top()) down.push(a),downsum += a;
            else up.push(a),upsum += a; 
            if(down.size() > up.size() + 1) {
                up.push(down.top());
                downsum -= (int)down.top();
                upsum += (int)down.top();
                down.pop();
            }
            if(up.size() > down.size()) {
                down.push(up.top());
                upsum -= (int)up.top();
                downsum += (int)up.top();
                up.pop();
            }
            tmpb += b;
        }else{
            ll res;
            int cnt = down.size() + up.size();
            printf("%d ",down.top());
            if(cnt & 1){
                res = upsum - downsum + down.top() + tmpb;
            }else{
                res = upsum - downsum + tmpb;
            }
            printf("%lld\n", res);
        }
    }
    return 0;
}

E题
题意:
求一个n*m网格图里每次选k个格,然后计算这k个格子里任两个曼哈顿距离之和。算出以上所有不同方案答案距离总和
思路:
选k个格子方案数是C(n,m),然后k个格子任两个欧几里得距离有C(k,2)
N×M 的网格图里面任意两点的曼哈顿距离的平均值是(n+m) / 3
答案 =
在这里插入图片描述

const ll mod = 1e9+7;
ll t,n,m,k;
ll fac[N],inv[N];
ll qmi(ll a,ll b){
	ll res = 1;
	while(b){
		if(b & 1) res = res * a % mod;
		a = a * a % mod;
		b >>= 1;
	}
	return res;
}
ll C(ll x,ll y){
	return fac[x] * inv[y] % mod * inv[x-y] % mod;
}
int main(){
	fac[0] = 1;
	inv[0] = qmi(fac[0],mod-2);
	for(int i=1;i<=200000;i++){
		fac[i] = fac[i-1] * i % mod;
		inv[i] = qmi(fac[i],mod - 2);
	}
	cin>>n>>m>>k;
	ll res = C(n*m,k) * C(k,2) % mod * (n + m) % mod * qmi(3,mod-2) % mod;
	cout<<res<<endl;
	return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值