南哪 2022-1-types-io
各位好呀,这里是某 CQ!
今天给大家带来 1-types-io 的练习题单~
根据 types-io 的题目,我们可以看出,这章主要是考察各位同学对变量类型的把控并使用变量类型及四则运算以及 math.h
库中的一些函数来解决较为实际的问题,所以这次我们主要的关注点是变量类型以及一些要注意的点。
首先先来列一下常见的变量类型:
int Num_int;
long long Num_long_long;
float Num_float;
double Num_double;
char ch;
bool flag;
// 注意,这里是随便命名,并不是某种标准的命名法,请不要参考!
int
类型:
int
类型被称为 32 位带符号整数,它是用 32
个二进制位来表示的整数,同时,它的最高位用来表示符号,如果该位是 1 则这个数是负数。所以 int
类型真正用来表示数据大小的只有 31 位,这也就直接决定了 int
类型能表示的范围是 -2147483648 ~ 2147483647
,也就是2的31次方减去1
提示
之所以负数能到 -2147483648,是因为在计算机中,负数是以补码的形式存储的,也就是把正数的二进制取反再加 1,所以 -2147483648 的补码就是 0,所以它实际上就是 0
如果你确定不会出现负数,而且你想追求更大一些的表示范围的话,你可以使用 unsigned int
来充分利用这 32 位,即使它不再能表示负数。
int
类型在 scanf
和 printf
里面的表示是%d
unsigned int
类型在 scanf
和 printf
里面的表示是%u
long long
类型:
和 int
实际上一样,只不过人家是 64 位的,比 int
大得多。
也有 unsigned long long
,很好用
long long
类型在 scanf
和 printf
里面的表示是 %lld
unsigned long long
在 scanf
和 printf
里面的表示是 %llu
关于整型变量的补充:
其实在大部分情况下,大家需要用到的还是整型变量,所以在此某 CQ 希望给出更多的一些小技巧。
关于存储空间:
大家可能知道,也可能不知道,二进制的 8 个位成一个字节,也就是 1 Byte,或者 1 B,而 1024 B = 1 KB,而 1024 KB = 1 MB
当我们在做题的时候,会看到题目给定的时空限制。
当我们思考一道题如何去做的时候,也不要忘了去算一算自己到底用掉了多少空间,或者花去了多少的时间(最简单的方式是以1亿次循环为标准,超出即危险),以避免空间超限和时间超限的问题。
当然,当你拿不到完全分的时候,使用超时的算法拿部分分未尝不可。
关于溢出:
整型变量的溢出实际上比较好控制,当你超过一个整形变量能够表示的范围时,它会从它能表示范围的另一端重新开始,比如一个 int
变量存了 2147483647,加上 1 就变成了 -2147483648
注意
实际上,溢出是未定义行为
,它的具体表现取决于编译器,所以你最好还是不要去尝试溢出,除非你非常清楚你自己在做什么。
float
类型:
float
类型被称为单精度浮点数,能被用来表示小数,但是表示的精度有限。
float
类型在 scanf
和 printf
里面的表示是 %f
double
类型:
double
类型被称为双精度浮点数,是我们常用的小数变量类型,能表示更多的小数位。
double
类型在scanf和printf里面的表示是%lf
一些注意点:
math.h
库中的函数实际上大多数的实现都是基于 double
的,使用 float
可能会出现一些精度上的问题
printf
输出的一些奇技淫巧在此并不赘述。
char
类型:
char
类型表示一个字符,ascii 码里面实际上并没有多少东西,所以实际上一个 char
变量只有 8 位,也就是 1 个字节,最多只能表示到 255,在答疑中发现有人尝试用字符存大于 255 的数字,这个是值得注意的。
char
类型在 scanf
和 printf
里面的表示是 %c
一些注意点:
可能不少同学去记'0'、'a'、'A'的ascii值,实际上是没有必要的,比如你可以使用'0'来直接表示字符0代表的值,C语言是认识这些东西的。
注意
当你 scanf
一个字符的时候,它是紧接着向后读一个字符,没错,这意味着换行符和空格也包括在内,使用时需要特别注意。
bool
类型:
bool
类型只有两种状态:0 或者 1,需要用到 stdbool.h
的库
因为存储空间占用至少是 1 B,所以 bool
类型硬生生占了1B的内存,虽然它实际上只有1bit。
提示
至少占用 1 Byte 的内存空间是因为 C 语言的变量存储是对齐的,也就是内存地址是 8 的整数倍,所以 bool 类型实际上也会占用 1 Byte 的内存空间。
bool
类型因为较 int
占用内存更加少而常被用在一些判断中。以及地图障碍的记录。
关于 getchar()
和 putchar()
:
这俩货其实根本没必要知道,和 scanf%c
还有 printf%c
实际上是一样的
提示
但是它们更快。😉
关于 enum
:
枚举类型实际上也是 int
,但可以为这个变量的特定值附上特定的名字,可以用来很方便地表示一些固定的值,比如一周的星期几,一年中的月份,等等。
比如:
enum week {
Monday = 0,
Tuesday,
Wednesday,
Thursday,
Friday,
Saturday,
Sunday
};
这样,我们就可以使用 Monday
来表示星期一,使用 Tuesday
来表示星期二……
提示
枚举类型默认从 0 开始,你也可以为某个特定的枚举指定值,如不指定,则它的值为前一个枚举的取值 +1
关于 typedef
:
typedef
可以用来给一个类型起一个新的名字,比如:
typedef int integer;
这样,我们就可以使用 integer
来表示 int
类型了。
关于 math.h
常见的数学函数,比如开根 sqrt
,立方根 cbrt
,乘方 pow
,对数 log
,绝对值 abs
,这些,如果想用,除了自己写,就只能借助这个库了,当然,每个函数都有属于它自己的坑(比如 pow
难以接受负数),在使用之前,最好先查清楚怎么用。
写出更好看的代码格式(非常重要):
一种好的代码格式,能让你的程序看上去更加清晰,检查起来好检查,也许也可以让你更有耐心地去Debug,而且别人看了至少也会觉着蛮清爽的。
下面来举一个某 CQ 喜欢的代码格式:
#include <stdio.h>
long long solve(long long year, long long month, long long day) {
long long a = (14ll - month) / 12ll;
long long y = year + 4800ll - a;
long long m = month + 12ll * a - 3ll;
return day + ((153ll * m + 2ll) / 5ll) + 365ll * y + y / 4ll - y / 100ll + y / 400ll - 32045;
}
int main(int argc, char *argv[]) {
long long year, month, day;
scanf("%lld%lld%lld", year, month, day);
printf("%lld\n", solve(year, month, day));
return 0;
}
写出这样的代码具体改变了什么呢?
- 控制好语句块的缩进
对于附属于某一语句(比如 int main()
、以及之后要学到的 for
、if
等)的内容,我们需要相对于原来的语句额外缩进一个 Tab,而不是和原来那句并排写,那样只会导致更大的混乱。
灵活运用 Tab 制表符来让你的程序变得更美观,比如:
int numA,
numA;
char ch;
long long ans;
- 语句块之间可以适当空行
虽然 C 语言中空行并不会影响程序,但是适当的空行可以让你的程序看起来区分步骤更加明显
- 多加空格
大家可能会问:加空格干什么用呢?
空格能让你的不少算式看上去更加分散,易于分辨哪个是哪个,同时也可以使算式看上去更加易于理解。
比如说上面那个长式子,给大家拿出来对比一下:
long long ans = day + ((153ll * m + 2ll) / 5ll) + 365ll * y + y / 4ll - y / 100ll + y / 400ll - 32045;
long long ans=day+((153ll*m+2ll)/5ll)+365ll*y+y/4ll-y/100ll+y/400ll-32045;
区别非常明显,某 CQ 表示第二行代码根本不想看。
另外某 CQ 想要提醒下各位同学,每道题有条件可把之前的代码清空了重写,这样可以更快地提高打字速度。
某 CQ 知道各位同学已经学过了if和for还有while,但某 CQ 还是建议同学们使用当周的知识点解决问题。
1-types-io就这些,其它内容个人根据需求自己看。
题单链接: