题意:

  前面3/4的英文都是废话。将一个正整数看成字符串,给定一个k,问区间[L,R]中严格的LIS=k的数有多少个?

思路:

  实在没有想到字符0~9最多才10种,况且也符合O(nlogn)求LIS的特点,所以用状态压缩可以解决。

  看到状态压缩的字眼基本就会做了,增加一维来保存当前LIS的状态。由于求LIS时的辅助数组d[i]表示长度为i的LIS最后一个元素,d数组是严格递增的,所以好好利用d数组的特性来设计状态压缩才是关键。压缩的状态0101可以表示:仅有0和2在数组d中,即d[1]=0,d[2]=2的意思。状态的设计方法有多种。

  此题在考虑前导零问题时,逐个枚举位数,可以这样做是因为如果位数超过了1,则最后一个数位若为0是不会对结果构成影响的,因为最后的0都不会被考虑在LIS中。而对于那些个位数为0(或者说后缀0)会对结果产生影响的,最好是不要这样用了(例如spoj Balanced Numbers就不可以)。

 #include <bits/stdc++.h>
#include <iostream>
#include <cstdio>
#include <cstring>
#include <cmath>
#include <map>
#include <algorithm>
#include <vector>
#include <iostream>
#define pii pair<int,int>
#define INF 0x7f3f3f3f
#define LL long long
#define ULL unsigned long long
using namespace std;
const double PI = acos(-1.0);
const int N=; LL f[N][<<][], bit[N];
//[位数][状态][k] int insert(int s,bool flag,int pos) //修改状态
{
for(int i=pos; i<=&&flag; i++) //找到第一位>=pos的,抹去
if(s&(<<i))
{
s^=(<<i);
break;
}
return s|(<<pos);
} int gethigh(int s) //获取LIS最大元素,即d[len]。
{
for(int i=; i>=; i--) if(s&(<<i)) return i;
return -;
} LL dfs(int i,int up,int s,int k,bool e)
{
//up为总位数,s为状态,k为仍需一段len=k的串来组成LIS=K的
if(i==) return k==;
if(i<k) return ; //剩下的位数已不够k个,不能组成LIS=k
if(!e && ~f[i][s][k] ) return f[i][s][k]; LL ans=;
int d= i==up? : ; //为了解决前缀0的情况,起始不为0
int u= e? bit[i]: ; int h=gethigh(s); //LIS的最大元素
for( ; d<=u; d++)
{
if(d>h) ans+=dfs(i-,up,insert(s,,d),k-,e&&d==u);
else ans+=dfs(i-,up,insert(s,,d),k,e&&d==u); //LIS长度不变
}
return e? ans: f[i][s][k]=ans;
} LL cal(LL n,int k)
{
if(n==) return ;
int len=;
while(n) //拆数
{
bit[++len]=n%;
n/=;
}
LL ans=;
for(int i=k; i<len; i++) //为了解决前导0问题,逐个枚举
ans+=dfs(i,i,,k,false);
if(len>=k)
ans+=dfs(len,len,,k,true);
return ans;
} int main()
{
//freopen("input.txt","r",stdin);
memset(f, -, sizeof(f));
LL L, R;int t, K, Case=;
cin>>t;
while( t-- )
{
scanf("%lld%lld%d",&L,&R,&K);
printf("Case #%d: %lld\n", ++Case, cal(R,K)-cal(L-,K));
}
return ;
}

AC代码

