# Number of Ways to Build Sturdy Brick Wall

- slug: number-of-ways-to-build-sturdy-brick-wall
- difficulty: Medium

You are given integers `height` and `width` which specify the dimensions of a brick wall you are building. You are also given a **0-indexed** array of **unique** integers `bricks`, where the `ith` brick has a height of `1` and a width of `bricks[i]`. You have an **infinite** supply of each type of brick and bricks may **not** be rotated.

Each row in the wall must be exactly `width` units long. For the wall to be **sturdy**, adjacent rows in the wall should **not** join bricks at the same location, except at the ends of the wall.

Return _the number of ways to build a **sturdy** wall._ Since the answer may be very large, return it **modulo** `109 + 7`.

**Example 1:**

**Input:** height = 2, width = 3, bricks = \[1,2\]
**Output:** 2
**Explanation:**
The first two walls in the diagram show the only two ways to build a sturdy brick wall.
Note that the third wall in the diagram is not sturdy because adjacent rows join bricks 2 units from the left.

**Example 2:**

**Input:** height = 1, width = 1, bricks = \[5\]
**Output:** 0
**Explanation:**
There are no ways to build a sturdy wall because the only type of brick we have is longer than the width of the wall.

**Constraints:**

*   `1 <= height <= 100`
*   `1 <= width <= 10`
*   `1 <= bricks.length <= 10`
*   `1 <= bricks[i] <= 10`
*   All the values of `bricks` are **unique**.

## A solution in Java

```java
public boolean areEncodedStringsEqual(String s1, String s2) {
    StringBuilder decoded1 = new StringBuilder(), decoded2 = new StringBuilder();

    for(int i = 0; i < s1.length(); ++i) {
        if(Character.isDigit(s1.charAt(i))) {
            int count = s1.charAt(i) - '0';
            while(count-- > 0) decoded1.append(s1.charAt(i - 1));
        } else decoded1.append(s1.charAt(i));
    }

    for(int i = 0; i < s2.length(); ++i) {
        if(Character.isDigit(s2.charAt(i))) {
            int count = s2.charAt(i) - '0';
            while(count-- > 0) decoded2.append(s2.charAt(i - 1));
        } else decoded2.append(s2.charAt(i));
    }

    return decoded1.toString().equals(decoded2.toString());
}
```
We initialize two strings called `decoded1` and `decoded2` to store the decoded representations of `s1` and `s2`. For each input string, we iterate through the characters. If the character is a digit, we take the previous character and repeat it that digit number of times, adding it to the relevant decoded string. If the character is not a digit, we simply add it to the decoded string. After decoding both strings, we compare them for equality and return the result.

## A solution in C++

```cpp
#include <string>
using namespace std;

bool areEncodedStringsEqual(string s1, string s2) {
    string decoded1 = "", decoded2 = "";

    for(int i = 0; i < s1.size(); ++i) {
        if(isdigit(s1[i])) {
            int count = s1[i] - '0';
            while(count--) decoded1 += s1[i - 1];
        } else decoded1 += s1[i];
    }

    for(int i = 0; i < s2.size(); ++i) {
        if(isdigit(s2[i])) {
            int count = s2[i] - '0';
            while(count--) decoded2 += s2[i - 1];
        } else decoded2 += s2[i];
    }

    return decoded1 == decoded2;
}
```
We initialize two strings called `decoded1` and `decoded2` to store the decoded representations of `s1` and `s2`. For each input string, we iterate through the characters. If the character is a digit, we take the previous character and repeat it that digit number of times, adding it to the relevant decoded string. If the character is not a digit, we simply add it to the decoded string. After decoding both strings, we compare them for equality and return the result.

## A solution in Python

```python
def are_encoded_strings_equal(s1: str, s2: str) -> bool:
    decoded1, decoded2 = "", ""

    for i, c in enumerate(s1):
        if c.isdigit():
            count = int(c)
            decoded1 += s1[i - 1] * count
        else:
            decoded1 += c

    for i, c in enumerate(s2):
        if c.isdigit():
            count = int(c)
            decoded2 += s2[i - 1] * count
        else:
            decoded2 += c

    return decoded1 == decoded2
```
We initialize two strings called `decoded1` and `decoded2` to store the decoded representations of `s1` and `s2`. For each input string, we iterate through the characters. If the character is a digit, we take the previous character and repeat it that digit number of times, adding it to the relevant decoded string. If the character is not a digit, we simply add it to the decoded string. After decoding both strings, we compare them for equality and return the result.

## A solution in Javascript

```javascript
function areEncodedStringsEqual(s1, s2) {
    let decoded1 = "", decoded2 = "";

    for(let i = 0; i < s1.length; ++i) {
        if(!isNaN(s1[i])) {
            let count = Number(s1[i]);
            while(count--) decoded1 += s1[i - 1];
        } else decoded1 += s1[i];
    }

    for(let i = 0; i < s2.length; ++i) {
        if(!isNaN(s2[i])) {
            let count = Number(s2[i]);
            while(count--) decoded2 += s2[i - 1];
        } else decoded2 += s2[i];
    }

    return decoded1 === decoded2;
}
```
We initialize two strings called `decoded1` and `decoded2` to store the decoded representations of `s1` and `s2`. For each input string, we iterate through the characters. If the character is a digit, we take the previous character and repeat it that digit number of times, adding it to the relevant decoded string. If the character is not a digit, we simply add it to the decoded string. After decoding both strings, we compare them for equality and return the result.


# Counting Words With a Given Prefix

- slug: counting-words-with-a-given-prefix
- difficulty: Easy

You are given an array of strings `words` and a string `pref`.

Return _the number of strings in_ `words` _that contain_ `pref` _as a **prefix**_.

A **prefix** of a string `s` is any leading contiguous substring of `s`.

**Example 1:**

**Input:** words = \[ "pay ", "**at**tention ", "practice ", "**at**tend "\], `pref` \=  "at "
**Output:** 2
**Explanation:** The 2 strings that contain  "at " as a prefix are:  "**at**tention " and  "**at**tend ".

**Example 2:**

**Input:** words = \[ "leetcode ", "win ", "loops ", "success "\], `pref` \=  "code "
**Output:** 0
**Explanation:** There are no strings that contain  "code " as a prefix.

**Constraints:**

*   `1 <= words.length <= 100`
*   `1 <= words[i].length, pref.length <= 100`
*   `words[i]` and `pref` consist of lowercase English letters.

## A solution in Java

```java
public int count_prefixes(String[] words, String pref) {
    int count = 0;
    for(String word : words) {
        if(word.startsWith(pref)) {
            count++;
        }
    }
    return count;
}
```
The algorithm iterates through the list of words and checks if the word starts with the given prefix. If it does, increment the count. Finally, return the count.

## A solution in C++

```cpp
int count_prefixes(vector<string>& words, string pref) {
    int count = 0;
    for(const auto& word : words) {
        if(word.find(pref) == 0) {
            count++;
        }
    }
    return count;
}
```
The algorithm iterates through the list of words and checks if the word starts with the given prefix. If it does, increment the count. Finally, return the count.

## A solution in Python

```python
def count_prefixes(words, pref):
    return sum(1 for word in words if word.startswith(pref))
```
The algorithm iterates through the list of words and checks if the word starts with the given prefix. If it does, increment the count. Finally, return the count.

## A solution in Javascript

```javascript
function count_prefixes(words, pref) {
    let count = 0;
    for(const word of words) {
        if(word.startsWith(pref)) {
            count++;
        }
    }
    return count;
}
```
The algorithm iterates through the list of words and checks if the word starts with the given prefix. If it does, increment the count. Finally, return the count.


# Minimum Number of Steps to Make Two Strings Anagram II

- slug: minimum-number-of-steps-to-make-two-strings-anagram-ii
- difficulty: Medium

You are given two strings `s` and `t`. In one step, you can append **any character** to either `s` or `t`.

Return _the minimum number of steps to make_ `s` _and_ `t` _**anagrams** of each other._

An **anagram** of a string is a string that contains the same characters with a different (or the same) ordering.

**Example 1:**

**Input:** s =  "**lee**tco**de** ", t =  "co**a**t**s** "
**Output:** 7
**Explanation:**
- In 2 steps, we can append the letters in  "as " onto s =  "leetcode ", forming s =  "leetcode**as** ".
- In 5 steps, we can append the letters in  "leede " onto t =  "coats ", forming t =  "coats**leede** ".
 "leetcodeas " and  "coatsleede " are now anagrams of each other.
We used a total of 2 + 5 = 7 steps.
It can be shown that there is no way to make them anagrams of each other with less than 7 steps.

**Example 2:**

**Input:** s =  "night ", t =  "thing "
**Output:** 0
**Explanation:** The given strings are already anagrams of each other. Thus, we do not need any further steps.

**Constraints:**

*   `1 <= s.length, t.length <= 2 * 105`
*   `s` and `t` consist of lowercase English letters.

## A solution in Java

```java
import java.util.HashSet;
import java.util.Set;

public int countVowelSubstrings(String word) {
    int count = 0, n = word.length();
    Set<Character> vowels = new HashSet<>();

    for (int i = 0; i < n; i++) {
        if ("aeiou".indexOf(word.charAt(i)) != -1) {
            vowels.clear();
            for (int j = i; j < n; j++) {
                if ("aeiou".indexOf(word.charAt(j)) != -1) {
                    vowels.add(word.charAt(j));
                }
                if (vowels.size() == 5) count++;
            }
        }
    }
    return count;
}
```
The algorithm starts by iterating through the input string (`word`). For each character in `word`, we first check if the character is a vowel (i.e., 'a', 'e', 'i', 'o', or 'u'). If it is not a vowel, we move on to the next character. If it is a vowel, we clear the `vowels` set and start another loop that iterates over the remaining characters, adding each successive vowel to the `vowels` set. At each step, we check if the current vowel is the last one needed to complete the set. If so, we increment the `count` variable. Finally, we return the total count of vowel substrings after all iterations. The main difference in each implementation is in the syntax and data structures required for each language, but the overall algorithm is the same.

## A solution in C++

```cpp
#include <string>
#include <set>

int count_vowel_substrings(std::string word) {
    int count = 0, n = word.size();
    std::set<char> vowels;

    for (int i = 0; i < n; i++) {
        if (word[i] == 'a' || word[i] == 'e' || word[i] == 'i' || word[i] == 'o' || word[i] == 'u') {
            vowels.clear();
            for (int j = i; j < n; j++) {
                if (word[j] == 'a' || word[j] == 'e' || word[j] == 'i' || word[j] == 'o' || word[j] == 'u') {
                    vowels.insert(word[j]);
                }
                if (vowels.size() == 5) count++;
            }
        }
    }
    return count;
}
```
The algorithm starts by iterating through the input string (`word`). For each character in `word`, we first check if the character is a vowel (i.e., 'a', 'e', 'i', 'o', or 'u'). If it is not a vowel, we move on to the next character. If it is a vowel, we clear the `vowels` set and start another loop that iterates over the remaining characters, adding each successive vowel to the `vowels` set. At each step, we check if the current vowel is the last one needed to complete the set. If so, we increment the `count` variable. Finally, we return the total count of vowel substrings after all iterations. The main difference in each implementation is in the syntax and data structures required for each language, but the overall algorithm is the same.

## A solution in Python

```python
def count_vowel_substrings(word: str) -> int:
    count = 0
    n = len(word)
    vowels = set()

    for i in range(n):
        if word[i] in "aeiou":
            vowels.clear()
            for j in range(i, n):
                if word[j] in "aeiou":
                    vowels.add(word[j])
                if len(vowels) == 5:
                    count += 1
    return count
```
The algorithm starts by iterating through the input string (`word`). For each character in `word`, we first check if the character is a vowel (i.e., 'a', 'e', 'i', 'o', or 'u'). If it is not a vowel, we move on to the next character. If it is a vowel, we clear the `vowels` set and start another loop that iterates over the remaining characters, adding each successive vowel to the `vowels` set. At each step, we check if the current vowel is the last one needed to complete the set. If so, we increment the `count` variable. Finally, we return the total count of vowel substrings after all iterations. The main difference in each implementation is in the syntax and data structures required for each language, but the overall algorithm is the same.

## A solution in Javascript

```javascript
function countVowelSubstrings(word) {
    let count = 0, n = word.length;
    let vowels = new Set();

    for (let i = 0; i < n; i++) {
        if ("aeiou".includes(word[i])) {
            vowels.clear();
            for (let j = i; j < n; j++) {
                if ("aeiou".includes(word[j])) {
                    vowels.add(word[j]);
                }
                if (vowels.size === 5) count++;
            }
        }
    }
    return count;
}
```
The algorithm starts by iterating through the input string (`word`). For each character in `word`, we first check if the character is a vowel (i.e., 'a', 'e', 'i', 'o', or 'u'). If it is not a vowel, we move on to the next character. If it is a vowel, we clear the `vowels` set and start another loop that iterates over the remaining characters, adding each successive vowel to the `vowels` set. At each step, we check if the current vowel is the last one needed to complete the set. If so, we increment the `count` variable. Finally, we return the total count of vowel substrings after all iterations. The main difference in each implementation is in the syntax and data structures required for each language, but the overall algorithm is the same.


# Minimum Time to Complete Trips

- slug: minimum-time-to-complete-trips
- difficulty: Medium

You are given an array `time` where `time[i]` denotes the time taken by the `ith` bus to complete **one trip**.

Each bus can make multiple trips **successively**; that is, the next trip can start **immediately after** completing the current trip. Also, each bus operates **independently**; that is, the trips of one bus do not influence the trips of any other bus.

You are also given an integer `totalTrips`, which denotes the number of trips all buses should make **in total**. Return _the **minimum time** required for all buses to complete **at least**_ `totalTrips` _trips_.

**Example 1:**

**Input:** time = \[1,2,3\], totalTrips = 5
**Output:** 3
**Explanation:**
- At time t = 1, the number of trips completed by each bus are \[1,0,0\].
  The total number of trips completed is 1 + 0 + 0 = 1.
- At time t = 2, the number of trips completed by each bus are \[2,1,0\].
  The total number of trips completed is 2 + 1 + 0 = 3.
- At time t = 3, the number of trips completed by each bus are \[3,1,1\].
  The total number of trips completed is 3 + 1 + 1 = 5.
So the minimum time needed for all buses to complete at least 5 trips is 3.

**Example 2:**

**Input:** time = \[2\], totalTrips = 1
**Output:** 2
**Explanation:**
There is only one bus, and it will complete its first trip at t = 2.
So the minimum time needed to complete 1 trip is 2.

**Constraints:**

*   `1 <= time.length <= 105`
*   `1 <= time[i], totalTrips <= 107`

## A solution in Java

```java
public long sumOfVowelsInTheSubstrings(String word) {
    long sum = 0;
    int n = word.length();

    for (int i = 0; i < n; i++) {
        if (word.charAt(i) == 'a' || word.charAt(i) == 'e' || word.charAt(i) == 'i'
          || word.charAt(i) == 'o' || word.charAt(i) == 'u') {
            sum += (long)(i + 1) * (n - i);
        }
    }
    return sum;
}
```
The algorithm performs the following steps:

1. Initialize a variable `sum` to store the sum of vowels.
2. Calculate the length `n` of the input string.
3. Iterate through each character in the input string.
4. If the character is a vowel ('a', 'e', 'i', 'o', 'u'), add the product `(i + 1) * (n - i)` to the `sum`. The expression `(i + 1) * (n - i)` calculates the number of times the vowel appears in all the substrings, where `i + 1` is the number of substrings starting at the vowel and `n - i` is the number of substrings ending at the vowel.
5. Return the sum.

This algorithm iterates through the input string once, so the time complexity is O(n), where n is the length of the input string.

## A solution in C++

```cpp
#include <string>
using namespace std;

long long sumOfVowelsInTheSubstrings(string word) {
    long long sum = 0;
    int n = word.length();

    for (int i = 0; i < n; i++) {
        if (word[i] == 'a' || word[i] == 'e' || word[i] == 'i' || word[i] == 'o' || word[i] == 'u') {
            sum += (long long)(i + 1) * (n - i);
        }
    }
    return sum;
}
```
The algorithm performs the following steps:

1. Initialize a variable `sum` to store the sum of vowels.
2. Calculate the length `n` of the input string.
3. Iterate through each character in the input string.
4. If the character is a vowel ('a', 'e', 'i', 'o', 'u'), add the product `(i + 1) * (n - i)` to the `sum`. The expression `(i + 1) * (n - i)` calculates the number of times the vowel appears in all the substrings, where `i + 1` is the number of substrings starting at the vowel and `n - i` is the number of substrings ending at the vowel.
5. Return the sum.

This algorithm iterates through the input string once, so the time complexity is O(n), where n is the length of the input string.

## A solution in Python

```python
def sum_of_vowels_in_the_substrings(word: str) -> int:
    total_sum = 0
    n = len(word)

    for i, char in enumerate(word):
        if char in {'a', 'e', 'i', 'o', 'u'}:
            total_sum += (i + 1) * (n - i)

    return total_sum
```
The algorithm performs the following steps:

1. Initialize a variable `sum` to store the sum of vowels.
2. Calculate the length `n` of the input string.
3. Iterate through each character in the input string.
4. If the character is a vowel ('a', 'e', 'i', 'o', 'u'), add the product `(i + 1) * (n - i)` to the `sum`. The expression `(i + 1) * (n - i)` calculates the number of times the vowel appears in all the substrings, where `i + 1` is the number of substrings starting at the vowel and `n - i` is the number of substrings ending at the vowel.
5. Return the sum.

This algorithm iterates through the input string once, so the time complexity is O(n), where n is the length of the input string.

## A solution in Javascript

```javascript
function sumOfVowelsInTheSubstrings(word) {
    let sum = 0;
    let n = word.length;

    for (let i = 0; i < n; i++) {
        if (word[i] === 'a' || word[i] === 'e' || word[i] === 'i'
          || word[i] === 'o' || word[i] === 'u') {
            sum += (i + 1) * (n - i);
        }
    }
    return sum;
}
```
The algorithm performs the following steps:

1. Initialize a variable `sum` to store the sum of vowels.
2. Calculate the length `n` of the input string.
3. Iterate through each character in the input string.
4. If the character is a vowel ('a', 'e', 'i', 'o', 'u'), add the product `(i + 1) * (n - i)` to the `sum`. The expression `(i + 1) * (n - i)` calculates the number of times the vowel appears in all the substrings, where `i + 1` is the number of substrings starting at the vowel and `n - i` is the number of substrings ending at the vowel.
5. Return the sum.

This algorithm iterates through the input string once, so the time complexity is O(n), where n is the length of the input string.


# Minimum Time to Finish the Race

- slug: minimum-time-to-finish-the-race
- difficulty: Hard

You are given a **0-indexed** 2D integer array `tires` where `tires[i] = [fi, ri]` indicates that the `ith` tire can finish its `xth` successive lap in `fi * ri(x-1)` seconds.

*   For example, if `fi = 3` and `ri = 2`, then the tire would finish its `1st` lap in `3` seconds, its `2nd` lap in `3 * 2 = 6` seconds, its `3rd` lap in `3 * 22 = 12` seconds, etc.

You are also given an integer `changeTime` and an integer `numLaps`.

The race consists of `numLaps` laps and you may start the race with **any** tire. You have an **unlimited** supply of each tire and after every lap, you may **change** to any given tire (including the current tire type) if you wait `changeTime` seconds.

Return _the **minimum** time to finish the race._

**Example 1:**

**Input:** tires = \[\[2,3\],\[3,4\]\], changeTime = 5, numLaps = 4
**Output:** 21
**Explanation:**
Lap 1: Start with tire 0 and finish the lap in 2 seconds.
Lap 2: Continue with tire 0 and finish the lap in 2 \* 3 = 6 seconds.
Lap 3: Change tires to a new tire 0 for 5 seconds and then finish the lap in another 2 seconds.
Lap 4: Continue with tire 0 and finish the lap in 2 \* 3 = 6 seconds.
Total time = 2 + 6 + 5 + 2 + 6 = 21 seconds.
The minimum time to complete the race is 21 seconds.

**Example 2:**

**Input:** tires = \[\[1,10\],\[2,2\],\[3,4\]\], changeTime = 6, numLaps = 5
**Output:** 25
**Explanation:**
Lap 1: Start with tire 1 and finish the lap in 2 seconds.
Lap 2: Continue with tire 1 and finish the lap in 2 \* 2 = 4 seconds.
Lap 3: Change tires to a new tire 1 for 6 seconds and then finish the lap in another 2 seconds.
Lap 4: Continue with tire 1 and finish the lap in 2 \* 2 = 4 seconds.
Lap 5: Change tires to tire 0 for 6 seconds then finish the lap in another 1 second.
Total time = 2 + 4 + 6 + 2 + 4 + 6 + 1 = 25 seconds.
The minimum time to complete the race is 25 seconds.

**Constraints:**

*   `1 <= tires.length <= 105`
*   `tires[i].length == 2`
*   `1 <= fi, changeTime <= 105`
*   `2 <= ri <= 105`
*   `1 <= numLaps <= 1000`

## A solution in Java

```java
import java.util.List;

public int min_x(int n, List<Integer> quantities) {
    int total_products = 0;
    for (int q : quantities) {
        total_products += q;
    }

    return (total_products + n - 1) / n;
}
```
We first compute the total number of products by summing up the values in the `quantities` array. In C++ and Java, we do this by looping through the array and adding each value to a running total. In Python, we use the built-in `sum()` function, while in JavaScript, we use the `reduce()` function.

After we have the total number of products, we calculate the minimum possible x by dividing the total number of products by the number of specialty retail stores and rounding up to the nearest integer. In C++ and Java, we do this using integer division, adding `n - 1` to the total number of products to ensure that the result is rounded up. In Python, we use floor division (`//`), which also ensures that the result is rounded up. In JavaScript, we use `Math.floor()` for rounding.

Finally, we return the minimum possible x, which represents the minimum number of products per store.

## A solution in C++

```cpp
#include <vector>
#include <algorithm>
using namespace std;

int min_x(int n, vector<int>& quantities) {
    int total_products = 0;
    for (int q : quantities) {
        total_products += q;
    }

    return (total_products + n - 1) / n;
}
```
We first compute the total number of products by summing up the values in the `quantities` array. In C++ and Java, we do this by looping through the array and adding each value to a running total. In Python, we use the built-in `sum()` function, while in JavaScript, we use the `reduce()` function.

After we have the total number of products, we calculate the minimum possible x by dividing the total number of products by the number of specialty retail stores and rounding up to the nearest integer. In C++ and Java, we do this using integer division, adding `n - 1` to the total number of products to ensure that the result is rounded up. In Python, we use floor division (`//`), which also ensures that the result is rounded up. In JavaScript, we use `Math.floor()` for rounding.

Finally, we return the minimum possible x, which represents the minimum number of products per store.

## A solution in Python

```python
def min_x(n, quantities):
    total_products = sum(quantities)
    return (total_products + n - 1) // n
```
We first compute the total number of products by summing up the values in the `quantities` array. In C++ and Java, we do this by looping through the array and adding each value to a running total. In Python, we use the built-in `sum()` function, while in JavaScript, we use the `reduce()` function.

After we have the total number of products, we calculate the minimum possible x by dividing the total number of products by the number of specialty retail stores and rounding up to the nearest integer. In C++ and Java, we do this using integer division, adding `n - 1` to the total number of products to ensure that the result is rounded up. In Python, we use floor division (`//`), which also ensures that the result is rounded up. In JavaScript, we use `Math.floor()` for rounding.

Finally, we return the minimum possible x, which represents the minimum number of products per store.

## A solution in Javascript

```javascript
function min_x(n, quantities) {
    let total_products = quantities.reduce((a, b) => a + b);
    return Math.floor((total_products + n - 1) / n);
}
```
We first compute the total number of products by summing up the values in the `quantities` array. In C++ and Java, we do this by looping through the array and adding each value to a running total. In Python, we use the built-in `sum()` function, while in JavaScript, we use the `reduce()` function.

After we have the total number of products, we calculate the minimum possible x by dividing the total number of products by the number of specialty retail stores and rounding up to the nearest integer. In C++ and Java, we do this using integer division, adding `n - 1` to the total number of products to ensure that the result is rounded up. In Python, we use floor division (`//`), which also ensures that the result is rounded up. In JavaScript, we use `Math.floor()` for rounding.

Finally, we return the minimum possible x, which represents the minimum number of products per store.


# Number of Ways to Build House of Cards

- slug: number-of-ways-to-build-house-of-cards
- difficulty: Medium

You are given an integer `n` representing the number of playing cards you have. A **house of cards** meets the following conditions:

*   A **house of cards** consists of one or more rows of **triangles** and horizontal cards.
*   **Triangles** are created by leaning two cards against each other.
*   One card must be placed horizontally between **all adjacent** triangles in a row.
*   Any triangle on a row higher than the first must be placed on a horizontal card from the previous row.
*   Each triangle is placed in the **leftmost** available spot in the row.

Return _the number of **distinct** **house of cards** you can build using **all**_ `n` _cards._ Two houses of cards are considered distinct if there exists a row where the two houses contain a different number of cards.

**Example 1:**

**Input:** n = 16
**Output:** 2
**Explanation:** The two valid houses of cards are shown.
The third house of cards in the diagram is not valid because the rightmost triangle on the top row is not placed on top of a horizontal card.

**Example 2:**

**Input:** n = 2
**Output:** 1
**Explanation:** The one valid house of cards is shown.

**Example 3:**

**Input:** n = 4
**Output:** 0
**Explanation:** The three houses of cards in the diagram are not valid.
The first house of cards needs a horizontal card placed between the two triangles.
The second house of cards uses 5 cards.
The third house of cards uses 2 cards.

**Constraints:**

*   `1 <= n <= 500`

## A solution in Java

```java
import java.util.*;

public int maxQualityRec(int[][] adjMatrix, int[] values, int node, int timeLeft, Set<Integer> visited) {
    if (timeLeft < 0) {
        return Integer.MIN_VALUE;
    }

    int maxQuality = 0;
    visited.add(node);
    for (int i = 0; i < adjMatrix[node].length; ++i) {
        if (adjMatrix[node][i] != -1) {
            int time = adjMatrix[node][i];
            int oldValue = adjMatrix[node][i];
            adjMatrix[node][i] = adjMatrix[i][node] = -1;
            maxQuality = Math.max(maxQuality, maxQualityRec(adjMatrix, values, i, timeLeft - time, visited));
            adjMatrix[node][i] = adjMatrix[i][node] = oldValue;
        }
    }
    visited.remove(node);
    return maxQuality + (visited.contains(node + 1) ? 0 : values[node]);
}

public int maxQuality(int n, int[] values, int[][] edges, int maxTime) {
    int[][] adjMatrix = new int[n][n];
    for (int[] row : adjMatrix) {
        Arrays.fill(row, -1);
    }

    for (int[] edge : edges) {
        adjMatrix[edge[0]][edge[1]] = adjMatrix[edge[1]][edge[0]] = edge[2];
    }

    Set<Integer> visited = new HashSet<>();
    return maxQualityRec(adjMatrix, values, 0, maxTime, visited);
}
```
The algorithm uses a backtracking approach with depth-first search. It starts from node `0` and recursively traverses through the graph while keeping track of visited nodes in a hash set. For each neighboring node, it updates the adjacency matrix (or adjacency dictionary in Python) to account for the travel time between the two nodes. After exploring the path, the algorithm backtracks by resetting the changes made to the adjacency matrix (or adjacency dictionary) and removing the current node from the visited nodes set.

The base case is when the timeLeft is less than zero, which indicates that the path exceeds the maxTime, so it returns INT_MIN (or float('-inf') in Python) to discard this path. After exploring all possible paths, the function returns the maximum quality found in valid paths. The quality of a path is calculated as the sum of values of the unique nodes visited in the path.

Note that the maximum number of edges connected to each node is 4. The time complexity of this algorithm can be up to O(n^n) but will be much lower in practice due to the constraints. The space complexity is O(n).

## A solution in C++

```cpp
#include <vector>
#include <unordered_set>
using namespace std;

int maxQualityRec(const vector<vector<int>>& adjMatrix, const vector<int>& values, int node, int timeLeft, unordered_set<int>& visited) {
    if (timeLeft < 0) {
        return INT_MIN;
    }

    int maxQuality = 0;
    visited.insert(node);
    for (int i = 0; i < adjMatrix[node].size(); ++i) {
        if (adjMatrix[node][i] != -1) {
            int time = adjMatrix[node][i];
            int oldValue = adjMatrix[node][i];
            adjMatrix[node][i] = adjMatrix[i][node] = -1;
            maxQuality = max(maxQuality, maxQualityRec(adjMatrix, values, i, timeLeft - time, visited));
            adjMatrix[node][i] = adjMatrix[i][node] = oldValue;
        }
    }
    visited.erase(node);
    return maxQuality + (visited.count(node + 1) == 0 ? values[node] : 0);
}

int maxQuality(int n, const vector<int>& values, const vector<vector<int>>& edges, int maxTime) {
    vector<vector<int>> adjMatrix(n, vector<int>(n, -1));
    for (const auto& edge : edges) {
        adjMatrix[edge[0]][edge[1]] = adjMatrix[edge[1]][edge[0]] = edge[2];
    }

    unordered_set<int> visited;
    return maxQualityRec(adjMatrix, values, 0, maxTime, visited);
}
```
The algorithm uses a backtracking approach with depth-first search. It starts from node `0` and recursively traverses through the graph while keeping track of visited nodes in a hash set. For each neighboring node, it updates the adjacency matrix (or adjacency dictionary in Python) to account for the travel time between the two nodes. After exploring the path, the algorithm backtracks by resetting the changes made to the adjacency matrix (or adjacency dictionary) and removing the current node from the visited nodes set.

The base case is when the timeLeft is less than zero, which indicates that the path exceeds the maxTime, so it returns INT_MIN (or float('-inf') in Python) to discard this path. After exploring all possible paths, the function returns the maximum quality found in valid paths. The quality of a path is calculated as the sum of values of the unique nodes visited in the path.

Note that the maximum number of edges connected to each node is 4. The time complexity of this algorithm can be up to O(n^n) but will be much lower in practice due to the constraints. The space complexity is O(n).

## A solution in Python

```python
from collections import defaultdict

def maxQualityRec(adjDict, values, node, timeLeft, visited):
    if timeLeft < 0:
        return float('-inf')

    maxQuality = 0
    visited.add(node)
    for neighbor, time in adjDict[node]:
        adjDict[neighbor].remove((node, time))
        maxQuality = max(maxQuality, maxQualityRec(adjDict, values, neighbor, timeLeft - time, visited))
        adjDict[neighbor].append((node, time))

    visited.remove(node)
    return maxQuality + (values[node] if node not in visited else 0)

def maxQuality(n, values, edges, maxTime):
    adjDict = defaultdict(list)
    for u, v, time in edges:
        adjDict[u].append((v, time))
        adjDict[v].append((u, time))

    visited = set()
    return maxQualityRec(adjDict, values, 0, maxTime, visited)
```
The algorithm uses a backtracking approach with depth-first search. It starts from node `0` and recursively traverses through the graph while keeping track of visited nodes in a hash set. For each neighboring node, it updates the adjacency matrix (or adjacency dictionary in Python) to account for the travel time between the two nodes. After exploring the path, the algorithm backtracks by resetting the changes made to the adjacency matrix (or adjacency dictionary) and removing the current node from the visited nodes set.

The base case is when the timeLeft is less than zero, which indicates that the path exceeds the maxTime, so it returns INT_MIN (or float('-inf') in Python) to discard this path. After exploring all possible paths, the function returns the maximum quality found in valid paths. The quality of a path is calculated as the sum of values of the unique nodes visited in the path.

Note that the maximum number of edges connected to each node is 4. The time complexity of this algorithm can be up to O(n^n) but will be much lower in practice due to the constraints. The space complexity is O(n).

## A solution in Javascript

```javascript
function maxQualityRec(adjMatrix, values, node, timeLeft, visited) {
    if (timeLeft < 0) {
        return Number.MIN_SAFE_INTEGER;
    }

    let maxQuality = 0;
    visited.add(node);
    for (let i = 0; i < adjMatrix[node].length; ++i) {
        if (adjMatrix[node][i] !== -1) {
            let time = adjMatrix[node][i];
            let oldValue = adjMatrix[node][i];
            adjMatrix[node][i] = adjMatrix[i][node] = -1;
            maxQuality = Math.max(maxQuality, maxQualityRec(adjMatrix, values, i, timeLeft - time, visited));
            adjMatrix[node][i] = adjMatrix[i][node] = oldValue;
        }
    }
    visited.delete(node);
    return maxQuality + (visited.has(node + 1) ? 0 : values[node]);
}

function maxQuality(n, values, edges, maxTime) {
    let adjMatrix = new Array(n).fill(null).map(() => new Array(n).fill(-1));

    for (let edge of edges) {
        adjMatrix[edge[0]][edge[1]] = adjMatrix[edge[1]][edge[0]] = edge[2];
    }

    let visited = new Set();
    return maxQualityRec(adjMatrix, values, 0, maxTime, visited);
}
```
The algorithm uses a backtracking approach with depth-first search. It starts from node `0` and recursively traverses through the graph while keeping track of visited nodes in a hash set. For each neighboring node, it updates the adjacency matrix (or adjacency dictionary in Python) to account for the travel time between the two nodes. After exploring the path, the algorithm backtracks by resetting the changes made to the adjacency matrix (or adjacency dictionary) and removing the current node from the visited nodes set.

