模数和余数不相同



准备好了,您会发现一篇非常花哨的文章,这可能会节省您的采访时间或节省几个小时的生产中的错误!

我正在积极研究《 The Impostor's Guide》的第二季并在撰写有关SSH的RSA密码的文章,这显然是IT历史上下载最多的代码。

我想完全理解这个故事。 谁发明了此代码,如何工作,为什么工作以及将来是否会工作 。 现在我发了一个该死的有趣的故事 。 我不是一个疯子,我确实看到其他人正在吸食这个领域。 但是我对此也很感兴趣,因为到处都有小水貂,就像喜pies一样,我被深水貂中的闪亮物体吸引 。 我也很擅长隐喻。

无论如何:上周我学到了一些奇怪的东西并想分享:事实证明, mod和该部门的其余部分不是同一回事 。 真有趣,有些读者跳出座位大喊大叫:“但这就是我一直试图告诉你和其他所有人的东西!”

从该宗派中召集伙计们称“ mod不是其余的”! 这是给你的。

什么是mod?


我必须对此进行研究,以及上一次此类话题浮出水面。 这是您知道但不记得的事情之一。 使用mod时,将一个数除以另一个,取余数。 因此: 5 mod 2将为1,因为5/2 = 2,其余为1。

术语mod表示运算,在这种情况下使用模块2。 大多数编程语言使用%表示这样的操作: 5 % 2 = 1

那就是我们进入奇怪的灰色区域的地方。

表盘的数学


我记得我在学校教过这个方法,然后忘记了。 有一种数学叫做“模算​​术”,它处理循环结构。 想象这的最简单方法是使用带周期12的表盘。对于数学家来说,表盘是mod 12 。 如果您想了解是否可以将253小时平均划分为几天,则可以应用操作253 mod 24结果将为13 ,因此答案是否定的! 只有结果为0时,我们才能回答yes。

您可以问的另一个问题是:“如果我下午6点离开,那么16小时后几点到达?” 这将是6 + 16 mod 12 ,即10。

密码学家喜欢mod ,因为当使用非常大的数字时,您可以创建称为“单向函数”的东西。 这些特殊功能使您可以轻松地沿一个方向而不是相反的方向进行计算。

如果我告诉您9是平方的结果,则可以轻松确定输入是3。从头到尾看到整个过程。 如果我说9是mod 29的结果,那么将很难理解什么是输入。

密码学家喜欢这个想法,因为他们可以使用带有大素数的余数除法来生成密码密钥。 这是一个完全不同的故事:如果您想阅读它,可以买一本书,或者甚至更好地支持我的努力来编写它

但是,我们不会偏离本主题。

刻度盘的余数和数学


现在,让我们直言不讳:当数字为正数时,模和简单余数相同,但对于负数则不同。

请考虑以下任务:

 const x = 19 % 12; console.log(x); 

x的值是多少? 除以数字,得到7作为12的余数。这是正确的答案。 怎么样:

 const y = 19 % -12; console.log(y); 

使用普通的数学运算,我们可以将-12与-1相乘,得出12,而我们仍然剩下7,所以我们的答案还是7。

JavaScript对此表示赞同:



C#也同意:



Google同意第一条陈述,但不同意第二条:



Ruby同意Google的观点:



以Dijkstra的名义,这是怎么回事?

小时前


要回答这个问题,您需要了解余数模数之间的区别。 程序员将这些操作组合在一起 ,但不应该这样做,因为仅当除数(在我们的例子中为12)为正时,它们才会给出相同的结果。 如果除数为负,则可以轻松地将错误发送到生产环境。

但是为什么会有区别呢? 考虑时钟上的正分频器19 mod 12



最终结果7.我们知道这一点,并且可以进行数学证明。 但是19 mod -12呢? 在这里您需要使用其他手表



该模块为-12,我们不能通过乘以-1来忽略或更改它,因为模数算法不能那样工作。 正确计算结果的唯一方法是重新排列时钟上的标记,以便我们从-12移动或逆时针旋转时钟,从而得到相同的结果。

为什么不以-1开头标签,然后移至-2等? 因为在这种情况下,我们将向后移动并不断减小结果,直到达到-12,这时我们将执行+12的跳转,而取模不会那样工作。

这是著名的东西。


在您称我为疯子并开始谷歌搜索之前, 这是一个众所周知的事实 。 实际上,MDN(Mozilla开发人员网络)甚至还可以调用%余数运算,而不是取模:

余数运算符返回将一个操作数除以另一个的余数。 他总是接受分红的迹象

这是C#众神之一埃里克·利珀特(Eric Lippert) 关于C#中的模数的说法

但是,这根本不是%运算符在C#中实际执行的操作。 %运算符不是规范的模运算符,它是余数运算符。

那你的语言呢?

那又怎样


我能理解您是否已经读完本文,现在挠头并想知道是否值得担心。 我认为这有两个原因:

  1. 我可以想象,这个问题会让我在一次采访中感到惊讶。
  2. 我可以想象这是如何投入生产的,开发人员将在几个小时内找出为什么数学不起作用。

如果您的学徒程序员朋友来了,这也是一个有趣的事实。

Source: https://habr.com/ru/post/zh-CN421071/


All Articles