時間限制:
3000
ms |
記憶體限制:
65535kb
描述
一本書的頁碼從自然數
1開始順序編碼到自然數
n。書的頁碼按照通常的習慣編排,每個頁碼都不含多餘的前導數字
0。例如,第
6頁用數字
6表示,而不是
06或者
006等。數字計數問題要求對給定書的總也碼
n,分別計算出
0,1,
…,9總共出現的次數
輸入
給定的頁碼n (
0) 輸出
分別輸出
0,1,
…,9出現的總次數
樣例輸入
99
樣例輸出
9 20 20 20 20 20 20 20 20 20
要求
不能直接從1迴圈到n,對每個數字計算0~9出現的次數。
/*
演算法實驗題,我覺得蠻難的蠻麻煩的=_=(對於演算法課來說),或者是我太水.>_<,
想去網上看人家怎麼破才比較簡單,沒找到,或者我搜尋能力也是很水=_=
dp[i][j][k] ,表示長度為 i , 以 j 開頭 , k 用的次數
轉移 dp[i][j][k] = 求和(dp[i-1][u][k]) 0 <= u <= 9
dp[i][j][j] += 10^(i-1) ;
因為不能有前導 0 ,所以我們開了 hehe陣列
hehe[i][j] 表示長度為 i-1 的所以數 , j 用的次數
然後對於 n , == 不好解釋,取個例子
n = 2345 先把 n 的各個位拿出來
對於 0 開頭的,直接取 hehe[3]
對於 1 開頭的,都可以取了 就是 dp[4][1]
對於 2 開頭的,2 能去 345 (2345%1000) 個
然後 就是 2 開頭下面的 2x1x2x3
x1 = 0 ,在 hehe 裡面已經算了
x1=1,2都可以取
對於 x1 = 3 , 3 能取 45(2345%100) 個
然後對於 23x2x3
....
一直這樣下去
ps: 測試了很多資料是對的,沒有oj可以交,所以不能保證所有的都是對的,
助教應該看不到的吧,hehe
by 20120125
*/
//e
#include
#include
#include
#include
#include
#include
#include
#define maxn 110
#define ll long long
using namespace std ;
ll dp[12][12][12] ,hehe[12][12] ;
int ans[12] ;
int get( int n )
void init()
for( i = 2 ; i <= 10 ;i++ )
for( j = 0 ; j < 10 ;j++ )
hehe[i+1][j] = hehe[i][j] ;
for( j = 1 ; j < 10 ;j++ )}}
int find( int u , int n )
void getans( int n )
for( i = 0 ; i < 10 ;i++ )
ans[i] = hehe[k-1][i] ;
for( i = k-1 ; i >= 1 ;i-- )
}void zhe( int n )//暴力}}
int main()
cout << "time: " << clock()-tt << endl;
return 0 ;
}
計數問題(數字dp)
給定兩個整數 a 和 b,求 a 和 b 之間的所有數字中0 9的出現次數。例如,a 1024,b 1032,則 a 和 b 之間共有9個數如下 1024 1025 1026 1027 1028 1029 1030 1031 1032 其中 0 出現10次,1 出現10次,2 出現7次,3 出現3次...
數字DP 計數問題
題目鏈結 第一次做真的很難,總之十分耗費時間。include include include using namespace std const int n 10 get前面字首部分的數值,即前面字首總方案數 intget vector int num,int l,int r 字尾有幾位就是十的幾次...
演算法題 數字dp 計數問題(Python
給定兩個整數 a 和 b,求 a 和 b 之間的所有數字中0 9的出現次數。例如,a 1024,b 1032,則 a 和 b 之間共有9個數如下 1024 1025 1026 1027 1028 1029 1030 1031 1032 其中 0 出現10次,1 出現10次,2 出現7次,3 出現3次...