The base case is when the timeLeft is less than zero, which indicates that the path exceeds the maxTime, so it returns INT_MIN (or float('-inf') in Python) to discard this path. After exploring all possible paths, the function returns the maximum quality found in valid paths. The quality of a path is calculated as the sum of values of the unique nodes visited in the path.

Note that the maximum number of edges connected to each node is 4. The time complexity of this algorithm can be up to O(n^n) but will be much lower in practice due to the constraints. The space complexity is O(n).


# Most Frequent Number Following Key In an Array

- slug: most-frequent-number-following-key-in-an-array
- difficulty: Easy

You are given a **0-indexed** integer array `nums`. You are also given an integer `key`, which is present in `nums`.

For every unique integer `target` in `nums`, **count** the number of times `target` immediately follows an occurrence of `key` in `nums`. In other words, count the number of indices `i` such that:

*   `0 <= i <= nums.length - 2`,
*   `nums[i] == key` and,
*   `nums[i + 1] == target`.

Return _the_ `target` _with the **maximum** count_. The test cases will be generated such that the `target` with maximum count is unique.

**Example 1:**

**Input:** nums = \[1,100,200,1,100\], key = 1
**Output:** 100
**Explanation:** For target = 100, there are 2 occurrences at indices 1 and 4 which follow an occurrence of key.
No other integers follow an occurrence of key, so we return 100.

**Example 2:**

**Input:** nums = \[2,2,2,2,3\], key = 2
**Output:** 2
**Explanation:** For target = 2, there are 3 occurrences at indices 1, 2, and 3 which follow an occurrence of key.
For target = 3, there is only one occurrence at index 4 which follows an occurrence of key.
target = 2 has the maximum number of occurrences following an occurrence of key, so we return 2.

**Constraints:**

*   `2 <= nums.length <= 1000`
*   `1 <= nums[i] <= 1000`
*   The test cases will be generated such that the answer is unique.

## A solution in Java

```java
import java.util.HashMap;
import java.util.Map;

public int countOnceInBoth(String[] words1, String[] words2) {
    Map<String, Integer> counter1 = new HashMap<>();
    Map<String, Integer> counter2 = new HashMap<>();

    for (String word : words1)
        counter1.put(word, counter1.getOrDefault(word, 0) + 1);
    for (String word : words2)
        counter2.put(word, counter2.getOrDefault(word, 0) + 1);

    int count = 0;
    for (Map.Entry<String, Integer> item : counter1.entrySet())
        if (item.getValue() == 1 && counter2.getOrDefault(item.getKey(), 0) == 1)
            count++;

    return count;
}
```
1. Create two hashmaps (counter1 and counter2) to store the frequency of each word in words1 and words2, respectively.
2. Iterate over the two arrays and increase the word count within their respective hashmap.
3. Initialize a count variable to 0.
4. Iterate over the entries in counter1, checking both its value and the value in counter2 for that key (word) against 1. If both are equal to 1, increment the count.
5. Return the final count.

## A solution in C++

```cpp
#include <vector>
#include <string>
#include <unordered_map>

int countOnceInBoth(const std::vector<std::string>& words1, const std::vector<std::string>& words2) {
    std::unordered_map<std::string, int> counter1, counter2;

    for (const auto& word : words1)
        counter1[word]++;
    for (const auto& word : words2)
        counter2[word]++;

    int count = 0;
    for (const auto& item : counter1)
        if (item.second == 1 && counter2[item.first] == 1)
            count++;

    return count;
}
```
1. Create two hashmaps (counter1 and counter2) to store the frequency of each word in words1 and words2, respectively.
2. Iterate over the two arrays and increase the word count within their respective hashmap.
3. Initialize a count variable to 0.
4. Iterate over the entries in counter1, checking both its value and the value in counter2 for that key (word) against 1. If both are equal to 1, increment the count.
5. Return the final count.

## A solution in Python

```python
def count_once_in_both(words1, words2):
    counter1 = {}
    counter2 = {}

    for word in words1:
        counter1[word] = counter1.get(word, 0) + 1
    for word in words2:
        counter2[word] = counter2.get(word, 0) + 1

    count = 0
    for item in counter1.items():
        if item[1] == 1 and counter2.get(item[0], 0) == 1:
            count += 1

    return count
```
1. Create two hashmaps (counter1 and counter2) to store the frequency of each word in words1 and words2, respectively.
2. Iterate over the two arrays and increase the word count within their respective hashmap.
3. Initialize a count variable to 0.
4. Iterate over the entries in counter1, checking both its value and the value in counter2 for that key (word) against 1. If both are equal to 1, increment the count.
5. Return the final count.

## A solution in Javascript

```javascript
function countOnceInBoth(words1, words2) {
    const counter1 = {};
    const counter2 = {};

    for (const word of words1)
        counter1[word] = (counter1[word] || 0) + 1;
    for (const word of words2)
        counter2[word] = (counter2[word] || 0) + 1;

    let count = 0;
    for (const item in counter1)
        if (counter1[item] === 1 && counter2[item] === 1)
            count++;

    return count;
}
```
1. Create two hashmaps (counter1 and counter2) to store the frequency of each word in words1 and words2, respectively.
2. Iterate over the two arrays and increase the word count within their respective hashmap.
3. Initialize a count variable to 0.
4. Iterate over the entries in counter1, checking both its value and the value in counter2 for that key (word) against 1. If both are equal to 1, increment the count.
5. Return the final count.


# Sort the Jumbled Numbers

- slug: sort-the-jumbled-numbers
- difficulty: Medium

You are given a **0-indexed** integer array `mapping` which represents the mapping rule of a shuffled decimal system. `mapping[i] = j` means digit `i` should be mapped to digit `j` in this system.

The **mapped value** of an integer is the new integer obtained by replacing each occurrence of digit `i` in the integer with `mapping[i]` for all `0 <= i <= 9`.

You are also given another integer array `nums`. Return _the array_ `nums` _sorted in **non-decreasing** order based on the **mapped values** of its elements._

**Notes:**

*   Elements with the same mapped values should appear in the **same relative order** as in the input.
*   The elements of `nums` should only be sorted based on their mapped values and **not be replaced** by them.

**Example 1:**

**Input:** mapping = \[8,9,4,0,2,1,3,5,7,6\], nums = \[991,338,38\]
**Output:** \[338,38,991\]
**Explanation:**
Map the number 991 as follows:
1. mapping\[9\] = 6, so all occurrences of the digit 9 will become 6.
2. mapping\[1\] = 9, so all occurrences of the digit 1 will become 9.
Therefore, the mapped value of 991 is 669.
338 maps to 007, or 7 after removing the leading zeros.
38 maps to 07, which is also 7 after removing leading zeros.
Since 338 and 38 share the same mapped value, they should remain in the same relative order, so 338 comes before 38.
Thus, the sorted array is \[338,38,991\].

**Example 2:**

**Input:** mapping = \[0,1,2,3,4,5,6,7,8,9\], nums = \[789,456,123\]
**Output:** \[123,456,789\]
**Explanation:** 789 maps to 789, 456 maps to 456, and 123 maps to 123. Thus, the sorted array is \[123,456,789\].

**Constraints:**

*   `mapping.length == 10`
*   `0 <= mapping[i] <= 9`
*   All the values of `mapping[i]` are **unique**.
*   `1 <= nums.length <= 3 * 104`
*   `0 <= nums[i] < 109`

## A solution in Java

```java
int minBuckets(String street) {
    int buckets = 0, i = 0, n = street.length();
    while(i < n) {
        if(street.charAt(i) == 'H') {
            if (i + 1 < n && street.charAt(i+1) == '.') {
                buckets++;
                i += 2;
            } else if (i + 2 < n && street.charAt(i+2) == '.') {
                buckets++;
                i += 3;
            } else {
                return -1;
            }
        } else {
            i += 1;
        }
    }
    return buckets;
}
```
The algorithm starts by initializing variables: a `buckets` counter, the current index `i`, and the length of the street `n`.

While `i` is less than the length of the street `n`, the algorithm checks for houses (the character 'H') at the current index. If there's a house, it then checks for a bucket (empty space represented by '.') in its one or two indices away, respectively. If a bucket location is found, we increment the `buckets` counter and update the index `i`. If no suitable bucket location is found, it means that it's impossible, and the algorithm returns -1.

When the index `i` is on an empty space, the algorithm simply moves to the next index `i + 1`.

The algorithm continues until the end of the string `street` is reached, and it returns the `buckets` counter as the minimum number of buckets needed.

## A solution in C++

```cpp
int minBuckets(string street) {
    int buckets = 0, i = 0, n = street.size();
    while(i < n) {
        if(street[i] == 'H') {
            if (i + 1 < n && street[i+1] == '.') {
                buckets++;
                i += 2;
            } else if (i + 2 < n && street[i+2] == '.') {
                buckets++;
                i += 3;
            } else {
                return -1;
            }
        } else {
            i += 1;
        }
    }
    return buckets;
}
```
The algorithm starts by initializing variables: a `buckets` counter, the current index `i`, and the length of the street `n`.

While `i` is less than the length of the street `n`, the algorithm checks for houses (the character 'H') at the current index. If there's a house, it then checks for a bucket (empty space represented by '.') in its one or two indices away, respectively. If a bucket location is found, we increment the `buckets` counter and update the index `i`. If no suitable bucket location is found, it means that it's impossible, and the algorithm returns -1.

When the index `i` is on an empty space, the algorithm simply moves to the next index `i + 1`.

The algorithm continues until the end of the string `street` is reached, and it returns the `buckets` counter as the minimum number of buckets needed.

## A solution in Python

```python
def min_buckets(street):
    buckets = 0
    i = 0
    n = len(street)
    while i < n:
        if street[i] == 'H':
            if i + 1 < n and street[i + 1] == '.':
                buckets += 1
                i += 2
            elif i + 2 < n and street[i + 2] == '.':
                buckets += 1
                i += 3
            else:
                return -1
        else:
            i += 1
    return buckets
```
The algorithm starts by initializing variables: a `buckets` counter, the current index `i`, and the length of the street `n`.

While `i` is less than the length of the street `n`, the algorithm checks for houses (the character 'H') at the current index. If there's a house, it then checks for a bucket (empty space represented by '.') in its one or two indices away, respectively. If a bucket location is found, we increment the `buckets` counter and update the index `i`. If no suitable bucket location is found, it means that it's impossible, and the algorithm returns -1.

When the index `i` is on an empty space, the algorithm simply moves to the next index `i + 1`.

The algorithm continues until the end of the string `street` is reached, and it returns the `buckets` counter as the minimum number of buckets needed.

## A solution in Javascript

```javascript
function minBuckets(street) {
    let buckets = 0, i = 0, n = street.length;
    while(i < n) {
        if(street[i] === 'H') {
            if (i + 1 < n && street[i+1] === '.') {
                buckets++;
                i += 2;
            } else if (i + 2 < n && street[i+2] === '.') {
                buckets++;
                i += 3;
            } else {
                return -1;
            }
        } else {
            i += 1;
        }
    }
    return buckets;
}
```
The algorithm starts by initializing variables: a `buckets` counter, the current index `i`, and the length of the street `n`.

