算法竞赛入门知识干货

article/2025/8/29 18:30:19

前言:本篇总结一部分来自刘汝佳老师的《算法竞赛入门经典》,一部分是个人竞赛学习中的一些算法知识点总结,是初学算法走了不弯路一点点积累起来的干货,对刚刚参加竞赛的盆友应该会很有帮助,如有不足请提出

一.程序设计入门

1.”%.1f” 保留小数点后一位

2.整数/整数=整数,浮点数/浮点数=浮点数

3.sqrt(x)=x的算数平方根

4.在算法竞赛中不要使用头文件conio.h,包括getch()、
clrscr()等函数。

5.在算法竞赛中,每行输出均应以回车符结束,包括最后一行。除非特别说明,每行的行首不应有空格,但行末通常可以有多余空格。另外,输出的每两个数或者字符串之间应以单个空格隔开。

6.三位数反转,反转后结果可以用printf函数控制
320→023:

 #include<stdio.h> 
int main() { int n, m; scanf("%d", &n); m = (n%10)*100 + (n/10%10)*10 + (n/100); printf("%03d\n", m); return 0; 
}

320→23:

 #include<stdio.h> 
int main() { int n, m; scanf("%d", &n); m = (n%10)*100 + (n/10%10)*10 + (n/100); printf("%d\n", m); return 0; 
}

7.输出\n:printf("\\\n"); 输出%d:printf("%%d")

8.int整数大小:-2147483648~2147483647,即-2^31~2^31-1

9.long long大小:-2^63~2^63-1 ,注意int输入的格式控制符改为%lld,Windows输入改为%I63d

二.循环结构程序设计

1.不拘一格地使用伪代码来思考和描述算法是一种值得推荐的做法。

2.x四舍五入:floor(x + 0.5); //floor返回不超过x的最大整数

3.浮点运算可能存在误差。在进行浮点数比较时,应考虑到浮点误差。

4.while适用于循环的次数是不确定的,而且n也不是“递增”式的循环。这样的情况

5.计算程序运行时间:printf("Time used = %.2f\n", (double)clock() / CLOCKS_PER_SEC);//在程序结束之前调用此函数,便可获得整个程序的运行时间。这个时间除以 常数CLOCKS_PER_SEC之后得到的值以“秒”为单位。用文件方式读入,要不然会计算键盘输入的时间
可以使用time.h和clock()函数获得程序运行时间。常数
CLOCKS_PER_SEC和操作系统相关,请不要直接使用clock()的返回值,而应总是除以CLOCKS_PER_SEC

6.文件读写操作
文件读入:freopen(“文件地址”,“r”,stdin);
写到文件:freopen(“文件地址”,“w”,stdou);

7.在观察无法找出错误时,可以用“输出中间结果”的方法查错

8.当输入数据个数不定时,且没有限制条件:

while(scanf("%d", &x) == 1) 
{执行操作	
}

直接用键盘停止输入
在Windows下,输入完毕后先按Enter键,再按Ctrl+Z键,最后再按Enter 键,即可结束输入。在Linux下,输入完毕后按Ctrl+D键即可结束输入。

9.变量在未赋值之前的值是不确定的。特别地,它不一定等于0

10.当变量大于其类型最大值是会产生溢出,运行结果会出现#INFO
解决技巧:如1/i*i 溢出 变化成:1/i/i

11.巧妙用输出来控制精确:a精确到c位:printf(“%.*f”,c,a);

三.数组和字符串

1.在算法竞赛中,常常难以精确计算出需要的数组大小,数组一般会声明得稍 大一些。在空间够用的前提下,浪费一点不会有太大影响。

2.比较大的数组应尽量声明在main函数外,否则程序可能无法运行。

3.数组a赋值k个元素到数组b

   #include<string.h>memcpy(b,a,sizeof(类型)* k)

给数组每个元素赋相同初值

  memset(数组名,初值,sizeof(数组名))//常用于初始化或者memset(数组名,初值,sizeof(类型)*大小)
注意:int类型只能赋值0-1

4.字符串数组char s[m][n] 可以用scanf(“%s”,s[i])读取第i个字符串

5.C语言中的字符串是以“\0”结尾的字符数组,可以用strlen(s)返回字符串s中结束标记之前的字符个数。

