广告
返回顶部
首页 > 资讯 > 后端开发 > 其他教程 >C语言取模取整的深入理解
  • 544
分享到

C语言取模取整的深入理解

2024-04-02 19:04:59 544人浏览 八月长安
摘要

目录一:四大取整  1.1、 0向取整1.2、  -∞取整( 地板取整)1.3、 +∞取整1.4、 四舍五入取整1.5、 例子汇总二:取模

一:四大取整  

1.1、 0向取整

看代码:

#include <stdio.h>
int main()
{
	//本质是向0取整
	int i = -2.9;
	int j = 2.9;
	printf("%d\n", i); //结果是:-2
	printf("%d\n", j); //结果是:2
    printf("%d %d\n", 5 / 2, -5 / 2);  // 2 -2
	return 0;
}

C中默认0向取整,画图解释0向取整:

 C语言当中有一个trunc函数,运用的也是0向取整。注意引用头文件#include<math.h>.示例如下:

#include <stdio.h>
#include<math.h>
int main()
{
	int i = -2.9;
	int j = 2.9;
	printf("%d\n", i); //结果是:-2
	printf("%d\n", j); //结果是:2
	printf("%d\n", (int)trunc(2.9)); //结果是:2 //结果是:-2
	printf("%d\n", (int)trunc(-2.9));//结果是:-2
	return 0;
}

1.2、  -∞取整( 地板取整)

其实运用的是floor函数,跟上述trunc一样引用#include<math.h>

看代码:

#include<stdio.h>
#include<math.h>
int main()
{
	printf("%.1f\n", floor(-2.9)); // -3.0
	printf("%.1f\n", floor(-2.1)); // -3.0
	printf("%.1f\n", floor(2.9));  // 2.0
	printf("%.1f\n", floor(2.1));  // 2.0
	return 0;
}

画图解释-∞取整

1.3、 +∞取整

运用的是ceil函数,同样需要#include<math.h>

看代码:

#include<stdio.h>
#include<math.h>
int main()
{
	printf("%.1f\n", ceil(-2.9));  // -2.0
	printf("%.1f\n", ceil(-2.1));  // -2.0
	printf("%.1f\n", ceil(2.9));   // 3.0
	printf("%.1f\n", ceil(2.1));   // 3.0
	return 0;
}

画图解释+∞取整:

1.4、 四舍五入取整

运用的是round函数,同样需要#include<math.h>

看代码:

#include<stdio.h>
#include<math.h>
int main()
{
	printf("%.1f\n", round(-2.9)); // -3.0
	printf("%.1f\n", round(-2.1)); // -2.0
	printf("%.1f\n", round(2.9));  // 3.0
	printf("%.1f\n", round(2.1));  // 2.0
}

1.5、 例子汇总

#include <stdio.h>
#include <math.h>
int main()
{
	const char* fORMat = "%.1f \t%.1f \t%.1f \t%.1f \t%.1f\n";
	printf("value\tround\tfloor\tceil\ttrunc\n");
	printf("-----\t-----\t-----\t----\t-----\n");
	printf(format, 2.3, round(2.3), floor(2.3), ceil(2.3), trunc(2.3));
	printf(format, 3.8, round(3.8), floor(3.8), ceil(3.8), trunc(3.8));
	printf(format, 5.5, round(5.5), floor(5.5), ceil(5.5), trunc(5.5));
	printf(format, -2.3, round(-2.3), floor(-2.3), ceil(-2.3), trunc(-2.3));
	printf(format, -3.8, round(-3.8), floor(-3.8), ceil(-3.8), trunc(-3.8));
	printf(format, -5.5, round(-5.5), floor(-5.5), ceil(-5.5), trunc(-5.5));
	return 0;
}

 结论:

浮点数(整数/整数),是有很多的取整方式的。

二:取模 / 取余

2.1、 概念

如果a和d是两个自然数,d非零,可以证明存在两个唯一的整数 q 和 r,满足 a = q*d + r 且0 ≤ r < d。其中,q 被称为商,r 被称为余数。

