<div dir="ltr">Hello!<div><br></div><div>While testing and reading the implementation of the class Number I found some things that might be cuestionable, some errors and a method that could have been implemented much faster:</div><div><ul><li>In Integer, the <b>sumTo: anInteger </b>method, computes "self+(self+1)+...+anInteger". The problem here is that if self > anInteger this operation does not have sense. For this case, the implementation returns 0 instead of rasing an error. This kind of makes sense, because not adding anything could be thought as 0, nevertheless this is cuestionable. </li><li>Analogously, the <b>productTo: anInteger </b>method, computes self*(self+1)*...*anInteger. Similarly, in this case when self > anInteger, it returns 1 instead of an error. In this case, I don't think there is a direct correlation to think that not multiplying any number should be equal to 1.<br></li><li>A detail, if now we make this change in the method <b>productTo: anInteger</b>, there will be a small problem in the method <b>factorial</b>. This is because what factorial does is <i>"^1 productTo: self"</i> (after checking if self is not negative). So, with this new change, if we make <i>0 factorial</i> it will raise an error, because we would be computing <i>"^1 productTo: 0"</i>, and this would be not defined. Anyway, this can be easily fixed by checking this border case.</li><li>The <b>raisedToInteger: exp modulo: m </b>method<b> </b>in Integer has a very big problem. If we compute, for example, <i>"5 raisedTo: 0 modulo: 0"</i>, this returns 1. This means, that according to Smalltalk, the rest of the division by 0 of 1(=5^0) is equal to 1 (Yes, division by zero!!). I think you can see the problem. This is due the first line of the method, that says <i>"(exp = 0) ifTrue: [^ 1].", </i>does not check anything else. This problem can be easily fixed by checking if m=0 just before.</li><li>Now, if we compute <i>"1 mod: 0" </i>or (worse) <i>"(5 raisedToInteger: 0) mod: 0"</i> it raises an error informing that the division by zero is not defined (exactly what we could expect if we me made <i>"5 raisedTo: 0 modulo: 0"</i>). So, not only we found an error, but also we found a problem of inconsistency in Smalltalk, since for the same calculation we can obtain two differents answers.</li><li>Another detail, in Number there are defined this methods: <b>mod: divisor</b>, <b>rem: divisor</b> y <b>\\ divisor</b>. All of this are thought like some kind of rest in the division. Particularly, the method <b>mod: divisor </b>maps to the mathematical operation of modulo of modular arithmetic. Smalltalk defines this operation in general for every number as modulo, but mathematically this operation should be only be defined for the natual numbers, thus it could be added some check for this. <a href="https://en.wikipedia.org/wiki/Modular_arithmetic" target="_blank" style="font-style:italic"><font color="#000000">"<span style="font-family:sans-serif;font-size:14px">For a positive integer </span><span style="font-feature-settings:"lnum","tnum","kern" 0;font-variant-numeric:lining-nums tabular-nums;font-kerning:none;font-family:"Nimbus Roman No9 L","Times New Roman",Times,serif;font-size:16.52px;line-height:1;white-space:nowrap">n</span><span style="font-family:sans-serif;font-size:14px">, two numbers </span><span style="font-feature-settings:"lnum","tnum","kern" 0;font-variant-numeric:lining-nums tabular-nums;font-kerning:none;font-family:"Nimbus Roman No9 L","Times New Roman",Times,serif;font-size:16.52px;line-height:1;white-space:nowrap">a</span><span style="font-family:sans-serif;font-size:14px"> and </span><span style="font-feature-settings:"lnum","tnum","kern" 0;font-variant-numeric:lining-nums tabular-nums;font-kerning:none;font-family:"Nimbus Roman No9 L","Times New Roman",Times,serif;font-size:16.52px;line-height:1;white-space:nowrap">b</span><span style="font-family:sans-serif;font-size:14px"> are said to be </span><span style="font-family:sans-serif;font-size:14px"><dfn>congruent modulo <span style="font-feature-settings:"lnum","tnum","kern" 0;font-variant-numeric:lining-nums tabular-nums;font-kerning:none;font-family:"Nimbus Roman No9 L","Times New Roman",Times,serif;font-size:16.52px;line-height:1;white-space:nowrap">n ...[]</span></dfn></span>"</font></a></li><li>Last detail, if we compute <i>"0 raisedToInteger: 0"</i> this returns 1. I am not a math expert, but I don't think this operation should be defined if there is not even a consensual answer for this. </li><li>The <b>isPrime </b>method in Integer makes some optimization in order to run the algorithm in O(sqrt(self)) instead of the naive way in O(self). This is very intelligent, but the constant factor of this method can be still improved significantly. I share with you my implementation of <b>isPrimeFast </b>with a small explanation. This implementation runs in general more than 3 times faster than the actual one. I leave you a test that checks the correctness of it as well, and some other tests that check this complexity I mentioned.</li></ul><div>Please let me know what you think.</div><div>Best regards,</div><div>Agustín Sansone<br></div></div></div>