6.两个数组操作函数

赋值:strcpy(a,b)//b赋值给a
比较:strcmp(a,b)//a>b返回1
连接:strcat(a,b)//返回里连接后字符串

7.头文件include<ctype.h>

  isalnum(a)   测试传入参数是否为为字母或数字,真返回值为非零isalpha(a)   测试传入参数是否为字母,真值返回非零isdigit(a)   测试传入参数是否为数字,真值返回非零

8.如果char 值为正,则是西文字符;如果为负,则是汉字的前一半(这时需要再读一个char)

9 函数的参数和返回值最好是“一等公民”,如int、char或者double等。其他“非 一等公民”作为参数和返回值要复杂一些。如果函数不需要返回值,则返回类型应写成 void。

10.在C语言中,定义结构体的方法为“struct 结构体名称{ 域定义 };”,注意花括号的后面还有一个分号。

11.为了使用方便,往往用“typedef struct { 域定义; }类型名;”的方式定义一个新类型名。这样,就可以像原生数据类型一样使用这个自定义类型。

12.结构体定义

第一种 struct point{int x ;int y};           使用: struct point  a;
第二种 typedef struct{int x;int y}point;     使用:point a;  

13.对复杂的表达式进行化简有时不仅能减少计算量,还能减少甚至避免中间结果溢出

14.“判断一个事物是否具有某一性质”的函数还有一个学术名称——谓词(predicate)
建议把谓词(用来判断某事物是否具有某种特性的函数)命名成is_xxx的形式,返回int值,非0表示真,0表示假。

15.在调用函数调用数组时,参数传递是传递数组的首地址,所以不能用sizeof(a)计算数组的大小,正确做法是在传递数组长度参数n

16.While()输入巧用

While(scanf("%d%d%d",&a,&b,&c)==3){}
//scanf(“%d%d%d”)==3  是判断是否输入完毕和输入的数是否有效while(scanf("%d%d%d",&a,&b,&c)!=EOF){}
//EOF表示结束标志while(getchar()!='\n'){};
//利用回车来巧妙结束循环

17.全局变量要少用

18.strcmp(a,b)函数

比较字符串a,b大小;相等返回0;a>b返回1;a<b返回-1

19.注意:在参加比赛时,千万不要在使用for循环的时候命名变量,可能会因为编译器兼容的原因是编译不通过,直接零分,最好在函数开始就命名

20.在实际问题中,如果利用输出函数来规定输出的小数位数,很可能会因为四舍五入而得不到正确结果,这是可以用这种方法来解决四舍五入

a=(int)(a*100)/100.0;  //防止四舍五入,首先将多余位给切掉,再还原成小数
printf("%.2f\n",a);//注意a*100一定要加括号

四.C++

1.头文件

#include<stdio.h>    →    #include< cstdio >
#include<string.h>   →    #include< cstring >
#include<math.h>     →    include < cmath >	
#include<ctype.h>    →    include< ctype >
#include< iostream >              提供了输入输出流
#include< algorithm >             提供常用算法

2.using namespace std 名称空间(写在函数开头)

3.声明数组: #define maxn 50 → const int maxn=50

4.C++中的数据类型和C语言很接近,最显著的区别是多了一个bool来表示布 尔值,然后用true和false分别表示真和假。虽然仍然可以用int来表示真假,但是用bool可以 让程序更清晰

5.void swap2(int& a, int& b) 如果在参数名之前加一个“&”符号,就表示这个参数按照传引用(byreference)的方式传递,而不是C语言里的传值(by value)方式传递。这样,在函数内改变参数的值,也会修改到函数的实参。

6.C++中的引用就是变量的"别名",它可以在一定程度上代替C中的指针。例如,可以用“传引用”的方式让函数内直接修改实参。

四.小知识

1.数学函数 double ceil(double);
功能:返回大于或者等于指定表达式的最小整数

2.scanf()函数输入字符串时,当读到空格就会停止输入
例如

char a[20] sacnf(%s”,a),输入”I LOVE YOU”最后读入的只有‘I’scanf(%[^\n],a)除了换行符外其他字符全部接收

3.负数的二进制(表示负数的补码)