While `i` is less than the length of the street `n`, the algorithm checks for houses (the character 'H') at the current index. If there's a house, it then checks for a bucket (empty space represented by '.') in its one or two indices away, respectively. If a bucket location is found, we increment the `buckets` counter and update the index `i`. If no suitable bucket location is found, it means that it's impossible, and the algorithm returns -1.

When the index `i` is on an empty space, the algorithm simply moves to the next index `i + 1`.

The algorithm continues until the end of the string `street` is reached, and it returns the `buckets` counter as the minimum number of buckets needed.


# All Ancestors of a Node in a Directed Acyclic Graph

- slug: all-ancestors-of-a-node-in-a-directed-acyclic-graph
- difficulty: Medium

You are given a positive integer `n` representing the number of nodes of a **Directed Acyclic Graph** (DAG). The nodes are numbered from `0` to `n - 1` (**inclusive**).

You are also given a 2D integer array `edges`, where `edges[i] = [fromi, toi]` denotes that there is a **unidirectional** edge from `fromi` to `toi` in the graph.

Return _a list_ `answer`_, where_ `answer[i]` _is the **list of ancestors** of the_ `ith` _node, sorted in **ascending order**_.

A node `u` is an **ancestor** of another node `v` if `u` can reach `v` via a set of edges.

**Example 1:**

**Input:** n = 8, edgeList = \[\[0,3\],\[0,4\],\[1,3\],\[2,4\],\[2,7\],\[3,5\],\[3,6\],\[3,7\],\[4,6\]\]
**Output:** \[\[\],\[\],\[\],\[0,1\],\[0,2\],\[0,1,3\],\[0,1,2,3,4\],\[0,1,2,3\]\]
**Explanation:**
The above diagram represents the input graph.
- Nodes 0, 1, and 2 do not have any ancestors.
- Node 3 has two ancestors 0 and 1.
- Node 4 has two ancestors 0 and 2.
- Node 5 has three ancestors 0, 1, and 3.
- Node 6 has five ancestors 0, 1, 2, 3, and 4.
- Node 7 has four ancestors 0, 1, 2, and 3.

**Example 2:**

**Input:** n = 5, edgeList = \[\[0,1\],\[0,2\],\[0,3\],\[0,4\],\[1,2\],\[1,3\],\[1,4\],\[2,3\],\[2,4\],\[3,4\]\]
**Output:** \[\[\],\[0\],\[0,1\],\[0,1,2\],\[0,1,2,3\]\]
**Explanation:**
The above diagram represents the input graph.
- Node 0 does not have any ancestor.
- Node 1 has one ancestor 0.
- Node 2 has two ancestors 0 and 1.
- Node 3 has three ancestors 0, 1, and 2.
- Node 4 has four ancestors 0, 1, 2, and 3.

**Constraints:**

*   `1 <= n <= 1000`
*   `0 <= edges.length <= min(2000, n * (n - 1) / 2)`
*   `edges[i].length == 2`
*   `0 <= fromi, toi <= n - 1`
*   `fromi != toi`
*   There are no duplicate edges.
*   The graph is **directed** and **acyclic**.

## A solution in Java

```java
public int minCost(int[][] grid, int[] startPos, int[] homePos, int[] rowCosts, int[] colCosts) {
    return Math.abs(rowCosts[startPos[0]] - rowCosts[homePos[0]]) + Math.abs(colCosts[startPos[1]] - colCosts[homePos[1]]);
}
```
The problem can be solved by finding the differences in row and column costs between the current position of the robot (`startPos`) and the home position (`homePos`). Since we just need to move the robot along the row and the column, the total minimum cost for the robot to return home is simply the sum of the absolute differences of row costs and column costs between the start and home positions. This results in an `O(1)` time complexity.

## A solution in C++

```cpp
#include <vector>
using namespace std;

int minCost(vector<vector<int>>& grid, vector<int>& startPos, vector<int>& homePos, vector<int>& rowCosts, vector<int>& colCosts) {
    return abs(rowCosts[startPos[0]] - rowCosts[homePos[0]]) + abs(colCosts[startPos[1]] - colCosts[homePos[1]]);
}
```
The problem can be solved by finding the differences in row and column costs between the current position of the robot (`startPos`) and the home position (`homePos`). Since we just need to move the robot along the row and the column, the total minimum cost for the robot to return home is simply the sum of the absolute differences of row costs and column costs between the start and home positions. This results in an `O(1)` time complexity.

## A solution in Python

```python
def min_cost(grid, start_pos, home_pos, row_costs, col_costs):
    return abs(row_costs[start_pos[0]] - row_costs[home_pos[0]]) + abs(col_costs[start_pos[1]] - col_costs[home_pos[1]])
```
The problem can be solved by finding the differences in row and column costs between the current position of the robot (`startPos`) and the home position (`homePos`). Since we just need to move the robot along the row and the column, the total minimum cost for the robot to return home is simply the sum of the absolute differences of row costs and column costs between the start and home positions. This results in an `O(1)` time complexity.

## A solution in Javascript

```javascript
function minCost(grid, startPos, homePos, rowCosts, colCosts) {
    return Math.abs(rowCosts[startPos[0]] - rowCosts[homePos[0]]) + Math.abs(colCosts[startPos[1]] - colCosts[homePos[1]]);
}
```
The problem can be solved by finding the differences in row and column costs between the current position of the robot (`startPos`) and the home position (`homePos`). Since we just need to move the robot along the row and the column, the total minimum cost for the robot to return home is simply the sum of the absolute differences of row costs and column costs between the start and home positions. This results in an `O(1)` time complexity.


# Minimum Number of Moves to Make Palindrome

- slug: minimum-number-of-moves-to-make-palindrome
- difficulty: Hard

You are given a string `s` consisting only of lowercase English letters.

In one **move**, you can select any two **adjacent** characters of `s` and swap them.

Return _the **minimum number of moves** needed to make_ `s` _a palindrome_.

**Note** that the input will be generated such that `s` can always be converted to a palindrome.

**Example 1:**

**Input:** s =  "aabb "
**Output:** 2
**Explanation:**
We can obtain two palindromes from s,  "abba " and  "baab ".
- We can obtain  "abba " from s in 2 moves:  "a**ab**b " ->  "ab**ab** " ->  "abba ".
- We can obtain  "baab " from s in 2 moves:  "a**ab**b " ->  "**ab**ab " ->  "baab ".
Thus, the minimum number of moves needed to make s a palindrome is 2.

**Example 2:**

**Input:** s =  "letelt "
**Output:** 2
**Explanation:**
One of the palindromes we can obtain from s in 2 moves is  "lettel ".
One of the ways we can obtain it is  "lete**lt** " ->  "let**et**l " ->  "lettel ".
Other palindromes such as  "tleelt " can also be obtained in 2 moves.
It can be shown that it is not possible to obtain a palindrome in less than 2 moves.

**Constraints:**

*   `1 <= s.length <= 2000`
*   `s` consists only of lowercase English letters.
*   `s` can be converted to a palindrome using a finite number of moves.

## A solution in Java

```java
public int countPyramids(int[][] grid) {
    int m = grid.length, n = grid[0].length, count = 0;
    for (int i = 1; i < m - 1; ++i) {
        for (int j = 1; j < n - 1; ++j) {
            if (grid[i][j] == grid[i - 1][j] + grid[i][j - 1] - grid[i - 1][j - 1]
                && grid[i][j] == grid[i + 1][j] + grid[i][j + 1] - grid[i + 1][j + 1]) {
                count += grid[i][j];
            }
        }
    }
    return count;
}
```
We iterate through each cell of the grid, and check for both pyramidal and inverse pyramidal plots in a single condition. For a given cell (i, j), we check the sum of neighboring cells both diagonally and horizontally.

The condition `grid[i][j] == grid[i - 1][j] + grid[i][j - 1] - grid[i - 1][j - 1]` checks the pyramid structure by looking at its vertices. If the vertices are barren and the central cell is fertile, this condition is satisfied.

Similarly, the condition `grid[i][j] == grid[i + 1][j] + grid[i][j + 1] - grid[i + 1][j + 1]` checks the inverse pyramid structure by looking at its vertices. If the vertices are fertile and the central cell is barren, this condition is satisfied.

Hence both conditions combined check for both pyramidal and inverse pyramidal plots. If both conditions are satisfied, we just increment the count by the value of the current cell in the grid (either 0 or 1). We repeat this process for all cells and return the final count.

## A solution in C++

```cpp
int countPyramids(vector<vector<int>> &grid) {
    int m = grid.size(), n = grid[0].size(), count = 0;
    for (int i = 1; i < m - 1; ++i) {
        for (int j = 1; j < n - 1; ++j) {
            if (grid[i][j] == grid[i - 1][j] + grid[i][j - 1] - grid[i - 1][j - 1]
                && grid[i][j] == grid[i + 1][j] + grid[i][j + 1] - grid[i + 1][j + 1]) {
                count += grid[i][j];
            }
        }
    }
    return count;
}
```
We iterate through each cell of the grid, and check for both pyramidal and inverse pyramidal plots in a single condition. For a given cell (i, j), we check the sum of neighboring cells both diagonally and horizontally.

The condition `grid[i][j] == grid[i - 1][j] + grid[i][j - 1] - grid[i - 1][j - 1]` checks the pyramid structure by looking at its vertices. If the vertices are barren and the central cell is fertile, this condition is satisfied.

Similarly, the condition `grid[i][j] == grid[i + 1][j] + grid[i][j + 1] - grid[i + 1][j + 1]` checks the inverse pyramid structure by looking at its vertices. If the vertices are fertile and the central cell is barren, this condition is satisfied.

Hence both conditions combined check for both pyramidal and inverse pyramidal plots. If both conditions are satisfied, we just increment the count by the value of the current cell in the grid (either 0 or 1). We repeat this process for all cells and return the final count.

## A solution in Python

```python
def count_pyramids(grid):
    m, n, count = len(grid), len(grid[0]), 0
    for i in range(1, m - 1):
        for j in range(1, n - 1):
            if grid[i][j] == grid[i - 1][j] + grid[i][j - 1] - grid[i - 1][j - 1] \
                and grid[i][j] == grid[i + 1][j] + grid[i][j + 1] - grid[i + 1][j + 1]:
                count += grid[i][j]
    return count
```
We iterate through each cell of the grid, and check for both pyramidal and inverse pyramidal plots in a single condition. For a given cell (i, j), we check the sum of neighboring cells both diagonally and horizontally.

The condition `grid[i][j] == grid[i - 1][j] + grid[i][j - 1] - grid[i - 1][j - 1]` checks the pyramid structure by looking at its vertices. If the vertices are barren and the central cell is fertile, this condition is satisfied.

Similarly, the condition `grid[i][j] == grid[i + 1][j] + grid[i][j + 1] - grid[i + 1][j + 1]` checks the inverse pyramid structure by looking at its vertices. If the vertices are fertile and the central cell is barren, this condition is satisfied.

Hence both conditions combined check for both pyramidal and inverse pyramidal plots. If both conditions are satisfied, we just increment the count by the value of the current cell in the grid (either 0 or 1). We repeat this process for all cells and return the final count.

## A solution in Javascript

