Codeforces Round #110 (Div. 2)

A Game Outcome

题意

福尔摩斯和华生在一个n * n的棋盘上玩添数游戏。在游戏期间,他们放置一些数到棋盘上,(其中的规则我们不知道)。然而,现在游戏结束了,棋盘中都有一个数字。要知道谁赢,他们需要计算获胜方块的数量。如果要确定特定的方块是否获胜,你需要做到以下几点。分别计算出这个方块所在的纵列上所有数的和(包括自身)和计算出这个方块所在的横列上所有数的和(包括自身)。如果纵列的和大于横列的和,那么这个方块就算一个获胜方块。 如图所示,真是一个结束的棋局。 然后,紫色格子获胜,因为其纵列之和(8+3+6+7=24)大于其横列(9+5+3+2=19)之和,以及24>1924>1924>19。

输入格式

第一行包含一个整数n(1<=n<=30)。 接下来n行,每行n个数,每个数用空格隔开。第i行上的第j个数字表示棋盘上地i行第j列方格上的数字。棋盘上所有数字大于等于1,小于等于100。

输出格式

输出一个数字——获胜方块的数量。

在这里插入图片描述

反思

水题,注意行列求值的时候的下标位置!!!

题意

如果纵列的和大于横列的和,那么这个方块就算一个获胜方块,问有多少个横纵方块

题解

直接模拟

Code

#include <iostream>
#include <cstdio>

using namespace std;

int n;
int a[35][35];

int main(){
    cin >> n;
    for(int i = 1; i <= n; i++){
        for(int j = 1; j <= n; j++){
            cin >> a[i][j];
        }
    }
    
    int ans = 0;
    
    for(int i = 1; i <= n; i++){
        for(int j = 1; j <= n; j++){
            int summ_h = 0;
            int summ_l = 0;
            
            for(int k = 1; k <= n; k++)
                summ_l += a[k][j];
                
            for(int k = 1; k <= n; k++)
                summ_h += a[i][k];
                
            if(summ_l > summ_h) ans++;
        }
    }
    
    cout << ans;
    
    return 0;
}

B Trace

题目描述

一天,夏洛克·福尔摩斯正在跟踪一个重要罪犯时,他在墙上发现了一张美妙的画。这个墙可以被表示成一个平面,墙上有许多同心圆,将平面分成了若干块。除此之外,相邻的两个部分被交错填上了红色和蓝色。其中在所有圆外的部分被填了蓝色。夏洛克想知道红色部分的面积是多少。 输入格式

第一行包含一个整数 n(1≤n≤100)。

第二行包含 n 个整数 ri(1≤ri≤1000),表示每个圆的半径。保证每个圆大小不同。 输出格式

输出一行一个实数,表示红色部分的面积。如果你的答案和标准答案的绝对或相对误差小于 10−4 就被认为正确。 样例 样例输入 1

1 1

样例输出 1

3.1415926536

样例解释 1

只有一个半径为 1 的圆,红色部分是这个圆的内部,面积为 π。 样例输入 2

3 1 4 2

样例输出 2

40.8407044967

样例解释 2

所有圆的外侧为蓝色,第二个第三个圆中间是红色,第一第三个圆中间是蓝色,第一圆内是红色。总面积为 (π×42−π×22)+π×12=12π+π=13π

反思

交替相减!!!

题解

就是求两个圆之间的面积

Code

// Problem: B. Trace
// Contest: Codeforces - Codeforces Round #110 (Div. 2)
// URL: https://codeforces.com/problemset/problem/157/B
// Memory Limit: 256 MB
// Time Limit: 2000 ms
// Code by: ING__
// 
// Powered by CP Editor (https://cpeditor.org)

#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cstring>

using namespace std;

int n;
int r[1010];

const double pi = 3.1415926536;

int main(){
	cin >> n;
	for(int i = 1; i <= n; i++){
		cin >> r[i];
	}
	
	sort(r + 1, r + 1 + n);
	
	double ans = 0;
	
	for(int i = n; i >= 1; i -= 2){
		ans += r[i] * r[i] - r[i - 1] * r[i - 1];
	}
	
	printf("%.10lf", ans * pi);
	
	return 0;
}

C Message

Dr. Moriarty is about to send a message to Sherlock Holmes. He has a string s .

String pp is called a substring of string s if you can read it starting from some position in the string s . For example, string “aba” has six substrings: “a”, “b”, “a”, “ab”, “ba”, “aba”.

Dr. Moriarty plans to take string ss and cut out some substring from it, let’s call it t . Then he needs to change the substring t zero or more times. As a result, he should obtain a fixed string u (which is the string that should be sent to Sherlock Holmes). One change is defined as making one of the following actions:

  • Insert one letter to any end of the string.
  • Delete one letter from any end of the string.
  • Change one letter into any other one.

Moriarty is very smart and after he chooses some substring t , he always makes the minimal number of changes to obtain u .

Help Moriarty choose the best substring t from all substrings of the string s . The substring t should minimize the number of changes Moriarty should make to obtain the string u from it.

反思

简单dp,注意方程

题解

我们可以通过求出来a与b之间最长的子串长度是多少,通过匹配子串长度,我们就能清楚的知道,两个字符串匹配的最长长度是多少

只要知道了最长长度,从b变为a无论是删或者替换来构造出来a

加是没有意义的,因为如果要加一个字符来构造为a的子串,不如删掉或者替换

那么我们怎么来求最长的匹配的子串长度呢

dp数组定义为:a的前i个字母和b的前j个字母匹配的长度是多少

那么转移方程就是: f ( i , j ) = m a x ( f [ i − 1 ] [ j − 1 ] , f [ i − 1 ] [ j − 1 ] + ( a [ i ] = = b [ j ] ) ) f(i,j) = max(f[i - 1][j - 1], f[i-1][j-1]+(a[i] == b[j])) f(i,j)=max(f[i1][j1],f[i1][j1]+(a[i]==b[j]))

Code

// Problem: A. Message
// Contest: Codeforces - Codeforces Round #110 (Div. 1)
// URL: https://codeforces.com/problemset/problem/156/A
// Memory Limit: 256 MB
// Time Limit: 2000 ms
// Code by: ING__
// 
// Powered by CP Editor (https://cpeditor.org)

#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cstring>

using namespace std;

char a[2010];
char b[2010];
int f[2010][2010];

int main(){
	scanf("%s", a + 1);
	scanf("%s", b + 1);
	
	int la = strlen(a + 1);
	int lb = strlen(b + 1);
	
	int ans = 0;
	
	for(int i = 1; i <= la; i++){
		for(int j = 1; j <= lb; j++){
			if(a[i] == b[j]) f[i][j] = f[i - 1][j - 1] + 1;
			else f[i][j] = f[i - 1][j - 1];
			ans = max(ans, f[i][j]);
		}
	}
	
	cout << lb - ans;
}

s = 0;

for(int i = 1; i <= la; i++){
	for(int j = 1; j <= lb; j++){
		if(a[i] == b[j]) f[i][j] = f[i - 1][j - 1] + 1;
		else f[i][j] = f[i - 1][j - 1];
		ans = max(ans, f[i][j]);
	}
}

cout << lb - ans;

}


  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值