Skip to content

Commit 1608d75

Browse files
authored
Improve collatz_sequence algorithm (TheAlgorithms#1726)
- Add more doctests and type checking to make sure only natural numbers are used - Simplified the algorithm slightly This new verison is also between 10-15% faster for really long sequences
1 parent e7041a8 commit 1608d75

File tree

1 file changed

+24
-10
lines changed

1 file changed

+24
-10
lines changed

maths/collatz_sequence.py

+24-10
Original file line numberDiff line numberDiff line change
@@ -1,19 +1,33 @@
1-
def collatz_sequence(n):
1+
from typing import List
2+
3+
4+
def collatz_sequence(n: int) -> List[int]:
25
"""
3-
Collatz conjecture: start with any positive integer n.Next term is obtained from the previous term as follows:
4-
if the previous term is even, the next term is one half of the previous term.
5-
If the previous term is odd, the next term is 3 times the previous term plus 1.
6-
The conjecture states the sequence will always reach 1 regaardless of starting value n.
6+
Collatz conjecture: start with any positive integer n. The next term is
7+
obtained as follows:
8+
If n term is even, the next term is: n / 2 .
9+
If n is odd, the next term is: 3 * n + 1.
10+
11+
The conjecture states the sequence will always reach 1 for any starting value n.
712
Example:
13+
>>> collatz_sequence(2.1)
14+
Traceback (most recent call last):
15+
...
16+
Exception: Sequence only defined for natural numbers
17+
>>> collatz_sequence(0)
18+
Traceback (most recent call last):
19+
...
20+
Exception: Sequence only defined for natural numbers
821
>>> collatz_sequence(43)
922
[43, 130, 65, 196, 98, 49, 148, 74, 37, 112, 56, 28, 14, 7, 22, 11, 34, 17, 52, 26, 13, 40, 20, 10, 5, 16, 8, 4, 2, 1]
1023
"""
24+
25+
if not isinstance(n, int) or n < 1:
26+
raise Exception("Sequence only defined for natural numbers")
27+
1128
sequence = [n]
1229
while n != 1:
13-
if n % 2 == 0: # even number condition
14-
n //= 2
15-
else:
16-
n = 3 * n + 1
30+
n = 3 * n + 1 if n & 1 else n // 2
1731
sequence.append(n)
1832
return sequence
1933

@@ -22,7 +36,7 @@ def main():
2236
n = 43
2337
sequence = collatz_sequence(n)
2438
print(sequence)
25-
print("collatz sequence from %d took %d steps." % (n, len(sequence)))
39+
print(f"collatz sequence from {n} took {len(sequence)} steps.")
2640

2741

2842
if __name__ == "__main__":

0 commit comments

Comments
 (0)