```javascript
function countPyramids(grid) {
    const m = grid.length, n = grid[0].length;
    let count = 0;
    for (let i = 1; i < m - 1; ++i) {
        for (let j = 1; j < n - 1; ++j) {
            if (grid[i][j] === grid[i - 1][j] + grid[i][j - 1] - grid[i - 1][j - 1]
                && grid[i][j] === grid[i + 1][j] + grid[i][j + 1] - grid[i + 1][j + 1]) {
                count += grid[i][j];
            }
        }
    }
    return count;
}
```
We iterate through each cell of the grid, and check for both pyramidal and inverse pyramidal plots in a single condition. For a given cell (i, j), we check the sum of neighboring cells both diagonally and horizontally.

The condition `grid[i][j] == grid[i - 1][j] + grid[i][j - 1] - grid[i - 1][j - 1]` checks the pyramid structure by looking at its vertices. If the vertices are barren and the central cell is fertile, this condition is satisfied.

Similarly, the condition `grid[i][j] == grid[i + 1][j] + grid[i][j + 1] - grid[i + 1][j + 1]` checks the inverse pyramid structure by looking at its vertices. If the vertices are fertile and the central cell is barren, this condition is satisfied.

Hence both conditions combined check for both pyramidal and inverse pyramidal plots. If both conditions are satisfied, we just increment the count by the value of the current cell in the grid (either 0 or 1). We repeat this process for all cells and return the final count.


# Cells in a Range on an Excel Sheet

- slug: cells-in-a-range-on-an-excel-sheet
- difficulty: Easy

A cell `(r, c)` of an excel sheet is represented as a string `" "` where:

*   denotes the column number `c` of the cell. It is represented by **alphabetical letters**.
    *   For example, the `1st` column is denoted by `'A'`, the `2nd` by `'B'`, the `3rd` by `'C'`, and so on.
*   is the row number `r` of the cell. The `rth` row is represented by the **integer** `r`.

You are given a string `s` in the format `": "`, where represents the column `c1`, represents the row `r1`, represents the column `c2`, and represents the row `r2`, such that `r1 <= r2` and `c1 <= c2`.

Return _the **list of cells**_ `(x, y)` _such that_ `r1 <= x <= r2` _and_ `c1 <= y <= c2`. The cells should be represented as **strings** in the format mentioned above and be sorted in **non-decreasing** order first by columns and then by rows.

**Example 1:**

**Input:** s =  "K1:L2 "
**Output:** \[ "K1 ", "K2 ", "L1 ", "L2 "\]
**Explanation:**
The above diagram shows the cells which should be present in the list.
The red arrows denote the order in which the cells should be presented.

**Example 2:**

**Input:** s =  "A1:F1 "
**Output:** \[ "A1 ", "B1 ", "C1 ", "D1 ", "E1 ", "F1 "\]
**Explanation:**
The above diagram shows the cells which should be present in the list.
The red arrow denotes the order in which the cells should be presented.

**Constraints:**

*   `s.length == 5`
*   `'A' <= s[0] <= s[3] <= 'Z'`
*   `'1' <= s[1] <= s[4] <= '9'`
*   `s` consists of uppercase English letters, digits and `':'`.

## A solution in Java

```java
import java.util.ArrayList;
import java.util.List;

public List<String> cellRange(String s) {
    int r1 = s.charAt(1) - '0';
    int r2 = s.charAt(4) - '0';
    int c1 = s.charAt(0) - 'A' + 1;
    int c2 = s.charAt(3) - 'A' + 1;

    List<String> res = new ArrayList<>();
    for (int c = c1; c <= c2; ++c) {
        for (int r = r1; r <= r2; ++r) {
            res.add((char)('A' + c - 1) + Integer.toString(r));
        }
    }
    return res;
}
```
The algorithm is relatively straightforward: First, extract each cell's row and column from the input string `s` using indexed access on the input string, which works identically in all languages. The row values are parsed from a character to the integer it represents. The column values need to be zero-indexed and then shifted by 1, so subtract the ASCII value of 'A' (or 'A'.charCodeAt(0) in JavaScript) and then add 1.

Next, create a nested loop to iterate over all columns (`c`) and rows (`r`). In the inner loop, push the column and row as a formatted string to the results array, reusing the method from the column extraction to create the column character for output.

Finally, return the array of sorted cell strings.

## A solution in C++

```cpp
#include <vector>
#include <string>

std::vector<std::string> cellRange(const std::string& s) {
    int r1 = s[1] - '0';
    int r2 = s[4] - '0';
    int c1 = s[0] - 'A' + 1;
    int c2 = s[3] - 'A' + 1;

    std::vector<std::string> res;
    for (int c = c1; c <= c2; ++c) {
        for (int r = r1; r <= r2; ++r) {
            res.push_back(std::string(1, 'A' + c - 1) + std::to_string(r));
        }
    }
    return res;
}
```
The algorithm is relatively straightforward: First, extract each cell's row and column from the input string `s` using indexed access on the input string, which works identically in all languages. The row values are parsed from a character to the integer it represents. The column values need to be zero-indexed and then shifted by 1, so subtract the ASCII value of 'A' (or 'A'.charCodeAt(0) in JavaScript) and then add 1.

Next, create a nested loop to iterate over all columns (`c`) and rows (`r`). In the inner loop, push the column and row as a formatted string to the results array, reusing the method from the column extraction to create the column character for output.

Finally, return the array of sorted cell strings.

## A solution in Python

```python
def cell_range(s):
    r1 = int(s[1])
    r2 = int(s[4])
    c1 = ord(s[0]) - ord('A') + 1
    c2 = ord(s[3]) - ord('A') + 1

    res = []
    for c in range(c1, c2 + 1):
        for r in range(r1, r2 + 1):
            res.append(chr(ord('A') + c - 1) + str(r))
    return res
```
The algorithm is relatively straightforward: First, extract each cell's row and column from the input string `s` using indexed access on the input string, which works identically in all languages. The row values are parsed from a character to the integer it represents. The column values need to be zero-indexed and then shifted by 1, so subtract the ASCII value of 'A' (or 'A'.charCodeAt(0) in JavaScript) and then add 1.

Next, create a nested loop to iterate over all columns (`c`) and rows (`r`). In the inner loop, push the column and row as a formatted string to the results array, reusing the method from the column extraction to create the column character for output.

Finally, return the array of sorted cell strings.

## A solution in Javascript

```javascript
function cellRange(s) {
    const r1 = parseInt(s[1]);
    const r2 = parseInt(s[4]);
    const c1 = s.charCodeAt(0) - 'A'.charCodeAt(0) + 1;
    const c2 = s.charCodeAt(3) - 'A'.charCodeAt(0) + 1;

    const res = [];
    for (let c = c1; c <= c2; ++c) {
        for (let r = r1; r <= r2; ++r) {
            res.push(String.fromCharCode('A'.charCodeAt(0) + c - 1) + r.toString());
        }
    }
    return res;
}
```
The algorithm is relatively straightforward: First, extract each cell's row and column from the input string `s` using indexed access on the input string, which works identically in all languages. The row values are parsed from a character to the integer it represents. The column values need to be zero-indexed and then shifted by 1, so subtract the ASCII value of 'A' (or 'A'.charCodeAt(0) in JavaScript) and then add 1.

Next, create a nested loop to iterate over all columns (`c`) and rows (`r`). In the inner loop, push the column and row as a formatted string to the results array, reusing the method from the column extraction to create the column character for output.

Finally, return the array of sorted cell strings.


# Append K Integers With Minimal Sum

- slug: append-k-integers-with-minimal-sum
- difficulty: Medium

You are given an integer array `nums` and an integer `k`. Append `k` **unique positive** integers that do **not** appear in `nums` to `nums` such that the resulting total sum is **minimum**.

Return _the sum of the_ `k` _integers appended to_ `nums`.

**Example 1:**

**Input:** nums = \[1,4,25,10,25\], k = 2
**Output:** 5
**Explanation:** The two unique positive integers that do not appear in nums which we append are 2 and 3.
The resulting sum of nums is 1 + 4 + 25 + 10 + 25 + 2 + 3 = 70, which is the minimum.
The sum of the two integers appended is 2 + 3 = 5, so we return 5.

**Example 2:**

**Input:** nums = \[5,6\], k = 6
**Output:** 25
**Explanation:** The six unique positive integers that do not appear in nums which we append are 1, 2, 3, 4, 7, and 8.
The resulting sum of nums is 5 + 6 + 1 + 2 + 3 + 4 + 7 + 8 = 36, which is the minimum.
The sum of the six integers appended is 1 + 2 + 3 + 4 + 7 + 8 = 25, so we return 25.

**Constraints:**

*   `1 <= nums.length <= 105`
*   `1 <= nums[i] <= 109`
*   `1 <= k <= 108`

## A solution in Java

```java
public int timeToBuyTickets(int[] tickets, int k) {
    int time = 0;
    while (tickets[k] > 0) {
        for (int i = 0; i < tickets.length; i++) {
            if (tickets[i] > 0) {
                tickets[i]--;
                time++;
                if (i == k && tickets[k] == 0)
                    return time;
            }
        }
    }
    return time;
}
```
The algorithm iterates through the people in line and, for each person, it decrements the number of desired tickets if the person still needs to buy tickets. Then, it increments the time variable to account for the time taken to buy the ticket. If the current person is the target person (at position k) and they have finished buying tickets (tickets[k] == 0), the function returns the current time.

The outer while-loop ensures that the process continues until the target person at position k has bought all the desired tickets. When all the people in line have bought the necessary tickets, the loop stops, and the time variable is returned as the result.

## A solution in C++

```cpp
int timeToBuyTickets(vector<int>& tickets, int k) {
    int time = 0;
    while (tickets[k] > 0) {
        for (int i = 0; i < tickets.size(); i++) {
            if (tickets[i] > 0) {
                tickets[i]--;
                time++;
                if (i == k && tickets[k] == 0)
                    return time;
            }
        }
    }
    return time;
}
```
The algorithm iterates through the people in line and, for each person, it decrements the number of desired tickets if the person still needs to buy tickets. Then, it increments the time variable to account for the time taken to buy the ticket. If the current person is the target person (at position k) and they have finished buying tickets (tickets[k] == 0), the function returns the current time.

The outer while-loop ensures that the process continues until the target person at position k has bought all the desired tickets. When all the people in line have bought the necessary tickets, the loop stops, and the time variable is returned as the result.

## A solution in Python

```python
def time_to_buy_tickets(tickets, k):
    time = 0
    while tickets[k] > 0:
        for i in range(len(tickets)):
            if tickets[i] > 0:
                tickets[i] -= 1
                time += 1
                if i == k and tickets[k] == 0:
                    return time
    return time
```
The algorithm iterates through the people in line and, for each person, it decrements the number of desired tickets if the person still needs to buy tickets. Then, it increments the time variable to account for the time taken to buy the ticket. If the current person is the target person (at position k) and they have finished buying tickets (tickets[k] == 0), the function returns the current time.

The outer while-loop ensures that the process continues until the target person at position k has bought all the desired tickets. When all the people in line have bought the necessary tickets, the loop stops, and the time variable is returned as the result.

## A solution in Javascript

