Skip to content

Commit a3a8df0

Browse files
authored
Updating tests and proof solution for palindrome-products (#2599)
1 parent a0862fe commit a3a8df0

File tree

4 files changed

+63
-89
lines changed

4 files changed

+63
-89
lines changed

exercises/practice/palindrome-products/.meta/config.json

+2
Original file line numberDiff line numberDiff line change
@@ -3,8 +3,10 @@
33
"contributors": [
44
"ankorGH",
55
"cmccandless",
6+
"Cool-Katt",
67
"draalger",
78
"ErikSchierboom",
9+
"jagdish-15",
810
"javaeeeee",
911
"kytrinyx",
1012
"matthewmorgan",
Original file line numberDiff line numberDiff line change
@@ -1,88 +1,38 @@
1-
const reverseString = (str) => str.split('').reverse().join('');
2-
3-
class Palindrome {
4-
constructor(factor1, factor2) {
5-
this.value = factor1 * factor2;
6-
this.factors = [[factor1, factor2]];
7-
}
8-
9-
withFactors(factors) {
10-
this.factors.push(factors);
11-
return this;
12-
}
13-
14-
valid() {
15-
const s = `${this.value}`;
16-
return s === reverseString(s);
17-
}
18-
19-
merge(other) {
20-
other.factors.forEach((f) => {
21-
this.factors.push(f);
22-
});
23-
return this;
24-
}
25-
}
26-
271
export class Palindromes {
28-
constructor(maxFactor, minFactor = 1) {
29-
this.maxFactor = maxFactor;
30-
this.minFactor = minFactor;
31-
}
32-
33-
get largest() {
34-
let left = this.maxFactor,
35-
right = this.maxFactor,
36-
best = new Palindrome(this.minFactor, this.minFactor);
37-
38-
while (right >= this.minFactor) {
39-
let p = new Palindrome(left, right);
40-
41-
if (best.value && p.value < best.value) {
42-
right--;
43-
left = right;
44-
continue;
45-
}
46-
47-
if (p.valid()) {
48-
if (best.value < p.value) {
49-
best = p;
50-
} else if (best.value === p.value) {
51-
best = p.merge(best);
2+
static generate({ minFactor, maxFactor }) {
3+
if (minFactor > maxFactor) throw new Error('min must be <= max');
4+
let isPalindrome = (n) =>
5+
[...n.toString()].reverse().join('') === n.toString();
6+
let search = (n, pred, fn) => {
7+
while (pred(n)) {
8+
if (!isPalindrome(n)) {
9+
n = fn(n);
10+
continue;
5211
}
53-
}
54-
55-
if (left <= this.minFactor) {
56-
right--;
57-
left = right;
58-
} else {
59-
left--;
60-
}
61-
}
62-
63-
if (best.valid()) {
64-
return best;
65-
}
66-
67-
return { value: null, factors: [] };
68-
}
69-
70-
get smallest() {
71-
for (let m = this.minFactor; m <= this.maxFactor; m += 1) {
72-
for (let n = m; n <= this.maxFactor; n += 1) {
73-
const p = new Palindrome(m, n);
74-
if (p.valid()) {
75-
return p;
12+
let factors = [];
13+
for (let p = minFactor; p <= n / p; p++) {
14+
if (n % p === 0) {
15+
let q = n / p;
16+
if (q <= maxFactor) factors.push([p, q]);
17+
}
7618
}
19+
if (factors.length > 0) return { value: n, factors };
20+
n = fn(n);
7721
}
78-
}
79-
return { value: null, factors: [] };
80-
}
81-
82-
static generate(params) {
83-
if ((params.minFactor || 1) > params.maxFactor) {
84-
throw new Error('min must be <= max');
85-
}
86-
return new Palindromes(params.maxFactor, params.minFactor || 1);
22+
return { value: null, factors: [] };
23+
};
24+
let [lower, upper] = [minFactor * minFactor, maxFactor * maxFactor];
25+
return {
26+
largest: search(
27+
upper,
28+
(n) => n >= lower,
29+
(x) => x - 1,
30+
),
31+
smallest: search(
32+
lower,
33+
(n) => n <= upper,
34+
(x) => x + 1,
35+
),
36+
};
8737
}
8838
}

exercises/practice/palindrome-products/.meta/tests.toml

+17-7
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,19 @@
1-
# This is an auto-generated file. Regular comments will be removed when this
2-
# file is regenerated. Regenerating will not touch any manually added keys,
3-
# so comments can be added in a "comment" key.
1+
# This is an auto-generated file.
2+
#
3+
# Regenerating this file via `configlet sync` will:
4+
# - Recreate every `description` key/value pair
5+
# - Recreate every `reimplements` key/value pair, where they exist in problem-specifications
6+
# - Remove any `include = true` key/value pair (an omitted `include` key implies inclusion)
7+
# - Preserve any other key/value pair
8+
#
9+
# As user-added comments (using the # character) will be removed when this file
10+
# is regenerated, comments can be added via a `comment` key.
411

512
[5cff78fe-cf02-459d-85c2-ce584679f887]
6-
description = "finds the smallest palindrome from single digit factors"
13+
description = "find the smallest palindrome from single digit factors"
714

815
[0853f82c-5fc4-44ae-be38-fadb2cced92d]
9-
description = "finds the largest palindrome from single digit factors"
16+
description = "find the largest palindrome from single digit factors"
1017

1118
[66c3b496-bdec-4103-9129-3fcb5a9063e1]
1219
description = "find the smallest palindrome from double digit factors"
@@ -15,13 +22,13 @@ description = "find the smallest palindrome from double digit factors"
1522
description = "find the largest palindrome from double digit factors"
1623

1724
[cecb5a35-46d1-4666-9719-fa2c3af7499d]
18-
description = "find smallest palindrome from triple digit factors"
25+
description = "find the smallest palindrome from triple digit factors"
1926

2027
[edab43e1-c35f-4ea3-8c55-2f31dddd92e5]
2128
description = "find the largest palindrome from triple digit factors"
2229

2330
[4f802b5a-9d74-4026-a70f-b53ff9234e4e]
24-
description = "find smallest palindrome from four digit factors"
31+
description = "find the smallest palindrome from four digit factors"
2532

2633
[787525e0-a5f9-40f3-8cb2-23b52cf5d0be]
2734
description = "find the largest palindrome from four digit factors"
@@ -37,3 +44,6 @@ description = "error result for smallest if min is more than max"
3744

3845
[eeeb5bff-3f47-4b1e-892f-05829277bd74]
3946
description = "error result for largest if min is more than max"
47+
48+
[16481711-26c4-42e0-9180-e2e4e8b29c23]
49+
description = "smallest product does not use the smallest factor"

exercises/practice/palindrome-products/palindrome-products.spec.js

+12
Original file line numberDiff line numberDiff line change
@@ -135,6 +135,18 @@ describe('Palindromes', () => {
135135
});
136136
});
137137

138+
xtest('smallest product does not use the smallest factor', () => {
139+
const palindromes = Palindromes.generate({
140+
maxFactor: 4000,
141+
minFactor: 3215,
142+
});
143+
const smallest = palindromes.smallest;
144+
const expected = { value: 10988901, factors: [[3297, 3333]] };
145+
146+
expect(smallest.value).toEqual(expected.value);
147+
expect(sortFactors(smallest.factors)).toEqual(expected.factors);
148+
});
149+
138150
function sortFactors(factors) {
139151
return factors.map((f) => f.sort()).sort();
140152
}

0 commit comments

Comments
 (0)