2023春季期中总结

文章介绍了算法在信息学竞赛中的应用,包括分治策略在解决复杂问题中的作用,前缀和在求和问题上的效率提升,以及二分查找在有序数组搜索中的效率。同时,指出了参赛者在比赛中存在的问题,如速度慢、应用不熟练等,强调了多练习和实践的重要性。
摘要由CSDN通过智能技术生成

在这里插入图片描述

评价:一般~~(超级棒)~~

模拟赛

1. 2023春季基础热身赛 第一场

排名第5,共600分,打了228分
速度慢了一点,没有做完题目,下次要快一点

2. 2023春季基础热身赛 第二场

排名第5,共600分,打了228分
算法的应用不够熟练,要多练习,熟能生巧

3.2023春季基础热身赛 第二场

排名第7,共600分,打了345分
对枚举等的优化不行,搜索题需要加强

4. 2023 年春季信息学普及 ~ 提高 挑战赛 - 中期测试

排名第48,共700分,打了100分
不能学以致用,要多实践

算法

1.分治

分治分治,就是“分而治之”,把一个复杂的问题拆分成两个及以上的问题,再把得到的子问题分解成更小的子问题…直到最后得到的子问题可以直接求解,这就是分治,也是许多高效算法的基础
例题:
南蛮图腾快速幂


2. 前缀和

前缀和可以简单理解为【数列的前 n 项的和】

sum[0]=0;
sum[1]=sum[0]+a[1];
...
sum[i]=sum[i-1]+a[i];

例题:
“非常男女”计划最大子段和


3. 二分

二分查找(英语:binary search),也称折半搜索(英语:half-interval search)、对数搜索(英语:logarithmic search),是用来在一个有序数组中查找某一元素的算法。

拿1—100的猜数字举例,想一个数字,先从50对半猜,如果小于50就继续猜25,如果大于50就猜75,不停的对半猜,二分法也是一样,把问题不停的1分为2这就是二分

注意!!!:二分查找时,所以调用前必须保证元素有序。
二分的模板是:

while(l+1<r){
	int mid=(l+r)/2;
	if(check(mid)){
		l=mid;
	}
	else {
		r=mid;
	}

二分答案
解题的时候往往会考虑枚举答案然后检验枚举的值是否正确。若满足单调性,则满足使用二分法的条件。把这里的枚举换成二分,就变成了「二分答案」

例题:
EKO / 砍树进击的奶牛


4.贪心

贪心算法(英语:greedy algorithm),是用计算机来模拟一个「贪心」的人做出决策的过程。这个人十分贪婪,每一步行动总是按某种指标选取最优的操作。而且他目光短浅,总是只看眼前,并不考虑以后可能造成的影响。

可想而知,并不是所有的时候贪心法都能获得最优解,所以一般使用贪心法的时候,都要确保自己能证明其正确性。

例题:
修改数组凌乱的yyy / 线段覆盖


5.递推

递推算法是一种用若干步可重复运算来描述复杂问题的方法。递推是序列计算中的一种常用算法。通常是通过计算前面的一些项来得出序列中的指定项的值。

以斐波那契数列(1,1,2,3,5,8,13…)为例:

f[1] = 1;
f[2] = 1;
f[3] = f[1] + f[2];
f[4] = f[2] + f[3];
...
f[n] = f[n - 2] + f[n - 1]; 

例题:
禽兽的传染病信封问题(错排)


6.LIS 和 LCS

LIS (Longest Increasing Subsequence的缩写)为最长上升子序列,例如1,2,3,4,5,6,那么最长的上升子序列就是6

LCS(Longest Common Subsequence的缩写),即最长公共子序列。一个序列,如果是两个或多个已知序列的子序列,且是所有子序列中最长的,则为最长公共子序列。LCS不是唯一的,它可以有很多种,例如 <A,B,C,B,D,A,B> 和 <B,D,C,A,B,A> 的最长子序列可以是 <B,C,A,B> 也可以是 <B,C,B,A> ,显然都成立
LIS模板:

#include <bits/stdc++.h>
using namespace std;
const int N = 105, inf = 1e9 + 10;
int a[N], f[N];
int n, ans = -inf;
int main() {
	cin >> n;
	for (int i = 1; i <= n; i ++) {cin >> a[i]; f[i] = 1;}
	for (int i = 1; i <= n; i ++)
		for (int j = 1; j < i; j ++)
			if (a[i] > a[j]) f[i] = max(f[i], f[j] + 1);
	for (int i = 1; i <= n; i ++)
		ans = max(ans, f[i]);
	cout << ans << '\n';
	return 0;
}

LCS模板:

#include <bits/stdc++.h>
#define int long long

using namespace std;
char s1[2333], s2[2333];
int n, m;
int f[2333][2333];
signed main() {
    scanf("%s", s1 + 1);
    n = strlen(s1 + 1);
    scanf("%s", s2 + 1);
    m = strlen(s2 + 1);
    for (int i = 1; i <= n; i++) {
        for (int j = 1; j <= m; j++) {
            if (s1[i] == s2[j])
                f[i][j] = f[i - 1][j - 1] + 1;
            else
                f[i][j] = max(f[i - 1][j], f[i][j - 1]);
        }
    }

    cout << f[n][m];
    return 0;
}

例题:
导弹拦截合唱队形

结尾

不积小流,无以成江海

不积跬步,无以至千里

一步一个脚印,脚踏实地

加油向前冲!!!

加油!在这里插入图片描述

评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值