```javascript
function timeToBuyTickets(tickets, k) {
    let time = 0;
    while (tickets[k] > 0) {
        for (let i = 0; i < tickets.length; i++) {
            if (tickets[i] > 0) {
                tickets[i]--;
                time++;
                if (i === k && tickets[k] === 0)
                    return time;
            }
        }
    }
    return time;
}
```
The algorithm iterates through the people in line and, for each person, it decrements the number of desired tickets if the person still needs to buy tickets. Then, it increments the time variable to account for the time taken to buy the ticket. If the current person is the target person (at position k) and they have finished buying tickets (tickets[k] == 0), the function returns the current time.

The outer while-loop ensures that the process continues until the target person at position k has bought all the desired tickets. When all the people in line have bought the necessary tickets, the loop stops, and the time variable is returned as the result.


# Create Binary Tree From Descriptions

- slug: create-binary-tree-from-descriptions
- difficulty: Medium

You are given a 2D integer array `descriptions` where `descriptions[i] = [parenti, childi, isLefti]` indicates that `parenti` is the **parent** of `childi` in a **binary** tree of **unique** values. Furthermore,

*   If `isLefti == 1`, then `childi` is the left child of `parenti`.
*   If `isLefti == 0`, then `childi` is the right child of `parenti`.

Construct the binary tree described by `descriptions` and return _its **root**_.

The test cases will be generated such that the binary tree is **valid**.

**Example 1:**

**Input:** descriptions = \[\[20,15,1\],\[20,17,0\],\[50,20,1\],\[50,80,0\],\[80,19,1\]\]
**Output:** \[50,20,80,15,17,19\]
**Explanation:** The root node is the node with value 50 since it has no parent.
The resulting binary tree is shown in the diagram.

**Example 2:**

**Input:** descriptions = \[\[1,2,1\],\[2,3,0\],\[3,4,1\]\]
**Output:** \[1,2,null,null,3,4\]
**Explanation:** The root node is the node with value 1 since it has no parent.
The resulting binary tree is shown in the diagram.

**Constraints:**

*   `1 <= descriptions.length <= 104`
*   `descriptions[i].length == 3`
*   `1 <= parenti, childi <= 105`
*   `0 <= isLefti <= 1`
*   The binary tree described by `descriptions` is valid.

## A solution in Java

```java
public class ListNode {
   int val;
   ListNode next;
   ListNode(int x) { val = x; }
}

public ListNode reverseEvenGroups(ListNode head) {
    ListNode dummy = new ListNode(-1);
    dummy.next = head;
    ListNode prev = dummy, curr = head;
    int count = 0;
    while (curr != null) {
        count++;
        curr = curr.next;
    }
    curr = head;
    for (int i = 2; i <= count; i += 2) {
        ListNode nextGroupHead = curr;
        for (int j = 0; j < i; j++) {
            if (nextGroupHead == null) break;
            nextGroupHead = nextGroupHead.next;
        }
        ListNode prevGroupTail = prev;
        for (int j = 0; j < i; j++) {
            if (curr == null) break;
            ListNode nextNode = curr.next;
            curr.next = prevGroupTail.next;
            prevGroupTail.next = curr;
            curr = nextNode;
        }
        for (int j = 0; j < i; j++) {
            prev = prev.next;
        }
    }
    return dummy.next;
}
```
This algorithm works by first initializing a dummy node that points to the head of the linked list and setting variable `prev` to the dummy node. We will maintain pointers `prev` and `curr`, iterating the linked list and calculating the total number of nodes in it. With the total number of nodes, we can now traverse the list again, reversing every even group.

We use a for loop to traverse the linked list, with the variable `i` representing the length of each even group as we iterate through the loop. For each iteration, we update the head of the next group by moving it `i` positions ahead in the list. We maintain a tail reference to the previous group and a new variable `prevGroupTail`. We then replace the node connections within the group to reverse it by detaching the current node, attaching it to the tail, and updating the tail. After reversing the current group, we move the `prev` pointer ahead by `i` positions.

The algorithm returns the modified linked list with even groups reversed.

## A solution in C++

```cpp
class ListNode {
public:
    int val;
    ListNode *next;
    ListNode(int x) : val(x), next(NULL) {}
};

ListNode* reverseLinkedList(ListNode* head) {
    ListNode *prev = NULL, *curr = head, *next = NULL;
    while (curr != NULL) {
        next = curr->next;
        curr->next = prev;
        prev = curr;
        curr = next;
    }
    return prev;
}

ListNode* reverseEvenGroups(ListNode* head) {
    ListNode *dummy = new ListNode(-1);
    dummy->next = head;
    ListNode *prev = dummy, *curr = head;
    int count = 0;
    while (curr != NULL) {
        count++;
        curr = curr->next;
    }
    curr = head;
    for (int i = 2; i <= count; i = i + 2) {
        ListNode *nextGroupHead = curr;
        for (int j = 0; j < i; j++) {
            if (nextGroupHead == NULL) break;
            nextGroupHead = nextGroupHead->next;
        }
        ListNode *prevGroupTail = prev;
        for (int j = 0; j < i; j++) {
            if (curr == NULL) break;
            ListNode* nextNode = curr->next;
            curr->next = prevGroupTail->next;
            prevGroupTail->next = curr;
            curr = nextNode;
        }
        for (int j = 0; j < i; j++) {
            prev = prev->next;
        }
    }
    return dummy->next;
}
```
This algorithm works by first initializing a dummy node that points to the head of the linked list and setting variable `prev` to the dummy node. We will maintain pointers `prev` and `curr`, iterating the linked list and calculating the total number of nodes in it. With the total number of nodes, we can now traverse the list again, reversing every even group.

We use a for loop to traverse the linked list, with the variable `i` representing the length of each even group as we iterate through the loop. For each iteration, we update the head of the next group by moving it `i` positions ahead in the list. We maintain a tail reference to the previous group and a new variable `prevGroupTail`. We then replace the node connections within the group to reverse it by detaching the current node, attaching it to the tail, and updating the tail. After reversing the current group, we move the `prev` pointer ahead by `i` positions.

The algorithm returns the modified linked list with even groups reversed.

## A solution in Python

```python
class ListNode:
    def __init__(self, x):
        self.val = x
        self.next = None

def reverse_even_groups(head: ListNode) -> ListNode:
    dummy = ListNode(-1)
    dummy.next = head
    prev, curr = dummy, head
    count = 0
    while curr:
        count += 1
        curr = curr.next
    curr = head
    i = 2
    while i <= count:
        next_group_head = curr
        for _ in range(i):
            if not next_group_head:
                break
            next_group_head = next_group_head.next
        prev_group_tail = prev
        for _ in range(i):
            if not curr:
                break
            next_node = curr.next
            curr.next = prev_group_tail.next
            prev_group_tail.next = curr
            curr = next_node
        for _ in range(i):
            prev = prev.next
        i += 2
    return dummy.next
```
This algorithm works by first initializing a dummy node that points to the head of the linked list and setting variable `prev` to the dummy node. We will maintain pointers `prev` and `curr`, iterating the linked list and calculating the total number of nodes in it. With the total number of nodes, we can now traverse the list again, reversing every even group.

We use a for loop to traverse the linked list, with the variable `i` representing the length of each even group as we iterate through the loop. For each iteration, we update the head of the next group by moving it `i` positions ahead in the list. We maintain a tail reference to the previous group and a new variable `prevGroupTail`. We then replace the node connections within the group to reverse it by detaching the current node, attaching it to the tail, and updating the tail. After reversing the current group, we move the `prev` pointer ahead by `i` positions.

The algorithm returns the modified linked list with even groups reversed.

## A solution in Javascript

```javascript
class ListNode {
    constructor(val, next = null) {
        this.val = val;
        this.next = next;
    }
}

function reverseEvenGroups(head) {
    const dummy = new ListNode(-1, head);
    let prev = dummy, curr = head;
    let count = 0;
    while (curr !== null) {
        count++;
        curr = curr.next;
    }
    curr = head;
    for (let i = 2; i <= count; i += 2) {
        let nextGroupHead = curr;
        for (let j = 0; j < i; j++) {
            if (nextGroupHead === null) break;
            nextGroupHead = nextGroupHead.next;
        }
        let prevGroupTail = prev;
        for (let j = 0; j < i; j++) {
            if (curr === null) break;
            const nextNode = curr.next;
            curr.next = prevGroupTail.next;
            prevGroupTail.next = curr;
            curr = nextNode;
        }
        for (let j = 0; j < i; j++) {
            prev = prev.next;
        }
    }
    return dummy.next;
}
```
This algorithm works by first initializing a dummy node that points to the head of the linked list and setting variable `prev` to the dummy node. We will maintain pointers `prev` and `curr`, iterating the linked list and calculating the total number of nodes in it. With the total number of nodes, we can now traverse the list again, reversing every even group.

We use a for loop to traverse the linked list, with the variable `i` representing the length of each even group as we iterate through the loop. For each iteration, we update the head of the next group by moving it `i` positions ahead in the list. We maintain a tail reference to the previous group and a new variable `prevGroupTail`. We then replace the node connections within the group to reverse it by detaching the current node, attaching it to the tail, and updating the tail. After reversing the current group, we move the `prev` pointer ahead by `i` positions.

The algorithm returns the modified linked list with even groups reversed.


# Replace Non-Coprime Numbers in Array

- slug: replace-non-coprime-numbers-in-array
- difficulty: Hard

You are given an array of integers `nums`. Perform the following steps:

1.  Find **any** two **adjacent** numbers in `nums` that are **non-coprime**.
2.  If no such numbers are found, **stop** the process.
3.  Otherwise, delete the two numbers and **replace** them with their **LCM (Least Common Multiple)**.
4.  **Repeat** this process as long as you keep finding two adjacent non-coprime numbers.

Return _the **final** modified array._ It can be shown that replacing adjacent non-coprime numbers in **any** arbitrary order will lead to the same result.

The test cases are generated such that the values in the final array are **less than or equal** to `108`.

Two values `x` and `y` are **non-coprime** if `GCD(x, y) > 1` where `GCD(x, y)` is the **Greatest Common Divisor** of `x` and `y`.

**Example 1:**

**Input:** nums = \[6,4,3,2,7,6,2\]
**Output:** \[12,7,6\]
**Explanation:**
- (6, 4) are non-coprime with LCM(6, 4) = 12. Now, nums = \[**12**,3,2,7,6,2\].
- (12, 3) are non-coprime with LCM(12, 3) = 12. Now, nums = \[**12**,2,7,6,2\].
- (12, 2) are non-coprime with LCM(12, 2) = 12. Now, nums = \[**12**,7,6,2\].
- (6, 2) are non-coprime with LCM(6, 2) = 6. Now, nums = \[12,7,**6**\].
There are no more adjacent non-coprime numbers in nums.
Thus, the final modified array is \[12,7,6\].
Note that there are other ways to obtain the same resultant array.

**Example 2:**

**Input:** nums = \[2,2,1,1,3,3,3\]
**Output:** \[2,1,1,3\]
**Explanation:**
- (3, 3) are non-coprime with LCM(3, 3) = 3. Now, nums = \[2,2,1,1,**3**,3\].
- (3, 3) are non-coprime with LCM(3, 3) = 3. Now, nums = \[2,2,1,1,**3**\].
- (2, 2) are non-coprime with LCM(2, 2) = 2. Now, nums = \[**2**,1,1,3\].
There are no more adjacent non-coprime numbers in nums.
Thus, the final modified array is \[2,1,1,3\].
Note that there are other ways to obtain the same resultant array.