2.2、 示例(C和Python

#include <stdio.h>
int main()
{
	int a = 10;
	int d = 3;
	printf("%d\n", a % d); //结果是1
	//因为:a=10,d=3,q=3,r=1 0<=r<d(3)
	//所以:a = q*d+r -> 10=3*3+1
 
	int m = -10;
	int n = 3;
	printf("%d\n", m / n); //C语言中是-3,很好理解
	printf("%d\n", m % n); //C语言是-1
 
	return 0;
}

C语言中,我们对-10/3=-3以及-10%3=-1很好理解,没有争议

而在Python中,-10/3竟然=-4,而-10%3竟然=2

为什么呢?

结论:很显然,上面关于取模的定义,并不能满足语言上的取模运算

解析:

因为在C中,现在-10%3出现了负数,根据定义:满足 a = q*d + r 且0 ≤ r < d,C语言中的余数,是不满足定义的, 因为,r<0了。

故,大家对取模有了一个修订版的定义: 如果a和d是两个自然数,d非零,可以证明存在两个唯一的整数 q 和 r,满足 a = q*d + r , q 为整数,且0 ≤ |r| < |d|。其中,q 被称为商,r 被称为余数。

有了这个新的定义,那么C中或者Python中的“取模”,就都能解释了。

解释C: -10 = (-3) * 3 + (-1)

解释Python:-10 = (?)* 3 + 2,其中,可以推到出来,'?'必须是-4(后面验证).即-10 = (-4)* 3 + 2,才能 满足定义。

所以,在不同语言,同一个计算表达式,负数“取模”结果是不同的。我们可以称之为分别叫做正余数 和 负余数

是什么决定了这种现象?

由上面的例子可以看出,具体余数r的大小,本质是取决于商q的。

而商,又取决谁呢?取决于除法计算的时候,取整规则。

2.3、 取余和取模一样吗?

细心的同学,应该看到了,我上面的取模都是带着""的。说明这两个并不能严格等价(虽然大部分情况差不多) 取余或者取模,都应该要算出商,然后才能得出余数。

本质 1 取整:

取余:尽可能让商,进行向0取整。

取模:尽可能让商,向-∞方向取整。

故:

C中%,本质其实是取余。

Python中%,本质其实是取模。

理解链:

对任何一个大于0的数,对其进行0向取整和-∞取整,取整方向是一致的。故取模等价于取余 对任何一个小于0的数,对其进行0向取整和-∞取整,取整方向是相反的。故取模不等价于取余

同符号数据相除,得到的商,一定是正数(正数vs正整数),即大于0! 故,在对其商进行取整的时候,取模等价于取余。

本质 2 符号:

参与取余的两个数据,如果同符号,取模等价于取余

2.4、 计算数据同符号

看代码:

#include <stdio.h>
int main()
{
	printf("%d\n", 10 / 3);  // 3
	printf("%d\n\n", 10 % 3);// 1
	printf("%d\n", -10 / -3); // 3
	printf("%d\n\n", -10 % -3); // -1
	return 0;
}

在Python中,我们发现运行结果和上述一样。

结论:通过对比试验,更加验证了,参与取余的两个数据,如果同符号,取模等价于取余

2.5、 计算数据不同符号

看代码:

#include <stdio.h>
int main()
{
	printf("%d\n", -10 / 3); //结果:-3
	printf("%d\n\n", -10 % 3); //结果:-1 为什么? -10=(-3)*3+(-1)
	printf("%d\n", 10 / -3); //结果:-3
	printf("%d\n\n", 10 % -3); //结果:1 为什么?10=(-3)*(-3)+1
	return 0;
}

而在Python中,结果却不是这样的。

明显结论:如果不同符号,余数的求法,参考之前定义。而余数符号,与被除数相同。

为什么呢?

重新看看定义:如果a和d是两个自然数,d非零,可以证明存在两个唯一的整数 q 和 r,满足 a = q*d + r , q 为整数,且0 ≤ |r| < |d|。其中,q 被称为商,r 被称为余数

a = q*d + r 变换成 r = a - q*d 变换成 r = a + (-q*d)

对于:x = y + z,这样的表达式,x的符号 与 |y|、|z|中大的数据一致

而r = a + (-q*d)中,|a| 和 |-q*d|的绝对值谁大,取决于商q的取整方式。

c是向0取整的,也就是q本身的绝对值是减小的。如:

-10/3=-3.333.33 向0取整 -3. a=-10 |10|, -q*d=-(-3)*3=9 |9|

10/-3=-3.333.33 向0取整 -3. a=10 |10|, -q*d=-(-3)*(-3)=-9 |9|

绝对值都变小了

python是向-∞取整的,也就是q本身的绝对值是增大的。

-10/3=-3.333.33 '//'向-∞取整 -4. a=-10 |10|, -q*d=-(-4)*3=12 |12|

10/-3=--3.333.33 '//'向-∞取整 -4. a=10 |10|, -q*d=-(-4)*(-3)=-12 |12|

绝对值都变大了

结论:如果参与取余的两个数据符号不同,在C语言中(或者其他采用向0取整的语言如:C++,Java),余数符号,与被除数 相同。

2.6、 总结

(1)浮点数(或者整数相除),是有很多的取整方式的。

(2)如果a和d是两个自然数,d非零,可以证明存在两个唯一的整数 q 和 r,满足 a = q*d + r , q 为整数,且0 ≤ |r| < |d|。其中,q 被称为商,r 被称为余数。

(3)在不同语言,同一个计算表达式,“取模”结果是不同的。我们可以称之为分别叫做正余数 和 负余数

(4)具体余数r的大小,本质是取决于商q的。而商,又取决于除法计算的时候,取整规则。

(5)取余vs取模: 取余尽可能让商,进行向0取整。取模尽可能让商,向-∞方向取整。

(6)参与取余的两个数据,如果同符号,取模等价于取余

(7)如果参与取余的两个数据符号不同,在C语言中(或者其他采用向0取整的语言如:         c++,Java),余数符号,与被 除数相同。(因为采用的向0取整)

 到此这篇关于C语言取模取整的深入理解的文章就介绍到这了,更多相关C语言取模取整 内容请搜索编程网以前的文章或继续浏览下面的相关文章希望大家以后多多支持编程网!

--结束END--

本文标题: C语言取模取整的深入理解

本文链接: https://www.lsjlt.com/news/162825.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

本篇文章演示代码以及资料文档资料下载

下载Word文档到电脑,方便收藏和打印~

下载Word文档
猜你喜欢
  • C语言取模取整的深入理解
    目录一:四大取整  1.1、 0向取整1.2、  -∞取整( 地板取整)1.3、 +∞取整1.4、 四舍五入取整1.5、 例子汇总二:取模...
    99+
    2022-11-12
  • C语言编程深入理解取整取余取模问题示例分析
    目录1. 取整问题1.0向取整(C语言默认的取整方案)2.地板取整(向负无穷的方向取整)3.天花板取整(向+无穷的方向取整)4.四舍五入取整汇总例子2.取模问题 1.余数的定义2.两...
    99+
    2022-11-12
  • 带你深度走入C语言取整以及4种函数
    目录前言取整⒈trunc - 0向取整⒉floor -地板取整⒊ceil-无穷大取整⒋round-四舍五入总结前言 这篇博客就带大家深度理解以下什么是取整。我提到的&quo...
    99+
    2022-11-13
    C语言取整函数 c语言四舍五入取整 c语言小数取整
  • C语言中四种取整方式,取余/取模运算以及负数取模问题详解
    目录零向取整、负无穷向取整、正无穷向取整、四舍五入取整总结零向取整、负无穷向取整、正无穷向取整、四舍五入取整 如果将一个浮点数赋值给整形,只会保存整数位: 这种取整方式为零向取整...
    99+
    2022-11-12
  • 深入理解C语言的指针
    目录起源进程内存布局栈设置分配方式特点堆分配方式特点堆与栈区别扩展总结起源 之前在知乎上看了一句话,指针是C的精髓,也是初学者的一个坎。换句话说,内存管理是C的精髓,C/C++可以直...
    99+
    2022-11-12
  • c语言取整和取余的方法是什么
    在C语言中,取整和取余可以使用以下方法:1. 取整:使用整除运算符(/)可以得到两个整数相除的商,如果操作数是整数类型,则结果也是整...
    99+
    2023-10-12
    c语言
  • c语言四舍五入取整数怎么表示
    在C语言中,可以使用不同的方法来实现四舍五入取整数的操作。以下是两种常见的方法:1. 使用round函数:round函数是C标准库中...
    99+
    2023-10-12
    c语言
  • 深入理解C语言的new[]和delete[]
    目录1、重载操作符2、new和delete的原理3、new[]和delete[]的原理总结c++的动态内存管理方式和c语言不一样,在c++中使用new和delete来替换c语言中的m...
    99+
    2022-11-12
  • 深入理解Go语言文档中的io/ioutil.ReadAll函数读取完整文件内容
    深入理解Go语言文档中的io/ioutil.ReadAll函数读取完整文件内容,需要具体代码示例在Go语言的标准库中,io/ioutil包提供了一些用于进行文件I/O操作的函数。其中,ReadAll函数被广泛用于读取完整文件内容,并返回一个...
    99+
    2023-11-04
    Go语言 ReadAll io/ioutil
  • c语言深入理解函数的递归
    前言:  首先,递归是什么,递归就是在定义函数时,然后在函数里调用这个函数,通俗讲,就是函数自己调用自己。那么递归的好处是什么呢?它能够将复杂的问题,用少量的代码来表示,增加了代码的...
    99+
    2022-11-13
  • C语言中bool变量的深入理解
    目录前言bool类型变量的大小bool 值与0比较c语言中bool如何输出总结前言 在一些高级语言当中,为了能够完成更好的逻辑判断,因此就有了bool类型,bool类型的变量值只有t...
    99+
    2022-11-12
  • 怎样深入理解C语言的指针
    本篇文章给大家分享的是有关怎样深入理解C语言的指针,小编觉得挺实用的,因此分享给大家学习,希望大家阅读完这篇文章后可以有所收获,话不多说,跟着小编一起来看看吧。起源之前在知乎上看了一句话,指针是C的精髓,也是初学者的一个坎。换句话说,内存管...
    99+
    2023-06-26
  • C语言由浅入深理解指针
    目录1. 相关概念2. 指针的定义方法3. 指针的分类4. 指针和变量的关系5. 指针与数组的关系6. 指针的运算1. 相关概念 操作系统给每个存储单元分配了一个编号,从ox00 0...
    99+
    2022-11-13
  • 深入了解c语言的循环语句
    目录C语言循环语句while循环for循环do......while循环的嵌套总结:C语言循环语句 大多数人都希望自己是体格强健,天资聪慧,多才多艺的人。虽然有时事与愿违,但至少我们...
    99+
    2022-11-12
  • C语言深入探究sizeof与整型数据存储及数据类型取值范围
    目录1.关键字sizeof2.整型数据存储深入3.数据类型取值范围深入1.关键字sizeof sizeof 与 strlen 是我们日常打代码时经常使用到的两个“工具&r...
    99+
    2022-11-13
  • C语言之预处理命令的深入讲解
    c提供的预处理功能有: 宏定义 文件包含 条件编译 为了与其她c语句区分,命令经常以符号“#”开头。 宏定义 #define 标识符 字符串 可以避免反复输入字符串...
    99+
    2022-11-12
  • 深入了解C语言的动态内存管理
    目录一、为什么会存在动态内存二、动态内存函数1.malloc和free2.calloc3.realloc三、动态内存函数常见错误2.对NULL指针进行解引用操作3.使用free释放一...
    99+
    2022-11-13
  • 深入了解C语言栈的创建
    目录栈的结构定义如下:栈的初始化如下:栈元素的输入接口:完整代码如下:运行结果如下:总结栈:是限定仅在表尾进行插入和删除操作的线性表! 栈的结构定义如下: typedef str...
    99+
    2022-11-12
  • C语言深入探究栈的原理
    栈 压栈:栈的插入操作叫做进栈/压栈/入栈,入数据在栈顶。 出栈:栈的删除操作叫做出栈。出数据也在栈顶。 栈的实现 栈的实现一般可以使用数组或者链表实现,相对而言数组的结构实现更优...
    99+
    2022-11-12
  • C语言的动态内存管理的深入了解
    目录一、动态内存分配二、动态内存分配函数1、malloc()2、realloc()3、calloc()三、用free函数释放内存四、迷途指针总结一、动态内存分配 (1)用malloc...
    99+
    2022-11-13
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作