首页 > 其他分享 >[lnsyoj4029/luoguP4109/HEOI2015]定价

[lnsyoj4029/luoguP4109/HEOI2015]定价

时间:2024-08-15 19:57:02浏览次数:14  
标签:10 log int while lnsyoj4029 luoguP4109 HEOI2015 ans include

题意

记 \(x'\) 为 \(x\) 去除后导零的值,则定义 \(f(x)=2(\lfloor\log_{10}x'\rfloor+1) - [x' \equiv 5 \pmod{10}]\),给定区间 \([L,R]\),求该区间中最小的 \(f(x)\) 值。

sol

一道贪心题,思想比较好想,我们需要使得前面的非 0 数字部分长度最小,且末尾尽可能为 \(5\)。具体实现中,我们可以运用倍增思想,向后枚举时使后面的 \(0\) 的部分长度不降,每次枚举判断其 \(f(x)\) 值,这样就可以 \(O(\log R)\) 地枚举,总时间复杂度 \(O(\log^2 R)\)。

代码

#include <iostream>
#include <algorithm>
#include <cstring>
#include <cmath>

using namespace std;

const int K = 15;

int T;
int l, r;
int p[K];

int count(int x){
    int ans = 0;
    while (!(x % 10)) ans ++ , x /= 10;
    return ans;
}

int calc(int x){
    while (!(x % 10)) x /= 10;
    int ans = 0;
    if (x % 10 == 5) ans -- ;
    while (x) ans += 2 , x /= 10;
    return ans ;
}

int main(){
    p[0] = 1;
    for (int i = 1; i < 10; i ++ ) p[i] = p[i - 1] * 10;

    scanf("%d", &T);
    while (T -- ){
        scanf("%d%d", &l, &r);
        int ans = 0x3f3f3f3f, id;
        for (; l <= r; l += p[count(l)]){
            int t = calc(l);
            if (t < ans) ans = t, id = l;
        }
        printf("%d\n", id);
    }

    return 0;
}

标签:10,log,int,while,lnsyoj4029,luoguP4109,HEOI2015,ans,include
From: https://www.cnblogs.com/XiaoJuRuoUP/p/-/lnsyoj4029_luoguP4109

相关文章

  • 题解 P4108【[HEOI2015]公约数数列】
    看到这种奇怪的操作,首先想到分块。以下记值域为\(w\),块长为\(B\)。前缀\(\gcd\)显然单调不增,而且后一个必须是前一个的因数,如果变化至少要减半。因此,我们知道,共有\(\mathcalO(\logw)\)个不同的前缀\(\gcd\)。我们可以接受对这些块暴力,只需要对前缀\(\gcd\)都相同的块......
  • 矩阵树定理学习笔记 & 洛谷 P4111 [HEOI2015]小 Z 的房间 题解
    矩阵树定理拉普拉斯矩阵无边权设无向图\(G\)有\(n\)个结点,则拉普拉斯矩阵\(L\)是一个\(n\timesn\)的矩阵,满足:\(L_{i,i}(i\inG)\)的值为结点\(i\)的度数......
  • 【HEOI2015】兔子与樱花(贪心)
    首先想一下题目中的操作如何转化:当一个节点被去掉之后,这个节点上的樱花和它的儿子节点都被连到删掉节点的父节点上。设当前节点为\(u\),\(u\)的父节点为\(fa\),儿子个......
  • BZOJ 4031([HEOI2015]小Z的房间-矩阵树定理+辗转相除)
    矩阵树定理,注意gauss消元辗转相除的写法#include<bits/stdc++.h>usingnamespacestd;#define#define#define#define#define#define#define#define#define#define#define#d......