Skip to content

Commit

Permalink
Merge pull request #15 from marcode24/2023
Browse files Browse the repository at this point in the history
✨ add challenge-11 solution
  • Loading branch information
marcode24 authored Dec 18, 2023
2 parents 9af3ee2 + 529b4ac commit 721cc68
Show file tree
Hide file tree
Showing 15 changed files with 671 additions and 0 deletions.
50 changes: 50 additions & 0 deletions 2023/11-los-elfos-estudiosos/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
# Reto 11: Los elfos estudiosos

## Problema

En el taller de Santa, los elfos aman los acertijos 🧠. Este año, han creado uno especial: un desafío para formar un palíndromo navideño.

**Un palíndromo es una palabra que se lee igual hacia adelante y hacia atrás.** Los elfos quieren saber si es posible formar un palíndromo haciendo, como mucho, un intercambio de letras.

Crea una función `getIndexsForPalindrome` que reciba una cadena de caracteres y devolverá:

- Si ya es un palíndromo, un array vacío.
- Si no es posible, null.
- Si se puede formar un palíndromo con un cambio, un array con las dos posiciones (índices) que se deben intercambiar para poder crearlo.

Por ejemplo:

```js
getIndexsForPalindrome('anna') // []
getIndexsForPalindrome('abab') // [0, 1]
getIndexsForPalindrome('abac') // null
getIndexsForPalindrome('aaaaaaaa') // []
getIndexsForPalindrome('aaababa') // [1, 3]
getIndexsForPalindrome('caababa') // null``
```

Si se puede formar el palíndromo con diferentes intercambios, **siempre se debe devolver el primero que se encuentre.**

## Mi solución

```js
function getIndexsForPalindrome(word) {
const wordLength = word.length;
const isPalindrome = (str) => str === [...str].reverse().join('');

if (isPalindrome(word)) return [];

for (let i = 0; i < wordLength; i++) {
for (let j = i + 1; j < wordLength; j++) {
const newWord = [...word];
[newWord[i], newWord[j]] = [newWord[j], newWord[i]];

if (newWord.join('') === newWord.reverse().join('')) {
return [i, j];
}
}
}

return null;
}
```
21 changes: 21 additions & 0 deletions 2023/11-los-elfos-estudiosos/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
function getIndexsForPalindrome(word) {
const wordLength = word.length;
const isPalindrome = (str) => str === [...str].reverse().join('');

if (isPalindrome(word)) return [];

for (let i = 0; i < wordLength; i++) {
for (let j = i + 1; j < wordLength; j++) {
const newWord = [...word];
[newWord[i], newWord[j]] = [newWord[j], newWord[i]];

if (newWord.join('') === newWord.reverse().join('')) {
return [i, j];
}
}
}

return null;
}

module.exports = getIndexsForPalindrome;
42 changes: 42 additions & 0 deletions 2023/11-los-elfos-estudiosos/index.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
const getIndexsForPalindrome = require('./index');

describe('11 => Los elfos estudiosos', () => {
const testCases = [
{
input: 'anna',
output: [],
},
{
input: 'abab',
output: [0, 1],
},
{
input: 'abac',
output: null,
},
{
input: 'aaaaaaaa',
output: [],
},
{
input: 'aaababa',
output: [1, 3],
},
{
input: 'caababa',
output: null,
},
];

it('should return an array type if the input is a palindrome', () => {
expect(getIndexsForPalindrome('abab')).toEqual([0, 1]);
});

it('should return null type if the input could not be a palindrome', () => {
expect(getIndexsForPalindrome('abac')).toBeNull();
});

it.each(testCases)('should return $output', ({ input, output }) => {
expect(getIndexsForPalindrome(input)).toEqual(output);
});
});
51 changes: 51 additions & 0 deletions 2023/13-calculando-el-tiempo/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,51 @@
# Reto 13: Calculando el tiempo

## Problema

Los elfos están preparando **la víspera de Navidad** y necesitan tu ayuda para calcular si van sobrados o no de tiempo ⏳.

Para ello te pasan un array con la duración de cada entrega. El formato de la duración es HH:mm:ss, las entregas empiezan a las 00:00:00 y el límite de tiempo es 07:00:00.

**Tu función debe devolver el tiempo que les faltará o el tiempo que les sobrará** para terminar las entregas. El formato de la duración devuelta debe ser HH:mm:ss.

Si terminan antes de las 07:00:00, el tiempo restante hasta las 07:00:00 debe ser mostrado con un signo negativo. Por ejemplo, **si sobran 1 hora y 30 minutos, devuelve -01:30:00**

