Arithmetic of Bomb Accepts: 1050 Submissions: 1762
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)
Problem Description
衆所周知,度度熊非常喜歡數字。
它最近在學習小學算術,第一次發現這個世界上居然存在兩位數,三位數……甚至N位數!
但是這回的算術題可並不簡單,由於含有表示bomb的#號,度度熊稱之爲 Arithmetic of Bomb。
Bomb Number中的bomb,也就是#號,會展開一些數字,這會導致最終展開的數字超出了度度熊所能理解的範疇。比如”(1)#(3)”表示”1”出現了3次,將會被展開爲”111”,
同理,”(12)#(2)4(2)#(3)”將會被展開爲”12124222”。
爲了方便理解,下面給出了Bomb Number的BNF表示。
請將Bomb Number中所有的#號展開,由於數字可能很長,結果對 1 000 000 007 取模。
Input
第一行爲T,表示輸入數據組數。
每組數據包含一個Bomb Expression。
1≤T≤100
1≤length(Bomb Number)≤1000
Output
對每組數據輸出表達式的結果,結果對 1 000 000 007 取模。
Sample Input
4
1
(1)#(3)
(12)#(2)4(2)#(3)
(12)#(5)
Sample Output
1
111
12124222
212121205
題解:模擬就行了。。。
代碼:
#include<iostream>
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<vector>
#include<queue>
#include<set>
#include<algorithm>
#include<map>
#include<math.h>
using namespace std;
typedef long long int ll;
typedef pair<int,int>pa;
const int N=1e5+100;
const int mod=1e9+7;
const ll INF=1e18;
int read()
{
int x=0;
char ch = getchar();
while('0'>ch||ch>'9')ch=getchar();
while('0'<=ch&&ch<='9')
{
x=(x<<3)+(x<<1)+ch-'0';
ch=getchar();
}
return x;
}
/***********************************************************/
int t;
char str[10000];
string ans,zhi;
int main()
{
scanf("%d",&t);
while(t--)
{
int cnt=0;
scanf("%s",str);
int sz=strlen(str);
ll c=0;
bool flag=false;
ans.clear();
for(int i=0; i<sz; i++)
{
if(str[i]=='(')
{
if(flag)
{
int j=i;
while(str[++j]!=')')
{
c=c*10+str[j]-'0';
}
i=j;
for(ll k=1;k<=c;k++)
{
ans+=zhi;
}
zhi.clear();
c=0;
flag=false;
}
else
{
int j=i;
while(str[++j]!=')')
{
zhi+=str[j];
}
i=j;
}
}
else if(str[i]=='#')
{
flag=true;
}
else
{
ans+=str[i];
}
}
int l=ans.length();
ll ok=0;
for(int i=0;i<l;i++)
{
ok=(ok*10+ans[i]-'0')%mod;
}
printf("%I64d\n",ok);
}
}
Pokémon GO Accepts: 738 Submissions: 1725
Time Limit: 3000/1500 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)
Problem Description
衆所周知,度度熊最近沉迷於 Pokémon GO。
今天它決定要抓住所有的精靈球!
爲了不讓度度熊失望,精靈球已經被事先放置在一個2*N的格子上,每一個格子上都有一個精靈球。度度熊可以選擇任意一個格子開始遊戲,抓捕格子上的精靈球,然後移動到一個相鄰的至少有一個公共點的格子上繼續抓捕。例如,(2, 2) 的相鄰格子有(1, 1), (2, 1) 和 (1, 2) 等等。
現在度度熊希望知道將所有精靈球都抓到並且步數最少的方案數目。兩個方案被認爲是不同,當且僅當兩個方案至少有一步所在的格子是不同的。
Input
第一行爲T,表示輸入數據組數。
每組數據包含一個數N。
●1≤T≤100
●1≤N≤10000
Output
對每組數據輸出方案數目,結果對 1 000 000 007 取模。
Sample Input
3
1
2
3
Sample Output
Copy
2
24
96
題解:原題。
代碼:
#include<iostream>
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<vector>
#include<queue>
#include<set>
#include<algorithm>
#include<map>
#include<math.h>
using namespace std;
typedef long long int ll;
typedef pair<int,int>pa;
const int N=1e5+100;
const int mod=1e9+7;
const ll INF=1e18;
int read()
{
int x=0;
char ch = getchar();
while('0'>ch||ch>'9')ch=getchar();
while('0'<=ch&&ch<='9')
{
x=(x<<3)+(x<<1)+ch-'0';
ch=getchar();
}
return x;
}
/***********************************************************/
ll a[N];
ll b[N];
ll c;
int n,t;
void init()
{
b[1]=1;
for (int i=2; i<=10000; i++)
{
b[i]=(b[i-1]*2%mod);
b[i]%=mod;
}
a[1]=1;
a[2]=6;
for (int i=3; i<=10000; i++)
{
a[i]=(2*a[i-1]+b[i]+4*a[i-2])%mod;
}
}
void slove()
{
c=4*a[n];
for (int i=2; i<n; i++)
{
c=(c+(8*b[n-i]*a[i-1]%mod)%mod+(8*a[n-i]*b[i-1])%mod)%mod;
}
printf("%I64d\n",c);
}
int main()
{
init();
scanf("%d",&t);
while(t--)
{
scanf("%d",&n);
if(n==1) puts("2");
else slove();
}
return 0;
}
Valley Numer Accepts: 548 Submissions: 1125
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)
Problem Description
衆所周知,度度熊非常喜歡數字。
它最近發明了一種新的數字:Valley Number,像山谷一樣的數字。
當一個數字,從左到右依次看過去數字沒有出現先遞增接着遞減的“山峯”現象,就被稱作 Valley Number。它可以遞增,也可以遞減,還可以先遞減再遞增。在遞增或遞減的過程中可以出現相等的情況。
比如,1,10,12,212,32122都是 Valley Number。
121,12331,21212則不是。
度度熊想知道不大於N的Valley Number數有多少。
注意,前導0是不合法的。
Input
第一行爲T,表示輸入數據組數。
每組數據包含一個數N。
● 1≤T≤200
● 1≤length(N)≤100
Output
對每組數據輸出不大於N的Valley Number個數,結果對 1 000 000 007 取模。
Sample Input
3
3
14
120
Sample Output
Copy
3
14
119
題解:數位dp,設dp[i][j][k]表示當前位,前一位爲j,前面是否爲遞增。
然後轉移一下就行。
代碼:
#include<iostream>
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<vector>
#include<queue>
#include<set>
#include<algorithm>
#include<map>
#include<math.h>
using namespace std;
typedef long long int ll;
typedef pair<int,int>pa;
const int N=1e5+100;
const int mod=1e9+7;
const ll INF=1e18;
int read()
{
int x=0;
char ch = getchar();
while('0'>ch||ch>'9')ch=getchar();
while('0'<=ch&&ch<='9')
{
x=(x<<3)+(x<<1)+ch-'0';
ch=getchar();
}
return x;
}
/***********************************************************/
int t;
char str[110];
int a[110];
ll dp[110][11][2];
ll dfs(int pos,int zhi,int sta ,bool limit,bool lead)
{
if(pos==-1) return 1;
if(!limit&&dp[pos][zhi][sta]!=-1&&!lead)
return dp[pos][zhi][sta];
ll ans=0;
int up=limit?a[pos]:9;
for(int i=0;i<=up;i++)
{
if(lead)
{
if(i==0)
ans+=dfs(pos-1,0,0,limit&&i==a[pos],true);
else
ans+=dfs(pos-1,i,0,limit&&i==a[pos],false);
}
else
{
if(sta==1)
{
if(i>=zhi)
ans+=dfs(pos-1,i,1,limit&&i==a[pos],false);
}
else
{
ans+=dfs(pos-1,i,i>zhi,limit&&i==a[pos],false);
}
}
}
ans=ans%mod;
if(!limit&&!lead)
dp[pos][zhi][sta]=ans;
return ans;
}
ll solve()
{
int pos=0;
int sz=strlen(str);
for(int i=sz-1;i>=0;i--)
{
a[pos++]=str[i]-'0';
}
return dfs(pos-1,0,0,true,true)%mod;
}
int main()
{
scanf("%d",&t);
memset(dp,-1,sizeof(dp));
while(t--)
{
scanf("%s",str);
printf("%I64d\n",(solve()-1+mod)%mod);
}
}