"-1"转为二进制的过程
第一步:找原码"1"8位二进制表示为00000001
第二步:找原码的反码为11111110
第三步:找补码(反码加一):11111111

4.各输出格式控制代码如下:

    int PrintVal = 9;/*按整型输出,默认右对齐*/printf("%d\n",PrintVal);/*按整型输出,补齐4位的宽度,补齐位为空格,默认右对齐*/printf("%4d\n",PrintVal);/*按整形输出,补齐4位的宽度,补齐位为0,默认右对齐*/printf("%04d\n",PrintVal);/*按16进制输出,默认右对齐*/   printf("%x\n",PrintVal);/*按16进制输出,补齐4位的宽度,补齐位为空格,默认右对齐*/printf("%4x\n",PrintVal);/*按照16进制输出,补齐4位的宽度,补齐位为0,默认右对齐*/printf("%04x\n",PrintVal);/*按8进制输出,默认右对齐*/printf("%o\n",PrintVal);/*按8进制输出,补齐4位的宽度,补齐位为空格,默认右对齐*/printf("%4o\n",PrintVal);/*按照8进制输出,补齐4位的宽度,补齐位为0,默认右对齐*/
printf("%04o\n",PrintVal);

5.等差数列通项,前n项和

   通项:an=a1+(n-1)*d;前n项和:Sn=a1*n+(n(n-1)d)/2;Sn=n(a1+an)/2;

6.等比数列通项,前n项和

通项:  an=a1*q^(n-1);前n项和: 当q=1时       Tn=n*a1;当q!=1时       Tn=a1(1-q^n)/(1-q)      

7.只有以\0结束的字符数组才可以以s%的方式用printf输出,否则输出会 非常奇怪,自己在char数组上构造一个字符串的时候,忘记在末尾加\0可能会导致访问非法内存的错误

8.字符串拼接函数: char* strcat(char *dest,char *source),可以将source字符串拼接到dest后面

9.声明数组全局变量会自动清零,局部变量需要手动清零

10.char a[10]; strlen(a+1)会从第二个数开始数到数组结尾,不要将strlen(a)写在for循环里面,否则循环一次计算一次会大大减低速度,正确做法是保存到变量中;

11.闰年:
满足一下任意一个条件都是闰年
1.年份非整百且能被4整除的为闰年
2.年份能被四百整除的是闰年(闰年二月29天,平年28天,大月31天,小月30天)

判断是否为闰年代码:

 int is_leap_year(int year){if(year%400==0||(year%100!=0&&year%4==0))return 1;elsereturn 0;}

12.蔡基姆拉尔森公式
在这里插入图片描述
13.C语言qsort()排序函数(默认从小到大,从大到小直接对cmp返回值取反)

#include<stdlib>int cmp(const void*a,const void*b)
{
return (*(int*)a-*(int*)b);
}
qsort(起始地址,排序元素个数,sizeof(类型),cmp); 

14.c++排序函数

#include<algorithm>
using namespace std;
sort(a,a+n);如果要从大到小排序则加一个函数
sort(a,a+n;cmp);
bool cmp(int a,int b)
{return a>b;}

21.万能头文件:#include<bits/stdc++.h>

22.round(a)求离a的最近整数

23.常用数学函数(math.h)

