开发语言
金创想
这个作者很懒,什么都没留下…
展开
-
scanf、printf函数对字符串的各种搞法
scanf("%s", s)”和“scanf("%d", &n)”类似,它会读入一个不含空格、TAB和回车符的字符串,存入字符数组s。注意,不是“scanf("%s", &s)”,s前面没有“&”符号,因为s本身就指向了内存地址。如果是字符串数组chars[maxn] [maxl],可以用“scanf("%s", s[i])”读取第i个字符串。原创 2024-05-09 17:33:30 · 131 阅读 · 0 评论 -
字符串的赋值
虽然看上去是将整个字符串赋给了数组,其实就是一种赋值方式的简化,本质上还是把一个个字符存入数组。和数组一样天生低人一等,给字符串变量赋值时,只有初始化时才可以使用“=”,之后均需使用strcpy()函数。因为字符串本质上就是数组,因此它的赋值也具有数组的特点:只能在初始化时用等号。原创 2024-05-08 16:55:12 · 167 阅读 · 0 评论 -
移位运算符的数学应用
如果你左移一个无符号整数,并且移动的位数超过了该整数类型可以表示的位数,那么结果将是未定义的(在大多数情况下,这会导致“环绕”行为,即最高位被丢弃,最低位被新位填充)。如果你左移一个有符号整数,并且移动的位数超过了该整数类型可以表示的位数减1(因为符号位通常占用一位),那么结果也是未定义的。规定实际移动的次数是移动次数和32的余数,也就是移位33次和移位1次得到的结果相同。移动long型的数值时,规定实际移动的次数是移动次数和64的余数,也就是 移动66次和移动2次得到的结果相同。原创 2024-05-07 17:55:58 · 313 阅读 · 0 评论 -
移位运算符的优先级
比如在二进制中,8位最大整数就是8个1,即2^8-1,用左移运算符“<<”写出来就是(1<<8)-1。,因为“<<”运算符的优先级没有减法高,括号是必需的。移位运算符分为左移<<、右移>>,它属于位操作符,即在二进制位级别上进行操作的运算符。5个双目位操作符的优先级顺序为:左移<<、右移>>→按位与&→按位异或^→按位或|。位操作符除了一个单目运算符(按位取反运算符~)外,优先级都低于加减运算符。左移n位就相当于乘以2的n次方,右移n位相当于除以2的n次方。原创 2024-05-07 17:52:11 · 240 阅读 · 0 评论 -
光速转换八进制、十六进制
想必各位也看出来了,0、0x、0X的选配版本关键在于#,它是一个标志符,表示要输出另一种版本。这个“另一种版本”是已经定义好的,只有一种选配。借助于printf函数,可以瞬间输出一个整数的八进制、十六进制。该函数还贴心地提供了带有0、0x、0X前缀的选配版本。甚至还能指定十六进制的6个专属字母的大小写。原创 2024-05-06 16:27:42 · 132 阅读 · 0 评论 -
打印浮点数的格式说明符
①3表示输出的总宽度(包括整数部分、小数点和小数部分,小数点算1位),如果整个浮点数的宽度小于这个数,那么它会在左侧用空格填充。如果整个浮点数的宽度大于这个数,那么它会原样输出,不会被截断。②.1 表示小数点保留1位小数,它会自动四舍五入。原创 2024-04-30 12:56:15 · 132 阅读 · 0 评论 -
字符的表示方法
不过,有一些字符直接表示出来并不方便,需要用转义序列(EscapeSequence)表示(以反斜线开头的字符)。为了方便书写,C语言允许用直接的方法表示字符,例如,“a”代表的就是a的ASCII码。每一个字符都有一个整数编码,称为ASCII码。如A的ASCII码值为65。空字符:“\0”,它也是C语言中字符串的结束标志。反斜线: “\\”(注意必须有两个反斜线)、双引号: “\"”和“"”都表示双引号。单引号:“\'”(这个是单引号),.直接用字符或转义字符表示。原创 2024-04-25 16:49:30 · 101 阅读 · 0 评论 -
memset函数的特别之处
注意,由于memset 是按字节操作的,所以它适合初始化char型,不适合初始化多字节的数据类型(如 int、float、double等),除非是将它们都初始化为0(这其实是memset的常用用法,因为所有字节都初始化为0,不管数据类型是几个字节的它也都是0)。memset的功能是以字节为单位初始化一块连续的内存空间(一般用于数组),将其所有字节都设置为特定的值。c 是要填充的值,虽然参数类型是 int,但实际上只有该值的低 8 位(一个字节)会被用来填充内存。str 是指向要填充的内存块的指针。原创 2024-04-24 14:17:17 · 173 阅读 · 0 评论 -
字符类型判断库函数合集
控制字符是那些用于控制文本流而非直接表示可打印字符的字符,其ASCII范围:0x00-0x1F和 0x7F(0-31和127)。常见的控制字符为:退格、水平制表符、换行键、回车键、删除。空白字符有6个:空格(' ')、水平制表符('\t')、换行符('\n')、回车符('\r')、垂直制表符('\v')和换页符('\f')。可打印字符是那些可以在文本中显示并且具有实际意义的字符,它比图形字符多了一个空格(' ')。isspace检查一个字符是否是空白字符(white-space character)。原创 2024-04-23 20:46:50 · 480 阅读 · 0 评论 -
“转义字符”知多少
①\xxx:其中 xxx 是1到3位八进制数,表示一个字符的八进制ASCII码。(注:八进制数通常以0开头,但在转义序列中,开头的0是可选的。在C语言中,以反斜杠 \ 开头,后面跟一个或多个字符,可用于表示这些不容易直接表示的字符。例如,\x41 也表示字符 'A'。有一些不容易直接表示的字符,最典型的是“换行符”,要表示这样的字符就需要用到“转义字符”。要明白,字符指的是单个的文字或符号,而序列是指一系列字符,因而\n确实不是字符。也就是说,严格来讲,\叫“转义字符”,而\n叫“转义序列”。原创 2024-04-22 17:03:14 · 121 阅读 · 0 评论 -
字符指针数组
在这个例子中,string_array是一个字符指针数组,包含8个元素,每个元素都是一个指向字符的指针,这些指针分别指向了8个不同的字符串字面量。字符指针数组(Character Pointer Array)是一个数组,其元素是指向字符的指针,通常用于存储字符串的地址。字符指针数组常用于存储一组字符串,每个字符串的地址作为数组的一个元素。原创 2024-04-21 16:41:12 · 73 阅读 · 0 评论 -
深度剖析“字符串与数组、指针”的关系
字符串的本质是数组,数组的本质是占用连续内存单元的多个变量(每个内存单元大小相同,就像把一整板豆腐切成大小相同的小块,每一块可看成一个内存单元,每个内存单元存储着一个变量——数组元素)。:因为是直接将字符串的首地址赋给指针,这里的字符串会被当作字符串常量,存储在程序的只读数据段(也称为文本段或代码段)中,因此用这种方式初化始后字符串是不能改变的。在C语言中,字符串是以字符数组的形式存储的。:这是用数组的方式初始化,字符串存储在程序的可写数据段(如堆或栈)中,因此你可以修改str数组中的字符。原创 2024-04-21 16:31:45 · 664 阅读 · 0 评论 -
常量数组的用法
相比普通数组,常量数组的优点在于性能更优:常量数组通常存储在程序的只读数据段中,由于其内容不会改变,编译器或运行时系统可能对其进行优化,从而提高访问速度并减少内存使用。输入对应数组的下标(索引),输出对应数组的元素。查找表(Lookup Table,简称LUT)是一种高效的数据结构,它通过预先存储输入到输出的映射关系,可以实现快速查找。下标对数组元素的映射关系可以是灵活的,比如可以很容易地通过上面的常量数组求出某月份前1个月的天数。比如在游戏中,通过常量数组可以设置难度等级对应的参数,比如敌人的血量。原创 2024-04-17 22:21:19 · 359 阅读 · 0 评论 -
strlen有多长?
字符数组s的大小是10,并不是所有空间都用上了。赋值“hello”实际保存了6个字符(还有一个结束标记“\0”),但有效字符只有“hello”这5个,因此strlen(s)返回的是5(不包含“\0”)。函数strlen(s)的作用是获取字符串s的实际长度。就是有效字符的个数。原创 2024-04-15 15:10:37 · 137 阅读 · 0 评论 -
C语言数组的初始化方法大全
请注意,memset通常不适用于将非字节大小的值(如int, float, double等)初始化为非零值,因为它按字节填充,可能会导致未定义的行为。对于静态数组(全局数组或在函数之外的数组)和静态存储期的局部数组,如果没有明确初始化,它们会被自动初始化为0。这通常用于将数组初始化为0或其他重复值(如果数据类型允许)。只给数组的前面一部分元素赋值,剩余的元素会被自动初始化为0(对于基本数据类型)。:C99标准引入了指定初始化器,允许你初始化数组的特定元素。在声明数组的同时给出数组所有元素的值。原创 2024-04-14 22:12:32 · 269 阅读 · 0 评论 -
定义数组的注意事项
这个问题咱们在“数组定义在main函数内外的区别”和“定义在mian函数之外的数组的自动初始化”两篇文章中有详细的阐述。作为参加竞赛的同学,只要记得将数组定义在main函数之外就可以了。问题:读入一些整数,按读入顺序的逆序将这些数输出到一行中,中间用空格隔开。已知整数不超过100个。在算法竞赛中,常常难以精确计算出需要的数组大小。数组一般会声明得稍大一些。下标必须是常数,不能是变量。可以用define定义下标。原创 2024-04-13 22:53:33 · 355 阅读 · 0 评论 -
数组名的指针用法
注意相比之前的代码,这时n会多自加1次(因为n++写在while语句的循环条件判断中,当输入CTRL+Z结束时,n++又被执行了1次),所以for循环的初始值应改为n-2。需要特别说明的是,虽然数组名起到指针的作用,但它本质上只是一个常量指针。因为是常量,所以不能改变自己的值,因而改变地址时要用a+n,不能写成a++。因为数组名a起到指向数组首元素的指针的作用,所以可以通过a加上一个自加的n来返回数组各元素的地址,从而将输入的数据直接存入对应的地址中。其实可以直接将输入的数赋给数组,这就需要用到指针。原创 2024-04-12 19:06:08 · 462 阅读 · 0 评论 -
常用变量名合集
数学中通常用x,y来表示坐标,同样的,在命名变量时,可以使用一些具有特定含义的单个字符。prev:previous的简写,表示前一个元素或节点(链表、栈等)。item:表示数据结构中的一个单独元素(列表、数组、集合或队列等)timestamp:时间戳,表示一个特定的时间点或日期时间标记。handle:表示一个指向某种资源、对象或数据结构的引用或指针。i、j、k:常用于循环中的迭代变量,尤其在嵌套循环中。tail:表示数据结构的最后一个节点(链表、队列等)。head:表示数据结构的起始节点(链表、队列等)。原创 2024-04-11 19:18:17 · 585 阅读 · 0 评论 -
数组定义在main函数内外的区别
定义在函数外部的数组分配在静态存储区(static storage area)。因此,这样的数组称“全局数组”,具有全局作用域和静态存储期。定义在函数内部的数组分配在栈区(stack)。因此,这样的数组称“局部数组”,具有局部作用域和自动存储期。栈区相对较小,因此,如果你在main函数或任何其他函数中定义了一个非常大的数组,可能会超出栈的大小限制,导致栈溢出错误。小时候,我们总是习惯先写main函数,然后把变量都写在main函数里面。长大了,我们发现有时候把数组写在main函数内,会直接导致程序异常退出。原创 2024-04-11 16:46:34 · 343 阅读 · 0 评论 -
能否直接比较不同类型的变量?
实际测试这个程序完全能够运行,并且运行结果正确,但在网上查的资料都说这样会导致编译器报错。能否直接判断一个int型变量与double型变量是否相等?老金有点懵,到底可不可以这样呢?原创 2024-04-05 23:15:48 · 83 阅读 · 0 评论 -
数据类型转换形式
显式类型转换,也称为强制类型转换,需要程序员明确指定要转换的目标类型。方法是在值或者变量前加带小括号的数据类型名(如“(int)”),即可将变量转换为指定的数据类型。当double类型的2.0与int类型的3进行除法运算时,编译器会自动将int类型的3转换为double类型,再与2.0进行运算。这很好理解,整型转换为浮点型不会丢失信息,而浮点型转换为整型会丢弃小数部分。注意括号只能加在类型名上,即只能写成(int)d,不能写成int(d)。编译器自动进行的类型转换,常发生在赋值操作或表达式求值时。原创 2024-04-05 23:00:48 · 351 阅读 · 0 评论 -
纯C++设置浮点数精度
当然了,如果在main函数前用了using namespace std;的话,代码中的std::就可以省去了,不过即便是这样,这种语法明显也比C语言麻烦的多。首先需要用到一个专用头文件<iomanip>,还需要用到一个流操作符setprecision,用于设置输出流中浮点数的精度。可见,用setprecision设置精度是包括整数部分的,即它指的是总的有效数字位数。如果你想要保留到小数点后几位,还需要引入另一个小伙伴:fixed。用纯C++语法输出固定位数小数的方法简直不要太麻烦。原创 2024-04-04 23:43:19 · 188 阅读 · 0 评论 -
永远留守在“输入缓冲区”里的孩子
(2)第2次执行for循环:当scanf从输入缓冲区读取完男生人数42后,再读取到一个类型不匹配的x时,它会把42赋值给male,而不会给fmale重新赋值。(1)第1次执行for循环:程序正常从输入缓冲区读取30 20,故male=30,fmale=20,male_count=30,female_count=20。第一行输入n表示有n个班,然后每行输入两个整数,表示每个班的男生、女生人数,用空格隔开。问题来了,如果在输入人数的过程中,误将整数输入成一个字母或小数,比如像下面这样,会出现什么情况呢?原创 2024-04-02 15:39:04 · 520 阅读 · 0 评论 -
非常绕的“输入结束”信号
那用什么发出“输入结束”信号,之前的文章“用恋爱脑搞懂scanf的返回值”已有介绍,在Windows下,输入完毕后按Enter键,然后按Ctrl+Z键,再按Enter键,即可结束输入。当输入完数据后,按Enter键再按下Ctrl+Z,然后再按下Enter,就会向当前正在执行scanf函数发出“输入结束”信号,当前scanf函数在没有任何有效输入的情况下结束输入。所以,准确地说,Ctrl+Z发出的“输入结束”信号是没有任何输入的“输入结束”信号。循环输入的代码很简单,但是用户的“输入结束”信号是什么呢?原创 2024-04-01 23:10:47 · 542 阅读 · 0 评论 -
字符串的三种输入方法
新标准对这个函数进行了升级,加了个小尾巴,变成gets_s()。不过这个升级版不光造型上狗尾续貂,食用起来也是个鸡肋,因为有些编译器(比如GCC)根本不支持它。因为scanf会将空格识别为输入数据的分隔符,所以用它是不能输入含有空格的字符串的。,它会将其识别为两个字符串,上面的代码结果只会输出Hello。要替代gets(),你不得不把代码写成这样的复杂形式。注意getchar()返回值的类型是int型,它返回的是读取的字符的 ASCII 值。gets()函数的功能是将键盘输入的单行字符串保存到字符数组中。原创 2024-03-30 21:16:54 · 512 阅读 · 0 评论 -
变量,前世你也许是个过客!
当完成寄存的一刹那,老金便和寄存柜的编号绑定了(在完成变量赋值的一刹那,变量也和变量地址绑定了),老金也就有了柜子的使用权(变量有了内存的使用权)。此时,老金这个存包人就是变量,“老金”这个名字自然就是变量名,老金存到柜子里的东西就是变量的值,而柜子的编号就是变量的地址,柜子的大小规格就相当于变量的类型。老金可以随时改变柜子里存放在东西(改变变量的值),只要放得进去(赋值要符合变量的类型),老金随便往里面存什么都可以。在解除绑定关系之前,老金就一直对这个柜子有使用权,它是专属于老金的(这叫变量的生存期)。原创 2024-03-27 16:42:50 · 493 阅读 · 0 评论 -
用恋爱脑搞懂scanf的返回值
显然如果输入完全满足它的要求,就代表成功输入了两个变量,所以返回值是2。如果输入超出2个整数呢,比如9、5、2、7,那也依然满足“依次输入两个整数”,所以后面的值会被忽略掉,依然返回2。在Windows下,输入完毕后按Ctrl+Z键,再按Enter键,即可结束输入。上面的结束输入快捷键是强制性的,一旦输入立即结束输入。注意它是从第一个输入的数据开始依次判断,是整数就计为输入成功,直到遇到不是整数的输入为止。所以,上面说的第2种情况,先输入3,再输入Ctrl+Z也会有同样的输出。但是什么算成功输入呢?原创 2024-03-26 16:21:01 · 300 阅读 · 0 评论 -
异或运算的本质
异或运算是一种二进制运算,在二进制异或运算中,对于每一位,如果两个相应的二进制位相同,则结果为0;如果两个相应的二进制位不同,则结果为1。a、b两个数的第2、3位不同,运算结果取值为1,所以它是保存了两个操作数的差别。根据以上运算规则可知,异或运算的结果其实是保存了两个操作数的差别。原创 2024-03-24 21:37:59 · 240 阅读 · 0 评论 -
找不到北的i++
表达式i++的计算结果是加1前的原始值(规定),所以先返回 i 的原始值,然后改变i的值,将其增加1。先将 i 的值增加1,然后返回表达式++i的计算结果:加1后的值(也是规定)。根据i++“先返后加”的特点,咱们可以明确的计算顺序是①→②,但是③是在②后计算还是在①、②之间计算却没有明确的规定。(2)如果③是在①、②之间计算,先将表达式的值(未加1前的值)赋给i,然后i++,所以i的值会变为i+1。(1)如果③是在②后计算,最终赋给i的是表达式i++的返回值,即未加1前的值。再猜猜下面的代码会输出什么?原创 2024-03-24 21:19:30 · 539 阅读 · 0 评论 -
i++的超高优先级
a= (i++) + (i++)的计算过程:第1个i++返回i加1前的值0,然后i的值加1变为1;第2个i++返回i+1前的值1,然后i的值加1变为2,所以a=0+1=1,i变为2。b=(i++) + (i++)的计算过程:第1个i++返回i加1前的值2,然后i的值加1变为3;第2个i++返回i+1前的值3,然后i的值加1变为4,所以a=2*3=6,i变为4。这里涉及到运算符的优先级问题。因为表达式i++的计算规则是:先返回 i 的当前值,然后将 i 的值加1。猜猜下面的代码会输出什么?原创 2024-03-23 22:22:15 · 115 阅读 · 0 评论 -
C/C++在线参考手册的使用技巧
离线手册下载:https://zh.cppreference.com/w/Cppreference:Archives。以谷歌为例,按下图指示打开浏览器插件安装页面,然后把插件(文件后缀名crx)用鼠标拖到打开后的页面上即可完成安装。cppreference.com是一个在线的C/C++参考手册,是C/C++学习者最常用的网站。安装后只要在浏览器的地址栏输入:cc,再按空格键,然后输入要搜索的关键词就可以了。谷歌浏览器插件因为被限制的原因打不开,可以在百度搜索插件进行安装。(2) 安装插件搜索。原创 2024-03-23 11:09:58 · 430 阅读 · 0 评论 -
信息学奥赛编写代码的注意事项
这不仅不会为程序赢得更高的“界面友好分”,反而会让程序丢掉大量的(甚至所有的)分数——这些提示信息会被当作输出数据的一部分。在一般情况下,你的程序不能直接读取键盘和控制屏幕:不要在算法竞赛中使用getch()、getche()、gotoxy()和clrscr()函数(早期的教材中可能会介绍这些函数),不要使用头文件conio.h。不要让程序“按任意键退出”(例如,调用system("pause"),或者添加一个多余的getchar()),因为不会有人来“按任意键”的。(1)最容易忽略的是输出的格式。原创 2024-03-22 21:56:59 · 259 阅读 · 0 评论 -
明知故犯式学习法
比如: scanf 语句中要输入的变量前要加 & , 你明知应该加 & , 但你也可以不加试试, 看看到 底会发生什么。在学习编程时, “ 明知故犯 ” 是有益的: 起码你知道了错误时的现象。这样, 当真的不小心 犯错时, 可以通过现象猜测到可能的原因。而且, 这多少会引起你的要奇心: 为什么会这样子?原创 2024-03-20 23:53:00 · 99 阅读 · 0 评论 -
逗号操作符的运算规则
逗号表达式的执行过程是从左到右依次计算每个表达式,并将最后一个表达式的结果作为整个逗号表达式的结果(注意这里说的结果不是说某个变量的值,而是整个表达式的返回值)。②计算 b + 3,结果:表达式b+3的返回值为5,但是这个返回值没什么用,因为逗号表达式最终结果取决于最后一个表达式。所以b的值没被改变,b=2。例如,在C语言中,表达式a = (b = 3, b + 4)是一个逗号表达式。③计算a * b,结果:a*b=2*2=4。把此结果作为整个逗号表达式的返回值。③最后b + 4的值赋给a,即a = 7。原创 2024-03-19 20:35:10 · 368 阅读 · 0 评论 -
if-else的配偶,你能找对吗?
B. 有的人活着,绽放生命光彩!A. 有的人死了,他还活着!给大家奉上一道小题。原创 2024-03-16 20:59:24 · 119 阅读 · 0 评论 -
格式规范性知识的探究式学习
1)%.1f\n:可以针对单个元素进行“增删改”,比如这里的“.”是可以去掉试试的,这叫“删”,数字“1”可以改成其他数字,或者删掉,这叫“改/删”,“f”可以再换成“d”试式。也可以组合“增删改”,如“.1”都删掉。这个printf语句分两部分,本身的功能就是格式化输出,因此参数完全是格式化内容。它有两个参数,用逗号格开。2)8.0/5.0:可以改成整数试试,试试改其中一个或两个,也可以试试前面改变%d时用x.0和x时的区别。对于格式规范性这种规定性的知识,可以采用“增删改”的方式进行控究式学习。原创 2024-03-03 21:12:57 · 330 阅读 · 0 评论 -
神经错乱的连赋值
像a=b=c=1、a+=b-=c*= 1这样的连赋值具有极简的形式,因此常用来炫技。但是它也会极难理解,甚至,它还会有精神分裂、神经错乱之时。原创 2024-03-02 20:41:50 · 430 阅读 · 1 评论 -
运算符的优先级和结合性
结合性分为左结合性和右结合性。所谓的左结合就是运算符跟着左边的数字混,比如3*6/2,“/”跟6混,*号跟3混,3前面没有别的运算符了,它就是领头的,所以要从它开始向右算起。这就是为什么左结合性表示从左到右依次计算,而右结合性则从右到左计算。大多数运算符(包括算术运算符、关系运算符等)都是左结合的,但也有一些特殊的运算符,如赋值运算符和条件运算符(?比如乘法和除法优先级相同,我们都知道3*6/2要从左向右计算,这说的就是结合性。每种运算符都有固定的优先级和结合性,它们是用来决定计算顺序的。原创 2024-02-28 16:55:50 · 192 阅读 · 1 评论 -
搞定C语言的“多边关系”
关系运算符的结合性是从左向右的,所以2<=x<=2等同于(2<=x)<=2,故应该先判断2<=x。见证奇迹的时刻到了,无论x取什么值,2<=x的返回值只可能是0或1,不管返回哪一个,都比2小,所以无论用户输入什么值,if语句都会被判定为真。总结一下,在C语言中,类似于1<x<=2,a=b=c=1这样的代码与数学中的意义完全不同,它们完全与不等式组、连等式无关,计算机一律把它们视为多个运算符的混合运算,一律按照优先级和结合性的规则计算。=的优先级相同,>、<、>=、<=的优先级相同,后者高于前者一个等级。原创 2024-02-27 22:28:34 · 477 阅读 · 0 评论