Skip to content

Commit a0b6c52

Browse files
Dev: Added algorithm to find the nth number in the Sylvester Sequence (#6613)
Added algorithm to find the nth number in the SylvesterSequence
1 parent 6d51709 commit a0b6c52

File tree

2 files changed

+101
-0
lines changed

2 files changed

+101
-0
lines changed
Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,50 @@
1+
package com.thealgorithms.recursion;
2+
3+
import java.math.BigInteger;
4+
5+
/**
6+
* A utility class for calculating numbers in Sylvester's sequence.
7+
*
8+
* <p>Sylvester's sequence is a sequence of integers where each term is calculated
9+
* using the formula:
10+
* <pre>
11+
* a(n) = a(n-1) * (a(n-1) - 1) + 1
12+
* </pre>
13+
* with the first term being 2.
14+
*
15+
* <p>This class is final and cannot be instantiated.
16+
*
17+
* @see <a href="https://en.wikipedia.org/wiki/Sylvester_sequence">Wikipedia: Sylvester sequence</a>
18+
*/
19+
public final class SylvesterSequence {
20+
21+
// Private constructor to prevent instantiation
22+
private SylvesterSequence() {
23+
}
24+
25+
/**
26+
* Calculates the nth number in Sylvester's sequence.
27+
*
28+
* <p>The sequence is defined recursively, with the first term being 2:
29+
* <pre>
30+
* a(1) = 2
31+
* a(n) = a(n-1) * (a(n-1) - 1) + 1 for n > 1
32+
* </pre>
33+
*
34+
* @param n the position in the sequence (must be greater than 0)
35+
* @return the nth number in Sylvester's sequence
36+
* @throws IllegalArgumentException if n is less than or equal to 0
37+
*/
38+
public static BigInteger sylvester(int n) {
39+
if (n <= 0) {
40+
throw new IllegalArgumentException("sylvester() does not accept negative numbers or zero.");
41+
}
42+
if (n == 1) {
43+
return BigInteger.valueOf(2);
44+
} else {
45+
BigInteger prev = sylvester(n - 1);
46+
// Sylvester sequence formula: a(n) = a(n-1) * (a(n-1) - 1) + 1
47+
return prev.multiply(prev.subtract(BigInteger.ONE)).add(BigInteger.ONE);
48+
}
49+
}
50+
}
Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,51 @@
1+
package com.thealgorithms.recursion;
2+
3+
import static org.junit.jupiter.api.Assertions.assertEquals;
4+
import static org.junit.jupiter.api.Assertions.assertNotNull;
5+
import static org.junit.jupiter.api.Assertions.assertThrows;
6+
import static org.junit.jupiter.api.Assertions.assertTrue;
7+
8+
import java.math.BigInteger;
9+
import java.util.stream.Stream;
10+
import org.junit.jupiter.api.Test;
11+
import org.junit.jupiter.params.ParameterizedTest;
12+
import org.junit.jupiter.params.provider.MethodSource;
13+
import org.junit.jupiter.params.provider.ValueSource;
14+
15+
class SylvesterSequenceTest {
16+
17+
/**
18+
* Provides test cases for valid Sylvester sequence numbers.
19+
* Format: { n, expectedValue }
20+
*/
21+
static Stream<Object[]> validSylvesterNumbers() {
22+
return Stream.of(new Object[] {1, BigInteger.valueOf(2)}, new Object[] {2, BigInteger.valueOf(3)}, new Object[] {3, BigInteger.valueOf(7)}, new Object[] {4, BigInteger.valueOf(43)}, new Object[] {5, BigInteger.valueOf(1807)}, new Object[] {6, new BigInteger("3263443")},
23+
new Object[] {7, new BigInteger("10650056950807")}, new Object[] {8, new BigInteger("113423713055421844361000443")});
24+
}
25+
26+
@ParameterizedTest
27+
@MethodSource("validSylvesterNumbers")
28+
void testSylvesterValidNumbers(int n, BigInteger expected) {
29+
assertEquals(expected, SylvesterSequence.sylvester(n), "Sylvester sequence value mismatch for n=" + n);
30+
}
31+
32+
/**
33+
* Test edge case for n <= 0 which should throw IllegalArgumentException
34+
*/
35+
@ParameterizedTest
36+
@ValueSource(ints = {0, -1, -10, -100})
37+
void testSylvesterInvalidZero(int n) {
38+
assertThrows(IllegalArgumentException.class, () -> SylvesterSequence.sylvester(n));
39+
}
40+
41+
/**
42+
* Test a larger number to ensure no overflow occurs.
43+
*/
44+
@Test
45+
void testSylvesterLargeNumber() {
46+
int n = 10;
47+
BigInteger result = SylvesterSequence.sylvester(n);
48+
assertNotNull(result);
49+
assertTrue(result.compareTo(BigInteger.ZERO) > 0, "Result should be positive");
50+
}
51+
}

0 commit comments

Comments
 (0)