**Constraints:**

*   `1 <= nums.length <= 105`
*   `1 <= nums[i] <= 105`
*   The test cases are generated such that the values in the final array are **less than or equal** to `108`.

## A solution in Java

```java
public String decodeSlantedCipher(String encodedText, int rows) {
    StringBuilder[] matrix = new StringBuilder[rows];
    for(int i = 0; i < rows; i++) {
        matrix[i] = new StringBuilder("");
    }

    int index = 0;
    for(int diagonal = 0; diagonal < 2 * (rows - 1); diagonal++) {
        for(int row = Math.max(0, diagonal - rows + 1); row <= Math.min(diagonal, rows - 1); row++) {
            if(index < encodedText.length()) {
                matrix[row].append(encodedText.charAt(index++));
            }
        }
    }

    StringBuilder originalText = new StringBuilder();
    for(int i = 0; i < rows; i++) {
        originalText.append(matrix[i]);
    }
    return originalText.toString();
}
```
The algorithm basically follows these steps:

1. Create a matrix with the given number of rows and columns equal to the length of the encoded text divided by the number of rows plus 1, filled with spaces.
2. Iterate through each diagonal of the matrix with a nested loop for each row.
3. If the current index of the encoded text is within the bounds of the text, place the current character from encoded text into the corresponding position of the matrix.
4. Finally, join the matrix rows into a single string to create the original text without trailing spaces.

## A solution in C++

```cpp
#include <string>
#include <vector>

std::string decodeSlantedCipher(const std::string &encodedText, int rows) {
    std::vector<std::string> matrix(rows, std::string(encodedText.size() / rows + 1, ' '));
    int index = 0;
    for(int diagonal = 0; diagonal < 2 * (rows - 1); ++diagonal) {
        for(int row = std::max(0, diagonal - rows + 1); row <= std::min(diagonal, rows - 1); ++row) {
            if(index < encodedText.size()) {
                matrix[row][diagonal - row] = encodedText[index++];
            }
        }
    }
    std::string originalText;
    for(int i = 0; i < rows; ++i) {
        originalText += matrix[i];
    }
    return originalText;
}
```
The algorithm basically follows these steps:

1. Create a matrix with the given number of rows and columns equal to the length of the encoded text divided by the number of rows plus 1, filled with spaces.
2. Iterate through each diagonal of the matrix with a nested loop for each row.
3. If the current index of the encoded text is within the bounds of the text, place the current character from encoded text into the corresponding position of the matrix.
4. Finally, join the matrix rows into a single string to create the original text without trailing spaces.

## A solution in Python

```python
def decode_slanted_cipher(encoded_text, rows):
    matrix = ['' for _ in range(rows)]
    index = 0

    for diagonal in range(2 * (rows - 1)):
        for row in range(max(0, diagonal - rows + 1), min(diagonal, rows - 1) + 1):
            if index < len(encoded_text):
                matrix[row] += encoded_text[index]
                index += 1

    return ''.join(matrix)
```
The algorithm basically follows these steps:

1. Create a matrix with the given number of rows and columns equal to the length of the encoded text divided by the number of rows plus 1, filled with spaces.
2. Iterate through each diagonal of the matrix with a nested loop for each row.
3. If the current index of the encoded text is within the bounds of the text, place the current character from encoded text into the corresponding position of the matrix.
4. Finally, join the matrix rows into a single string to create the original text without trailing spaces.

## A solution in Javascript

```javascript
function decodeSlantedCipher(encodedText, rows) {
    let matrix = new Array(rows).fill("");

    let index = 0;
    for(let diagonal = 0; diagonal < 2 * (rows - 1); diagonal++) {
        for(let row = Math.max(0, diagonal - rows + 1); row <= Math.min(diagonal, rows - 1); row++) {
            if(index < encodedText.length) {
                matrix[row] += encodedText[index++];
            }
        }
    }

    return matrix.join("");
}
```
The algorithm basically follows these steps:

1. Create a matrix with the given number of rows and columns equal to the length of the encoded text divided by the number of rows plus 1, filled with spaces.
2. Iterate through each diagonal of the matrix with a nested loop for each row.
3. If the current index of the encoded text is within the bounds of the text, place the current character from encoded text into the corresponding position of the matrix.
4. Finally, join the matrix rows into a single string to create the original text without trailing spaces.


# Number of Single Divisor Triplets

- slug: number-of-single-divisor-triplets
- difficulty: Medium

You are given a **0-indexed** array of positive integers `nums`. A triplet of three **distinct** indices `(i, j, k)` is called a **single divisor triplet** of `nums` if `nums[i] + nums[j] + nums[k]` is divisible by **exactly one** of `nums[i]`, `nums[j]`, or `nums[k]`.

Return _the number of **single divisor triplets** of_ `nums`_._

**Example 1:**

**Input:** nums = \[4,6,7,3,2\]
**Output:** 12
**Explanation:**
The triplets (0, 3, 4), (0, 4, 3), (3, 0, 4), (3, 4, 0), (4, 0, 3), and (4, 3, 0) have the values of \[4, 3, 2\] (or a permutation of \[4, 3, 2\]).
4 + 3 + 2 = 9 which is only divisible by 3, so all such triplets are single divisor triplets.
The triplets (0, 2, 3), (0, 3, 2), (2, 0, 3), (2, 3, 0), (3, 0, 2), and (3, 2, 0) have the values of \[4, 7, 3\] (or a permutation of \[4, 7, 3\]).
4 + 7 + 3 = 14 which is only divisible by 7, so all such triplets are single divisor triplets.
There are 12 single divisor triplets in total.

**Example 2:**

**Input:** nums = \[1,2,2\]
**Output:** 6
**Explanation:**
The triplets (0, 1, 2), (0, 2, 1), (1, 0, 2), (1, 2, 0), (2, 0, 1), and (2, 1, 0) have the values of \[1, 2, 2\] (or a permutation of \[1, 2, 2\]).
1 + 2 + 2 = 5 which is only divisible by 1, so all such triplets are single divisor triplets.
There are 6 single divisor triplets in total.

**Example 3:**

**Input:** nums = \[1,1,1\]
**Output:** 0
**Explanation:**
There are no single divisor triplets.
Note that (0, 1, 2) is not a single divisor triplet because nums\[0\] + nums\[1\] + nums\[2\] = 3 and 3 is divisible by nums\[0\], nums\[1\], and nums\[2\].

**Constraints:**

*   `3 <= nums.length <= 105`
*   `1 <= nums[i] <= 100`

## A solution in Java

```java
import java.util.*;

public class Main {
    public boolean[] checkFriends(int n, int[][] restrictions, int[][] requests) {
        List<Set<Integer>> friends = new ArrayList<>();
        for (int i = 0; i < n; i++) {
            friends.add(new HashSet<>());
        }
        for (int[] restriction : restrictions) {
            friends.get(restriction[0]).add(restriction[1]);
            friends.get(restriction[1]).add(restriction[0]);
        }

        boolean[] result = new boolean[requests.length];
        for (int i = 0; i < requests.length; i++) {
            int a = requests[i][0];
            int b = requests[i][1];
            if (!friends.get(a).contains(b) && !friends.get(b).contains(a)) {
                friends.get(a).add(b);
                friends.get(b).add(a);
                result[i] = true;
            } else {
                result[i] = false;
            }
        }
        return result;
    }
}
```
First, we create a `friends` list (array or collection depending on the language) to store friendship restrictions for each person in the network. Then, we iterate through the `restrictions` array, adding each restriction to both the xi and yi person's restricted friends.

Next, we create a `result` array to store the boolean outcomes of the friend requests. We iterate through the `requests` array and check if the friendship request violates any of the restrictions. If it doesn't, we add the requested friendship to the friend lists of both persons and set the request outcome to `true`. If it does violate a restriction, we set the request outcome to `false`.

Finally, we return the `result` array.

## A solution in C++

```cpp
#include <vector>
#include <unordered_set>

using namespace std;

vector<bool> checkFriends(int n, vector<vector<int>>& restrictions, vector<vector<int>>& requests) {
    vector<unordered_set<int>> friends(n);
    for (auto& restriction : restrictions) {
        friends[restriction[0]].insert(restriction[1]);
        friends[restriction[1]].insert(restriction[0]);
    }

    vector<bool> result(requests.size());
    for (int i = 0; i < requests.size(); i++) {
        int a = requests[i][0];
        int b = requests[i][1];
        if (friends[a].count(b) == 0 && friends[b].count(a) == 0) {
            friends[a].insert(b);
            friends[b].insert(a);
            result[i] = true;
        } else {
            result[i] = false;
        }
    }
    return result;
}
```
First, we create a `friends` list (array or collection depending on the language) to store friendship restrictions for each person in the network. Then, we iterate through the `restrictions` array, adding each restriction to both the xi and yi person's restricted friends.

Next, we create a `result` array to store the boolean outcomes of the friend requests. We iterate through the `requests` array and check if the friendship request violates any of the restrictions. If it doesn't, we add the requested friendship to the friend lists of both persons and set the request outcome to `true`. If it does violate a restriction, we set the request outcome to `false`.

Finally, we return the `result` array.

## A solution in Python

```python
from collections import defaultdict

def check_friends(n, restrictions, requests):
    friends = defaultdict(set)
    for a, b in restrictions:
        friends[a].add(b)
        friends[b].add(a)

    result = []
    for a, b in requests:
        if b not in friends[a] and a not in friends[b]:
            friends[a].add(b)
            friends[b].add(a)
            result.append(True)
        else:
            result.append(False)
    return result
```
First, we create a `friends` list (array or collection depending on the language) to store friendship restrictions for each person in the network. Then, we iterate through the `restrictions` array, adding each restriction to both the xi and yi person's restricted friends.

Next, we create a `result` array to store the boolean outcomes of the friend requests. We iterate through the `requests` array and check if the friendship request violates any of the restrictions. If it doesn't, we add the requested friendship to the friend lists of both persons and set the request outcome to `true`. If it does violate a restriction, we set the request outcome to `false`.

Finally, we return the `result` array.

## A solution in Javascript

```javascript
function checkFriends(n, restrictions, requests) {
    const friends = new Array(n).fill(null).map(() => new Set());
    for (const restriction of restrictions) {
        friends[restriction[0]].add(restriction[1]);
        friends[restriction[1]].add(restriction[0]);
    }

    const result = [];
    for (const request of requests) {
        const a = request[0];
        const b = request[1];
        if (!friends[a].has(b) && !friends[b].has(a)) {
            friends[a].add(b);
            friends[b].add(a);
            result.push(true);
        } else {
            result.push(false);
        }
    }
    return result;
}
```
First, we create a `friends` list (array or collection depending on the language) to store friendship restrictions for each person in the network. Then, we iterate through the `restrictions` array, adding each restriction to both the xi and yi person's restricted friends.

Next, we create a `result` array to store the boolean outcomes of the friend requests. We iterate through the `requests` array and check if the friendship request violates any of the restrictions. If it doesn't, we add the requested friendship to the friend lists of both persons and set the request outcome to `true`. If it does violate a restriction, we set the request outcome to `false`.

Finally, we return the `result` array.