```js
calculateTime(['00:10:00', '01:00:00', '03:30:00'])
// '-02:20:00'

calculateTime(['02:00:00', '05:00:00', '00:30:00'])
// '00:30:00'

calculateTime([
'00:45:00',
'00:45:00',
'00:00:30',
'00:00:30'
]) // '-05:29:00'
```

## Mi solución

```js
function calculateTime(deliveries) {
const deliveryLimit = 7 * 3600; // Límite de tiempo en segundos (7 horas)
let totalSeconds = 0;

// eslint-disable-next-line no-restricted-syntax
for (const time of deliveries) {
const [hours, minutes, seconds] = time.split(':').map(Number);
totalSeconds += hours * 3600 + minutes * 60 + seconds;
}

const remainingSeconds = deliveryLimit - totalSeconds;
const pad = (value) => (value < 10 ? `0${value}` : `${value}`);
const sign = remainingSeconds <= 0 ? '' : '-';
const absRemainingSeconds = Math.abs(remainingSeconds);
const resultHours = pad(Math.floor(absRemainingSeconds / 3600));
const resultMinutes = pad(Math.floor((absRemainingSeconds % 3600) / 60));
const resultSeconds = pad(absRemainingSeconds % 60);
return `${sign}${resultHours}:${resultMinutes}`
+ `:${resultSeconds}`;
}
```
22 changes: 22 additions & 0 deletions 2023/13-calculando-el-tiempo/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
function calculateTime(deliveries) {
const deliveryLimit = 7 * 3600; // Límite de tiempo en segundos (7 horas)
let totalSeconds = 0;

// eslint-disable-next-line no-restricted-syntax
for (const time of deliveries) {
const [hours, minutes, seconds] = time.split(':').map(Number);
totalSeconds += hours * 3600 + minutes * 60 + seconds;
}

const remainingSeconds = deliveryLimit - totalSeconds;
const pad = (value) => (value < 10 ? `0${value}` : `${value}`);
const sign = remainingSeconds <= 0 ? '' : '-';
const absRemainingSeconds = Math.abs(remainingSeconds);
const resultHours = pad(Math.floor(absRemainingSeconds / 3600));
const resultMinutes = pad(Math.floor((absRemainingSeconds % 3600) / 60));
const resultSeconds = pad(absRemainingSeconds % 60);
return `${sign}${resultHours}:${resultMinutes}`
+ `:${resultSeconds}`;
}

module.exports = calculateTime;
26 changes: 26 additions & 0 deletions 2023/13-calculando-el-tiempo/index.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
const calculateTime = require('./index');

describe('13 => Calculando el tiempo', () => {
const testCases = [
{
input: ['00:10:00', '01:00:00', '03:30:00'],
output: '-02:20:00',
},
{
input: ['02:00:00', '05:00:00', '00:30:00'],
output: '00:30:00',
},
{
input: ['00:45:00', '00:45:00', '00:00:30', '00:00:30'],
output: '-05:29:00',
},
];

it('should return a string type', () => {
expect(typeof calculateTime(testCases[0].input)).toBe('string');
});

it.each(testCases)('should return $output', (testCase) => {
expect(calculateTime(testCase.input)).toBe(testCase.output);
});
});
32 changes: 32 additions & 0 deletions 2023/14-evita-la-alarma/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
# Reto 14: Evita la alarma

## Problema

Con el tema de las redes sociales, Santa Claus **tiene pánico que los niños se despierten mientras él está repartiendo regalos en sus casos,** usen el móvil para grabarlo y se haga viral en TikTok.

Quiere evitarlo a toda costa. Cada casa en esa calle tiene un número de regalos preparados. Sin embargo, **las casas tienen un sistema de seguridad conectado entre casas adyacentes,** por lo que **no puede dejar los regalos en dos casas seguidas,** o se activará la alarma que alertará a los niños.

Dada un **array de enteros no negativos regalos** que representa la cantidad de regalos en cada casa, tu tarea es ayudar a Papá Noel a determinar la **máxima cantidad de regalos que puede entregar** en una noche sin activar ninguna alarma.

```js
maxGifts([2, 4, 2]) // 4 (4)
maxGifts([5, 1, 1, 5]) // 10 (5 + 5)
maxGifts([4, 1, 1, 4, 2, 1]) // 9 (4 + 4 + 1)
maxGifts([1, 3, 1, 3, 100]) // 103 (3 + 100)
```

## Mi solución

