Skip to content
28 changes: 25 additions & 3 deletions Sprint-1/fix/median.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,9 +6,31 @@
// or 'list' has mixed values (the function is expected to sort only numbers).

function calculateMedian(list) {
const middleIndex = Math.floor(list.length / 2);
const median = list.splice(middleIndex, 1)[0];
return median;
if (!Array.isArray(list)) {
return null;
}

// filter out non-numbers and then sort
const filteredList = list
.filter((item) => typeof item === "number")
.toSorted((a, b) => a - b);

if (filteredList.length === 0) {
return null;
}
// if odd length, just return the middle index
// else return the sum of the two middle indices divided by 2
if (filteredList.length % 2) {
const middleIndex = Math.floor(filteredList.length / 2);
return filteredList[middleIndex];
} else {
const secondIndex = filteredList.length / 2;
const firstIndex = secondIndex - 1;
const median = (filteredList[firstIndex] + filteredList[secondIndex]) / 2;
// console.log(median);
return median;
}
}

calculateMedian([6, -2, 2, 12, 14]);
module.exports = calculateMedian;
22 changes: 17 additions & 5 deletions Sprint-1/fix/median.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,8 @@ describe("calculateMedian", () => {
{ input: [1, 2, 3, 4], expected: 2.5 },
{ input: [1, 2, 3, 4, 5, 6], expected: 3.5 },
].forEach(({ input, expected }) =>
it(`returns the median for [${input}]`, () => expect(calculateMedian(input)).toEqual(expected))
it(`returns the median for [${input}]`, () =>
expect(calculateMedian(input)).toEqual(expected))
);

[
Expand All @@ -24,7 +25,8 @@ describe("calculateMedian", () => {
{ input: [110, 20, 0], expected: 20 },
{ input: [6, -2, 2, 12, 14], expected: 6 },
].forEach(({ input, expected }) =>
it(`returns the correct median for unsorted array [${input}]`, () => expect(calculateMedian(input)).toEqual(expected))
it(`returns the correct median for unsorted array [${input}]`, () =>
expect(calculateMedian(input)).toEqual(expected))
);

it("doesn't modify the input array [3, 1, 2]", () => {
Expand All @@ -33,8 +35,17 @@ describe("calculateMedian", () => {
expect(list).toEqual([3, 1, 2]);
});

[ 'not an array', 123, null, undefined, {}, [], ["apple", null, undefined] ].forEach(val =>
it(`returns null for non-numeric array (${val})`, () => expect(calculateMedian(val)).toBe(null))
[
"not an array",
123,
null,
undefined,
{},
[],
["apple", null, undefined],
].forEach((val) =>
it(`returns null for non-numeric array (${val})`, () =>
expect(calculateMedian(val)).toBe(null))
);

[
Expand All @@ -45,6 +56,7 @@ describe("calculateMedian", () => {
{ input: [3, "apple", 1, null, 2, undefined, 4], expected: 2.5 },
{ input: ["banana", 5, 3, "apple", 1, 4, 2], expected: 3 },
].forEach(({ input, expected }) =>
it(`filters out non-numeric values and calculates the median for [${input}]`, () => expect(calculateMedian(input)).toEqual(expected))
it(`filters out non-numeric values and calculates the median for [${input}]`, () =>
expect(calculateMedian(input)).toEqual(expected))
);
});
17 changes: 16 additions & 1 deletion Sprint-1/implement/dedupe.js
Original file line number Diff line number Diff line change
@@ -1 +1,16 @@
function dedupe() {}
function dedupe(arr) {
const placeholder = [];

if (arr.length === 0) {
return arr;
}

arr.forEach((element) => {
if (!placeholder.includes(element)) {
placeholder.push(element);
}
});

return placeholder;
}
module.exports = dedupe;
18 changes: 16 additions & 2 deletions Sprint-1/implement/dedupe.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,13 +16,27 @@ E.g. dedupe([1, 2, 1]) returns [1, 2]
// Given an empty array
// When passed to the dedupe function
// Then it should return an empty array
test.todo("given an empty array, it returns an empty array");
test("given empty array, returns empty array", () => {
expect(dedupe([])).toEqual([]);
});

// Given an array with no duplicates
// When passed to the dedupe function
// Then it should return a copy of the original array
test("array with no duplicates returns copy of original", () => {
expect(dedupe([1, 3, 4])).toEqual([1, 3, 4]);
});

// Given an array of strings or numbers
// When passed to the dedupe function
// Then it should return a new array with duplicates removed while preserving the
// Then it should return a new array with duplicates removed while preserving the
// first occurrence of each element from the original array.
test("removes duplicates, while preserving first occurrance of each element", () => {
expect(dedupe([1, 3, 3, "as", "as", "df"])).toEqual([1, 3, "as", "df"]);
});

// Given an array where all elements are the same
// When passed to the dedupe function
// Then it should return an array with that single element
test("when all items are same, return array containing one single one of that item", () => {});
expect(dedupe(["a", "a", "a", "a"])).toEqual(["a"]);
14 changes: 13 additions & 1 deletion Sprint-1/implement/max.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,16 @@
function findMax(elements) {
function findMax(nums) {
if (!Array.isArray(nums)) {
throw new TypeError("Expected an array");
}

return nums.reduce((acc, curr) => {
// ignores non-num values
if (typeof curr !== "number" || isNaN(curr)) {
return acc;
}

return curr > acc ? curr : acc;
}, -Infinity); // returns -Infinity for empty elements arr, as reduce callback never runs.
}

module.exports = findMax;
28 changes: 25 additions & 3 deletions Sprint-1/implement/max.test.js
Original file line number Diff line number Diff line change
@@ -1,9 +1,11 @@
/* Find the maximum element of an array of numbers

In this kata, you will need to implement a function that find the largest numerical element of an array.
In this kata, you will need to implement a function that find the
largest numerical element of an array.

E.g. max([30, 50, 10, 40]), target output: 50
E.g. max(['hey', 10, 'hi', 60, 10]), target output: 60 (sum ignores any non-numerical elements)
E.g. max(['hey', 10, 'hi', 60, 10]),
target output: 60 (sum ignores any non-numerical elements)

You should implement this function in max.js, and add tests for it in this file.

Expand All @@ -16,28 +18,48 @@ const findMax = require("./max.js");
// When passed to the max function
// Then it should return -Infinity
// Delete this test.todo and replace it with a test.
test.todo("given an empty array, returns -Infinity");
test("empty array returns -Infinity", () => {
expect(findMax([])).toEqual(-Infinity);
});

// Given an array with one number
// When passed to the max function
// Then it should return that number
test("array with single element returns that element", () => {
expect(findMax([3])).toEqual(3);
});

// Given an array with both positive and negative numbers
// When passed to the max function
// Then it should return the largest number overall
test("array with positive and negative elements still returns correct value", () => {
expect(findMax([-3, 3])).toEqual(3);
});

// Given an array with just negative numbers
// When passed to the max function
// Then it should return the closest one to zero
test("array of all negative numbers returns closest value to zero", () => {
expect(findMax([-5, -6, -3, -12])).toEqual(-3);
});

// Given an array with decimal numbers
// When passed to the max function
// Then it should return the largest decimal number
test("array of decimal numbers returns correct value", () => {
expect(findMax([3.3, 12.2, 4.3, 22.22])).toEqual(22.22);
});

// Given an array with non-number values
// When passed to the max function
// Then it should return the max and ignore non-numeric values
test("ignores non-numeric values in array and returns max", () => {
expect(findMax([3, "asd", [22], { a: 12 }, 12])).toEqual(12);
});

// Given an array with only non-number values
// When passed to the max function
// Then it should return the least surprising value given how it behaves for all other inputs
test("if all elements are non-numeric, return -Infinity", () => {
expect(findMax(["67", "asd", [22], { a: 12 }, "ss"])).toEqual(-Infinity);
});
6 changes: 6 additions & 0 deletions Sprint-1/implement/sum.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,10 @@
function sum(elements) {
return elements.reduce((acc, curr) => {
if (typeof curr !== "number" || isNaN(curr)) {
return acc;
}
return acc + curr;
}, 0);
}

module.exports = sum;
15 changes: 14 additions & 1 deletion Sprint-1/implement/sum.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -13,24 +13,37 @@ const sum = require("./sum.js");
// Given an empty array
// When passed to the sum function
// Then it should return 0
test.todo("given an empty array, returns 0")
test("empty array should return 0", () => expect(sum([])).toEqual(0));

// Given an array with just one number
// When passed to the sum function
// Then it should return that number
test("array of single value should return that value", () =>
expect(sum([3])).toEqual(3));

// Given an array containing negative numbers
// When passed to the sum function
// Then it should still return the correct total sum
test("should return correct sum for negative and positive numbers", () =>
expect(sum([-2, -4, 6])).toEqual(0));

// Given an array with decimal/float numbers
// When passed to the sum function
// Then it should return the correct total sum

// use toBeCloseTo to account for floating point
test("should sum floats", () => expect(sum([0.1, 0.2])).toBeCloseTo(0.3));

// Given an array containing non-number values
// When passed to the sum function
// Then it should ignore the non-numerical values and return the sum of the numerical elements
test("ignores non-numerical values in array", () => {
expect(sum(["asd", { a: 12 }, [22, 33], 3, 3])).toEqual(6);
});

// Given an array with only non-number values
// When passed to the sum function
// Then it should return the least surprising value given how it behaves for all other inputs
test("array of all non-numbers should return 0", () => {
expect(sum(["asdf", { a: 12 }, [22, 33]])).toEqual(0);
});
Loading
Loading