1fabs(double x)  求绝对值
(2floor(double x)向下取整  ceil(double x)向上取整
(3pow(double x,double y)x 的y次方
(4sqrt(double)返回算术平方根

24.String二维数组string mp[1005]初始化

for(int i=0;i<n;i++)mp[i].resize(m);//先要个数撑起来for(int i=0;i<n;i++)mp[i].resize(m,t)//会初始化为t值

25.周期性运动通式

 guess(起点,方向,步数){while(步数--){终点=(起点+方向+周期-1)%周期+1}

26.一颗包含有2019个节点的二叉树,最多包含多少个叶节点

各个节点之间的关系:n=n0+n1+n2,为了使叶子结点(n0)最多,必须n1最小即设为0; 有关系n0=n2+1
得到n2=(2019-1)/2=1009,所以n0=1010;

27.用while输入字符串

while(c=getchar())!=EOF&&c!=’\n’){a[len++]=c;
}
注意:c=getchar()必须打包处理

http://chatgpt.dhexx.cn/article/9uRdyiBK.shtml

相关文章

《算法竞赛入门经典》——刘汝佳

“构造性”和“可行性”是计算机学科的两个最根本特征。 比赛的核心是算法 #1 语言篇 编程不是看会的&#xff0c;也不是听会的&#xff0c;而是练会的&#xff0c;所以应尽量在计算机旁阅读书本&#xff0c;以便把书中的程序输入到计算机中进行调试&#xff0c;顺便再做做上机…

ntoskrnl.exe占用大量cpu解决方法

ntoskrnl.exe 计划任务里面结束关于空闲时段内存自检的任务

ntoskrnl.exe占用cpu高

winr -->control 打开控制面板 还是过高&#xff0c;重启即可 转载于:https://my.oschina.net/u/2425353/blog/3081583

Win10开机提示蓝屏错误ntoskrnl.exe怎么修复?

1、下载bluescreenview软件。 2、下载后解压缩&#xff0c;启动就可以查看蓝屏原因了&#xff01;如下图所示 3、发现问题出在ntoskrnl.exe这个文件上&#xff0c;我重新下载这个文件替换也没用&#xff01; 4、继续解决问题&#xff0c;同时按下winX按键&#xff0c;如下图…

计算机反复蓝屏问题--ntoskrnl.exe

最近电脑反反复复地蓝屏吗&#xff0c;尤其是在电脑开机但又没怎么用的情况下。 使用联想电脑管家分析问题 下载了蓝屏分析诊断工具&#xff0c;提取码&#xff1a;5dti 检测出来问题根源是ntoskrnl.exe 解决方案&#xff1a; ① 参考博客1 控制面板----管理工具----任务计…

ntoskrnl.exe蓝屏

win10装完系统后频繁蓝屏,用bluescreen工具检测后,提示ntoskrnl.exe文件导致; 按照以下步骤处理: 1、在开始菜单上单击右键或按下win+x,点击命令提示符(管理员); 2、在命令提示符中输入: chkdsk c: /f 按下回车键,会弹出如下提示: 3、提示:是否计划在下次系统重…

win10一直蓝屏!一直是这个代码,ntoskrnl.exe导致,要废了。。

几个月了&#xff0c;一直都是这样&#xff0c;刚开始的系统1909&#xff0c;中间用过20H2、21H1&#xff0c;一直到现在的22H2&#xff0c;这个蓝屏问题一直没解决&#xff0c;网上的方式都试了&#xff0c;不行&#xff01;重装了几次系统也没解决&#xff0c;从WIN10 专业版…

Windows内核Shellcode获取ntoskrnl.exe基址

使用NASM编译以下汇编代码 BITS 64 ORG 0section .textglobal _start _start:push rbxmov rax,QWORD [gs:0x38]mov rax,QWORD [rax0x4]shr rax,0xcshl rax,0xc _x64_find_nt_walk_page:mov rbx,QWORD [rax]cmp bx,0x5a4dje _foundsub rax,0x1000jmp _x64_find_nt_walk_page _f…

ERROR: Module load completed but symbols could not be loaded for ntoskrnl.exe Loading Kernel Symbols

电脑蓝屏问题ERROR: Module load completed but symbols could not be loaded for ntoskrnl.exe Loading Kernel Symbols 1.先找出蓝屏日志&#xff1a;C:\Windows\Minidumpc 2.此文件记录了蓝屏的具体原因,由于是dmp文件,这里我是用的是windbg工具进行解析,此工具可以在某讯…

ntoskrnl.lib(loadcfg.obj) : error LNK2001: 无法解析的外部符号 ___security_cookie 解决方法

背景 今天编译公司x86驱动的时候发现了如下报错&#xff0c;我也奇怪&#xff0c;为什么会找不到符号 后来发现是因为用的xp的lib。ObRegisterCallbacks最少都是sp1 改为win7\i386,错误变成了 后来在网上找了找&#xff0c;都是一个人写的&#xff0c;被反复的转载&#xff0c…

ntoskrnl.exe导致Win10蓝屏的解决方案(转载)

转自&#xff1a;https://zhuanlan.zhihu.com/p/37619207 下面两个方案都操作了&#xff0c;暂时三天了没有再出现蓝屏&#xff08;之前一两天必然出现一次&#xff09;&#xff0c;具体哪个起作用也不清楚&#xff0c;只要不再蓝屏就好。 我的PC是自己安装的兼容机。起初安装…

win10电脑蓝屏问题 ntoskrnl.exe导致蓝屏

之前两次打都打不开&#xff0c;直接送去重装系统了&#xff0c;文件丢失/软件重装/配置环境真的很崩溃 [2020/04/23] 第三次蓝屏 这次用回形针按了电脑背后的重启按钮&#xff0c;就是一个小圆点&#xff0c;成功重启了。 怕关机又打不开&#xff0c;尝试了如下修复&#xf…

【系统】ntoskrnl.exe导致Win10蓝屏的解决方案

近期公司一台电脑频繁蓝屏&#xff0c;根据经验直接换了内存条&#xff0c;结果还是蓝屏&#xff1b; 没办法&#xff0c;只有查查代码了&#xff0c;下载了bluescreenview&#xff0c;蓝屏代码查看工具&#xff0c;链接如下&#xff1a; https://download.csdn.net/download…

Windows10磁盘占用率100%(ntoskrnl占用资源)导致系统卡顿

欢迎大家关注我的公众号&#xff0c;会不定期更新一些开发与测试的一些技术文章。 电脑从前几天开始总是莫名其妙卡顿&#xff0c;打开任务管理器后发现System一直占用很高&#xff0c; 通过下图所示打开占用系统资源的文件位置 发现是ntoskrnl占用比较多(这是还原后的ntoskrnl…

[电脑故障]ntoskrnl.exe导致DRIVER_POWER_STATE_FAILURE

描述&#xff1a; 用360驱动大师发现查找不到任何驱动。无法正常关机&#xff0c;关机时间长且最终蓝屏&#xff0c;显示DRIVER_POWER_STATE_FAILURE。设备管理器中驱动无法正常启用禁用&#xff0c;会卡死&#xff0c;无法正常卸载&#xff0c;等待时间超级长(但最后还是卸载…

windows服务器system进程cpu占用率高解决方案(ntoskrnl.exe)

之前给客户服务器部署过服务器监控程序&#xff0c;今天收到邮件告警提醒CPU过高&#xff0c;进入监控发现System进程突然升高&#xff0c;这个是系统进程&#xff0c;只查看进程cpu占用率没用&#xff0c;需要去查看System进程里的线程&#xff0c;具体是由那个线程占用CPU比较…

至强服务器装2003系统蓝屏,Windows Server 2008 R2 ntoskrnl.exe 引起蓝屏故障,重新启动...

前不久在HP ProLiant DL360 G6的服务器上面安装了Windows Server 2008 R2,系统一到晚上凌晨就出现蓝屏、重启现象,并且在 C:\Windows\Minidump 目录下面产生一些Dump文件,如下图所示: 后面我用微软的Windbg程序查看了一下系统产生的Dump文件内容,分析一下文件日志,发现内…

windows系统进程System ntoskrnl.exe pid 4占用8080端口

最近发现8080端口被占用了&#xff0c;花了点时间解决了。 原因&#xff1a;被系统的HTTP.sys 占用了 解决方法&#xff1a; winR, 输入regedit&#xff0c;打开注册表&#xff0c; 依次找到 HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\HTTP 将start的值改为4&a…

驱动开发:内核取ntoskrnl模块基地址

模块是程序加载时被动态装载的&#xff0c;模块在装载后其存在于内存中同样存在一个内存基址&#xff0c;当我们需要操作这个模块时&#xff0c;通常第一步就是要得到该模块的内存基址&#xff0c;模块分为用户模块和内核模块&#xff0c;这里的用户模块指的是应用层进程运行后…

解决由于ntoskrnl.exe导致的蓝屏

文章目录 1. 复现问题2. 分析问题3. 解决问题4. 备注 1. 复现问题 之前电脑总是出现蓝屏&#xff0c;如下所示&#xff1a; 起初并没有放在心上&#xff0c;因为重启之后就正常了&#xff0c;但在某天又蓝屏了&#xff0c;如下所示&#xff1a; 在工作的过程中蓝屏很让人心烦&…