HDU 4352 XHXJ's LIS (数位DP,状压)的更多相关文章

  1. HDU.4352.XHXJ's LIS(数位DP 状压 LIS)

    题目链接 \(Description\) 求\([l,r]\)中有多少个数,满足把这个数的每一位从高位到低位写下来,其LIS长度为\(k\). \(Solution\) 数位DP. 至于怎么求LIS, ...

  2. hdu 4352 XHXJ's LIS(数位dp+状压)

    Problem Description #define xhxj (Xin Hang senior sister(学姐)) If you do not know xhxj, then carefull ...

  3. HDU 4352 XHXJ's LIS 数位dp lis

    目录 题目链接 题解 代码 题目链接 HDU 4352 XHXJ's LIS 题解 对于lis求的过程 对一个数列,都可以用nlogn的方法来的到它的一个可行lis 对这个logn的方法求解lis时用 ...

  4. $HDU$ 4352 ${XHXJ}'s LIS$ 数位$dp$

    正解:数位$dp$+状压$dp$ 解题报告: 传送门! 题意大概就是港,给定$[l,r]$,求区间内满足$LIS$长度为$k$的数的数量,其中$LIS$的定义并不要求连续$QwQ$ 思路还算有新意辣$ ...

  5. hdu 4352 XHXJ's LIS 数位dp+状态压缩

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=4352 XHXJ's LIS Time Limit: 2000/1000 MS (Java/Others ...

  6. HDU 4352 XHXJ's LIS (数位DP+LIS+状态压缩)

    题意:给定一个区间,让你求在这个区间里的满足LIS为 k 的数的数量. 析:数位DP,dp[i][j][k] 由于 k 最多是10,所以考虑是用状态压缩,表示 前 i 位,长度为 j,状态为 k的数量 ...

  7. hdu 4352 XHXJ's LIS 数位DP+最长上升子序列

    题目描述 #define xhxj (Xin Hang senior sister(学姐))If you do not know xhxj, then carefully reading the en ...

  8. hdu 4352 XHXJ's LIS 数位DP

    数位DP!dp[i][j][k]:第i位数,状态为j,长度为k 代码如下: #include<iostream> #include<stdio.h> #include<a ...

  9. HDU 4352 - XHXJ's LIS - [数位DP][LIS问题]

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=4352 Time Limit: 2000/1000 MS (Java/Others) Memory Li ...

  10. HDU 4352 XHXJ's LIS ★(数位DP)

    题意 求区间[L,R]内满足各位数构成的数列的最长上升子序列长度为K的数的个数. 思路 一开始的思路是枚举数位,最后判断LIS长度.但是这样的话需要全局数组存枚举的各位数字,同时dp数组的区间唯一性也 ...

随机推荐

  1. URL shortening service

    Use Cases 1, shortening : take a URL => return a much shorter URL 2, redirection : take a short U ...

  2. Linux&nbsp;rpm&nbsp;命令参数使用…

    RPM是RedHat Package Manager(RedHat软件包管理工具)类似Windows里面的"添加/删除程序" rpm 执行安装包 二进制包(Binary)以及源代码 ...

  3. HDU - 1150 POJ - 1325 Machine Schedule 匈牙利算法(最小点覆盖)

    Machine Schedule As we all know, machine scheduling is a very classical problem in computer science ...

  4. HDU - 2571 命运 DP倍数跳跃处理

    命运 穿过幽谷意味着离大魔王lemon已经无限接近了! 可谁能想到,yifenfei在斩杀了一些虾兵蟹将后,却再次面临命运大迷宫的考验,这是魔王lemon设下的又一个机关.要知道,不论何人,若在迷宫中 ...

  5. Coreseek 安装问题

    Ubuntu下安装coreseek mmseg出现了cannot find input file: src/Makefile.in 解决方法如下 >autoheader >automake ...

  6. sqlserver2012——变量declare

    1.声明变量病定义类型 赋值操作 ) set @name='小明' select @name 使用select进行赋值 ) select @name='李明' seelelct @name

  7. 一文带你认识Java8中接口的默认方法

    Java8是Oracle于2014年3月发布的一个重要版本,其API在现存的接口上引入了非常多的新方法. 例如,Java8的List接口新增了sort方法.在Java8之前,则每个实现了List接口的 ...

  8. OVN学习(三)

    部署OVN实验环境 同OVN学习(一) 网关 在L3网络基础上部署网关 添加L3网关 ### Central节点 # ovn-sbctl show Chassis "8bd09faf-5ba ...

  9. hdu2612(dijkstra)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=2612 题意:给出一个n*m的矩阵,' . ' 表示可以走的路, ' # '表示不能走的路 ,’ @'表 ...

  10. codeforces786E ALT【倍增+最小割】

    方案二选一,显然是最小割,朴素的想法就是一排人点一排边点,分别向st连流量1的边,然后人点向路径上的边点连流量inf的边跑最大流 但是路径可能很长,这样边数就爆了,所以考虑倍增,然后倍增后大区间向小区 ...