CODINGCONTRACT: Move internals to a separate folder (#1932)

This commit is contained in:
G4mingJon4s
2025-02-12 07:04:23 +01:00
committed by GitHub
parent 5bc9068745
commit b61e93b246
33 changed files with 2101 additions and 1927 deletions

View File

@@ -0,0 +1,107 @@
import { getRandomIntInclusive } from "../../utils/helpers/getRandomIntInclusive";
import { CodingContractTypes, removeBracketsFromArrayString, removeQuotesFromString } from "../ContractTypes";
import { CodingContractName } from "@enums";
export const sanitizeParenthesesInExpression: Pick<
CodingContractTypes,
CodingContractName.SanitizeParenthesesInExpression
> = {
[CodingContractName.SanitizeParenthesesInExpression]: {
desc: (data: string): string => {
return [
"Given the following string:\n\n",
`${data}\n\n`,
"remove the minimum number of invalid parentheses in order to validate",
"the string. If there are multiple minimal ways to validate the string,",
"provide all of the possible results. The answer should be provided",
"as an array of strings. If it is impossible to validate the string",
"the result should be an array with only an empty string.\n\n",
"IMPORTANT: The string may contain letters, not just parentheses.\n\n",
`Examples:\n\n`,
`"()())()" -> ["()()()", "(())()"]\n`,
`"(a)())()" -> ["(a)()()", "(a())()"]\n`,
`")(" -> [""]`,
].join(" ");
},
difficulty: 10,
generate: (): string => {
const len: number = getRandomIntInclusive(6, 20);
const chars: string[] = [];
chars.length = len;
// 80% chance of the first parenthesis being (
Math.random() < 0.8 ? (chars[0] = "(") : (chars[0] = ")");
for (let i = 1; i < len; ++i) {
const roll = Math.random();
if (roll < 0.4) {
chars[i] = "(";
} else if (roll < 0.8) {
chars[i] = ")";
} else {
chars[i] = "a";
}
}
return chars.join("");
},
solver: (data, answer) => {
let left = 0;
let right = 0;
const res: string[] = [];
for (let i = 0; i < data.length; ++i) {
if (data[i] === "(") {
++left;
} else if (data[i] === ")") {
left > 0 ? --left : ++right;
}
}
function dfs(
pair: number,
index: number,
left: number,
right: number,
s: string,
solution: string,
res: string[],
): void {
if (s.length === index) {
if (left === 0 && right === 0 && pair === 0) {
for (let i = 0; i < res.length; i++) {
if (res[i] === solution) {
return;
}
}
res.push(solution);
}
return;
}
if (s[index] === "(") {
if (left > 0) {
dfs(pair, index + 1, left - 1, right, s, solution, res);
}
dfs(pair + 1, index + 1, left, right, s, solution + s[index], res);
} else if (s[index] === ")") {
if (right > 0) dfs(pair, index + 1, left, right - 1, s, solution, res);
if (pair > 0) dfs(pair - 1, index + 1, left, right, s, solution + s[index], res);
} else {
dfs(pair, index + 1, left, right, s, solution + s[index], res);
}
}
dfs(0, 0, left, right, data, "", res);
if (res.length !== answer.length) return false;
return res.every((sol) => answer.includes(sol));
},
convertAnswer: (ans) => {
const sanitized = removeBracketsFromArrayString(ans).split(",");
return sanitized.map((s) => removeQuotesFromString(s.replace(/\s/g, "")));
},
validateAnswer: (ans): ans is string[] =>
typeof ans === "object" && Array.isArray(ans) && ans.every((s) => typeof s === "string"),
},
};