```js
const maxGifts = (houses) => {
let incl = 0;
let excl = 0;

// eslint-disable-next-line no-restricted-syntax
for (const current of houses) {
[incl, excl] = [excl + current, Math.max(incl, excl)];
}

return Math.max(incl, excl);
};
```
13 changes: 13 additions & 0 deletions 2023/14-evita-la-alarma/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
const maxGifts = (houses) => {
let incl = 0;
let excl = 0;

// eslint-disable-next-line no-restricted-syntax
for (const current of houses) {
[incl, excl] = [excl + current, Math.max(incl, excl)];
}

return Math.max(incl, excl);
};

module.exports = maxGifts;
30 changes: 30 additions & 0 deletions 2023/14-evita-la-alarma/index.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
const maxGifts = require('./index');

describe('14 => Evita la alarma', () => {
const testCases = [
{
input: [2, 4, 2],
output: 4,
},
{
input: [5, 1, 1, 5],
output: 10,
},
{
input: [4, 1, 1, 4, 2, 1],
output: 9,
},
{
input: [1, 3, 1, 3, 100],
output: 103,
},
];

it('should return a number type', () => {
expect(typeof maxGifts([1, 2, 3])).toBe('number');
});

it.each(testCases)('should return $output', ({ input, output }) => {
expect(maxGifts(input)).toBe(output);
});
});
68 changes: 68 additions & 0 deletions 2023/15-robot-autonomo/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
# Reto 15: Robot autonomo

## Problema

Estamos programando unos **robots** llamados giftbot 🤖🎁 que navegan de forma autónoma por los almacenes de regalos.

Estamos creando una función a la que le pasamos: el almacén 🏬 que deben navegar y los movimientos ↔️ que pueden realizar.

El almacén se representa como un **array de cadenas de texto,** donde:

- `.` significa que hay vía libre.
- `*` significa que hay un obstáculo.
- `!` es la posición inicial del robot.

Los movimientos son un **array de cadenas de texto,** donde:

- `R` mueve al robot una posición a la derecha.
- `L` mueve al robot una posición a la izquierda.
- `U` mueve al robot una posición hacia arriba.
- `D` mueve al robot una posición hacia abajo.

Hay que tener en cuenta que **el robot no puede superar los obstáculos ni los límites del almacén.**

Dados un almacén y los movimientos, debemos devolver el array con la posición final de nuestro robot.

```js
const store = ['..!....', '...*.*.']

const movements = ['R', 'R', 'D', 'L']
const result = autonomousDrive(store, movements)
console.log(result)
/*
[
".......",
"...*!*."
]
*/

// El último movimiento es hacia la izquierda, pero no puede moverse porque hay un obstáculo.
```

Ten en cuenta que la store es **un array que puede ser de un número de filas que va de 1 a 100,** ya que tenemos almacenes de todos los tamaños.

También que el robot **es posible que termine en su posición inicial** si no puede moverse o si está dando vueltas.

## Mi solución

```js
function autonomousDrive(store, movements) {
let currentRow = store.findIndex((line) => line.includes('!'));
let currentCol = store[currentRow].indexOf('!');
store[currentRow] = store[currentRow].replace('!', '.');

// eslint-disable-next-line no-restricted-syntax
for (const movement of movements) {
const di = +(movement === 'D') - +(movement === 'U');
const dj = +(movement === 'R') - +(movement === 'L');
currentRow += +(store[currentRow + di]?.[currentCol] === '.' && di);
currentCol += +(store[currentRow][currentCol + dj] === '.' && dj);
}

const currentLine = store[currentRow];
store[currentRow] = `${currentLine.substring(0, currentCol)}!${
currentLine.substring(currentCol + 1)}`;

return store;
}
```
21 changes: 21 additions & 0 deletions 2023/15-robot-autonomo/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
function autonomousDrive(store, movements) {
let currentRow = store.findIndex((line) => line.includes('!'));
let currentCol = store[currentRow].indexOf('!');
store[currentRow] = store[currentRow].replace('!', '.');

// eslint-disable-next-line no-restricted-syntax
for (const movement of movements) {
const di = +(movement === 'D') - +(movement === 'U');
const dj = +(movement === 'R') - +(movement === 'L');
currentRow += +(store[currentRow + di]?.[currentCol] === '.' && di);
currentCol += +(store[currentRow][currentCol + dj] === '.' && dj);
}

const currentLine = store[currentRow];
store[currentRow] = `${currentLine.substring(0, currentCol)}!${
currentLine.substring(currentCol + 1)}`;

return store;
}

module.exports = autonomousDrive;
Loading

0 comments on commit 721cc68

Please sign in to comment.