AtCoder Beginner Contest 154

A
签到

B
签到

C签到

D
说实话,题意我没读懂,并且忘了期望是什么东东了。。。。
然后…
对每一个 p i p_i ,它的期望为 ( 1 p i ( 1 + 2 + 3..... + p i ) ) (\tfrac{1}{p_i}(1+2+3.....+p_i)) ,现在让你求子区间为 k k 的期望的最大和值。
那么前缀和搞一下即可。

double sum[N];
int main(){
    int n,m;
    cin >> n >> m;
    for(int i = 1;i <= n;++i){
        int a;
        cin >> a;
        sum[i] = sum[i-1] + (1.0/a)*(a+1)*a/2;
    }
    double  M = -1;
    for(int i = m;i <= n;++i){
        M = max(M,sum[i]-sum[i-m]);
    }
    printf("%.13lf",M);

}

E
来还愿了~~~
题意
给你一个数 N N ,然后让你求 [ 1 , n ] [1,n] 中恰好有 k k 位非0位的数字的个数。
思路:
数位dp模板题。
d p [ p o s ] [ s t a ] dp[pos][sta] 是第pos位,目前非零位为 s t a sta 满足要求的数字的个数。

int dp[120][120];
int a[120];	
int k;
int dfs(int pos,int sta,int lead,int limit){
	if(pos == -1) return sta == k;//最后看是否恰有k为非零位
	if(!lead&&!limit&&dp[pos][sta]!=-1) return dp[pos][sta];
	int up = limit?a[pos]:9;
	int tmp = 0;
	for(int i = 0;i <= up;++i){
		if(lead&&i == 0) tmp += dfs(pos - 1,sta,lead,limit&&i == a[pos]);//注意前导零
		else tmp += dfs(pos-1,sta + (i == 0?0:1),lead&&i == 0,limit&&i == a[pos]);
	}
	if(!limit&&!lead) dp[pos][sta] = tmp;//记录状态
	return tmp;
}
int main(){
	string s;
	cin >> s;

	cin >> k;
	int l = s.size();
	int pos = 0;
	memset(dp,-1,sizeof dp);
	for(int i = l-1;i >= 0;-- i){
		a[pos++] = s[i] - '0';
	}
	cout <<	dfs(pos-1,0,1,1);
}
发布了589 篇原创文章 · 获赞 31 · 访问量 5万+

猜你喜欢

转载自blog.csdn.net/qq_43408238/article/details/104255616