math-exercises 3.0.215 → 3.0.217
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/lib/exercises/math/arithmetic/whichDayInXDays.d.ts.map +1 -1
- package/lib/exercises/math/arithmetic/whichDayInXDays.js +2 -1
- package/lib/exercises/math/calculLitteral/equation/exp/expOfFEqualsExpOfGEquation.d.ts.map +1 -1
- package/lib/exercises/math/calculLitteral/equation/exp/expOfFEqualsExpOfGEquation.js +19 -32
- package/lib/exercises/math/complex/unitRoots/giveOneSolutionToComplexPowNEqualsOne.js +1 -1
- package/lib/exercises/math/conversion/clock/index.d.ts +0 -1
- package/lib/exercises/math/conversion/clock/index.d.ts.map +1 -1
- package/lib/exercises/math/conversion/clock/index.js +1 -1
- package/lib/exercises/math/derivation/derivative/trigo/sinCosDerivativeRewriteUsingCos2PlusSin2Equals1.js +2 -2
- package/lib/exercises/math/graphs/adjacentMatrixPath.d.ts +10 -0
- package/lib/exercises/math/graphs/adjacentMatrixPath.d.ts.map +1 -0
- package/lib/exercises/math/graphs/adjacentMatrixPath.js +89 -0
- package/lib/exercises/math/graphs/edgesNumberFromSummitsDegrees.d.ts +7 -0
- package/lib/exercises/math/graphs/edgesNumberFromSummitsDegrees.d.ts.map +1 -0
- package/lib/exercises/math/graphs/edgesNumberFromSummitsDegrees.js +98 -0
- package/lib/exercises/math/graphs/eulerianChainFromAdjacentMatrix.d.ts +8 -0
- package/lib/exercises/math/graphs/eulerianChainFromAdjacentMatrix.d.ts.map +1 -0
- package/lib/exercises/math/graphs/eulerianChainFromAdjacentMatrix.js +96 -0
- package/lib/exercises/math/graphs/graphsChainOrPathOfLengthN.d.ts +15 -0
- package/lib/exercises/math/graphs/graphsChainOrPathOfLengthN.d.ts.map +1 -0
- package/lib/exercises/math/graphs/graphsChainOrPathOfLengthN.js +262 -0
- package/lib/exercises/math/graphs/graphsCheckIsConnectedGraph.d.ts +11 -0
- package/lib/exercises/math/graphs/graphsCheckIsConnectedGraph.d.ts.map +1 -0
- package/lib/exercises/math/graphs/graphsCheckIsConnectedGraph.js +178 -0
- package/lib/exercises/math/graphs/graphsCheckIsConnectedUndirectedGraph.d.ts +11 -0
- package/lib/exercises/math/graphs/graphsCheckIsConnectedUndirectedGraph.d.ts.map +1 -0
- package/lib/exercises/math/graphs/graphsCheckIsConnectedUndirectedGraph.js +178 -0
- package/lib/exercises/math/graphs/graphsCheckIsSameGraph.d.ts +19 -0
- package/lib/exercises/math/graphs/graphsCheckIsSameGraph.d.ts.map +1 -0
- package/lib/exercises/math/graphs/graphsCheckIsSameGraph.js +301 -0
- package/lib/exercises/math/graphs/graphsCheckIsVerticesAdjacent.d.ts +16 -0
- package/lib/exercises/math/graphs/graphsCheckIsVerticesAdjacent.d.ts.map +1 -0
- package/lib/exercises/math/graphs/graphsCheckIsVerticesAdjacent.js +207 -0
- package/lib/exercises/math/graphs/graphsDegreeOfVertex.d.ts +15 -0
- package/lib/exercises/math/graphs/graphsDegreeOfVertex.d.ts.map +1 -0
- package/lib/exercises/math/graphs/graphsDegreeOfVertex.js +232 -0
- package/lib/exercises/math/graphs/graphsOrderOfGraph.d.ts +14 -0
- package/lib/exercises/math/graphs/graphsOrderOfGraph.d.ts.map +1 -0
- package/lib/exercises/math/graphs/graphsOrderOfGraph.js +222 -0
- package/lib/exercises/math/graphs/index.d.ts +10 -0
- package/lib/exercises/math/graphs/index.d.ts.map +1 -0
- package/lib/exercises/math/graphs/index.js +9 -0
- package/lib/exercises/math/index.d.ts +1 -0
- package/lib/exercises/math/index.d.ts.map +1 -1
- package/lib/exercises/math/index.js +1 -0
- package/lib/exercises/math/integration/fromExpr/integralFromExpr.d.ts.map +1 -1
- package/lib/exercises/math/integration/fromExpr/integralFromExpr.js +2 -0
- package/lib/exercises/math/matrices/areMatricesInverse.d.ts +9 -0
- package/lib/exercises/math/matrices/areMatricesInverse.d.ts.map +1 -0
- package/lib/exercises/math/matrices/areMatricesInverse.js +106 -0
- package/lib/exercises/math/matrices/computeFixedMatrixInRecurrenceSequence.d.ts +9 -0
- package/lib/exercises/math/matrices/computeFixedMatrixInRecurrenceSequence.d.ts.map +1 -0
- package/lib/exercises/math/matrices/computeFixedMatrixInRecurrenceSequence.js +144 -0
- package/lib/exercises/math/matrices/findInversedMatrixFromSystem.d.ts +8 -0
- package/lib/exercises/math/matrices/findInversedMatrixFromSystem.d.ts.map +1 -0
- package/lib/exercises/math/matrices/findInversedMatrixFromSystem.js +148 -0
- package/lib/exercises/math/matrices/index.d.ts +12 -0
- package/lib/exercises/math/matrices/index.d.ts.map +1 -1
- package/lib/exercises/math/matrices/index.js +12 -0
- package/lib/exercises/math/matrices/isMatrixTransitionMatrix.d.ts +8 -0
- package/lib/exercises/math/matrices/isMatrixTransitionMatrix.d.ts.map +1 -0
- package/lib/exercises/math/matrices/isMatrixTransitionMatrix.js +132 -0
- package/lib/exercises/math/matrices/matrixBuildMatrixFromCoefficients.d.ts +8 -0
- package/lib/exercises/math/matrices/matrixBuildMatrixFromCoefficients.d.ts.map +1 -0
- package/lib/exercises/math/matrices/matrixBuildMatrixFromCoefficients.js +152 -0
- package/lib/exercises/math/matrices/matrixCheckIsSymmetrical.d.ts +8 -0
- package/lib/exercises/math/matrices/matrixCheckIsSymmetrical.d.ts.map +1 -0
- package/lib/exercises/math/matrices/matrixCheckIsSymmetrical.js +155 -0
- package/lib/exercises/math/matrices/matrixComputeDetOfMat2.d.ts +8 -0
- package/lib/exercises/math/matrices/matrixComputeDetOfMat2.d.ts.map +1 -0
- package/lib/exercises/math/matrices/matrixComputeDetOfMat2.js +142 -0
- package/lib/exercises/math/matrices/matrixComputeInverseOfMat2.d.ts +8 -0
- package/lib/exercises/math/matrices/matrixComputeInverseOfMat2.d.ts.map +1 -0
- package/lib/exercises/math/matrices/matrixComputeInverseOfMat2.js +237 -0
- package/lib/exercises/math/matrices/matrixComputeLinearCombination.d.ts +15 -0
- package/lib/exercises/math/matrices/matrixComputeLinearCombination.d.ts.map +1 -0
- package/lib/exercises/math/matrices/matrixComputeLinearCombination.js +232 -0
- package/lib/exercises/math/matrices/matrixComputePower.d.ts +12 -0
- package/lib/exercises/math/matrices/matrixComputePower.d.ts.map +1 -0
- package/lib/exercises/math/matrices/matrixComputePower.js +230 -0
- package/lib/exercises/math/matrices/matrixComputeProduct.d.ts +9 -0
- package/lib/exercises/math/matrices/matrixComputeProduct.d.ts.map +1 -0
- package/lib/exercises/math/matrices/matrixComputeProduct.js +178 -0
- package/lib/exercises/math/matrices/writeMatrixAssociatedToSystem.d.ts +8 -0
- package/lib/exercises/math/matrices/writeMatrixAssociatedToSystem.d.ts.map +1 -0
- package/lib/exercises/math/matrices/writeMatrixAssociatedToSystem.js +105 -0
- package/lib/exercises/math/spaceGeometry/parametricLine/lineLineRelativePositionsFromParametricLines.d.ts.map +1 -1
- package/lib/exercises/math/spaceGeometry/parametricLine/lineLineRelativePositionsFromParametricLines.js +56 -3
- package/lib/exercises/math/spaceGeometry/planes/findNormalVectorFromPlaneEquation.d.ts.map +1 -1
- package/lib/exercises/math/spaceGeometry/planes/findNormalVectorFromPlaneEquation.js +6 -0
- package/lib/exercises/vea/matrixVEA.d.ts +2 -0
- package/lib/exercises/vea/matrixVEA.d.ts.map +1 -0
- package/lib/exercises/vea/matrixVEA.js +1 -0
- package/lib/exercises/vea/treeTableVEA.d.ts.map +1 -1
- package/lib/exercises/vea/treeTableVEA.js +2 -0
- package/lib/index.d.ts +86 -13
- package/lib/index.d.ts.map +1 -1
- package/lib/math/geometry/point.d.ts.map +1 -1
- package/lib/math/geometry/point.js +3 -1
- package/lib/math/graphs/graph.d.ts +43 -0
- package/lib/math/graphs/graph.d.ts.map +1 -0
- package/lib/math/graphs/graph.js +447 -0
- package/lib/math/matrices/matrix.d.ts +42 -3
- package/lib/math/matrices/matrix.d.ts.map +1 -1
- package/lib/math/matrices/matrix.js +173 -7
- package/lib/math/matrices/parseMatrix.d.ts +3 -0
- package/lib/math/matrices/parseMatrix.d.ts.map +1 -0
- package/lib/math/matrices/parseMatrix.js +22 -0
- package/lib/math/systems/generalSystem.d.ts +2 -0
- package/lib/math/systems/generalSystem.d.ts.map +1 -1
- package/lib/math/systems/generalSystem.js +5 -0
- package/lib/math/utils/graphs/graphRenderer.d.ts +25 -0
- package/lib/math/utils/graphs/graphRenderer.d.ts.map +1 -0
- package/lib/math/utils/graphs/graphRenderer.js +123 -0
- package/lib/playground.d.ts +6 -1
- package/lib/playground.d.ts.map +1 -1
- package/lib/playground.js +6 -5
- package/lib/tree/parsers/latexParser.d.ts +1 -1
- package/lib/tree/utilities/nodeSimplifier.d.ts +1 -1
- package/lib/types/keyIds.d.ts +2 -0
- package/lib/types/keyIds.d.ts.map +1 -1
- package/lib/utils/arrays/arrayChunks.d.ts +9 -0
- package/lib/utils/arrays/arrayChunks.d.ts.map +1 -0
- package/lib/utils/arrays/arrayChunks.js +34 -0
- package/lib/utils/strings/ordinalSuffixed.d.ts +2 -0
- package/lib/utils/strings/ordinalSuffixed.d.ts.map +1 -0
- package/lib/utils/strings/ordinalSuffixed.js +5 -0
- package/package.json +7 -1
|
@@ -0,0 +1,301 @@
|
|
|
1
|
+
import { addValidProp, tryToAddWrongProp, GeneratorOptionTarget, GeneratorOptionType, } from "../../../exercises/exercise.js";
|
|
2
|
+
import { getDistinctQuestions } from "../../../exercises/utils/getDistinctQuestions.js";
|
|
3
|
+
import { defaultArrayedOptsWhereNeeded } from "../../../exercises/utils/options/arrayedOptions.js";
|
|
4
|
+
import { GeogebraConstructor } from "../../../geogebra/geogebraConstructor.js";
|
|
5
|
+
import { Point } from "../../../math/geometry/point.js";
|
|
6
|
+
import { Vector } from "../../../math/geometry/vector.js";
|
|
7
|
+
import { GraphConstructor, Graph, } from "../../../math/graphs/graph.js";
|
|
8
|
+
import { GraphRenderer, } from "../../../math/utils/graphs/graphRenderer.js";
|
|
9
|
+
import { randint } from "../../../math/utils/random/randint.js";
|
|
10
|
+
import { coinFlip } from "../../../utils/alea/coinFlip.js";
|
|
11
|
+
import { probaLawFlip } from "../../../utils/alea/probaLawFlip.js";
|
|
12
|
+
import { random, randomMany } from "../../../utils/alea/random.js";
|
|
13
|
+
import { shuffle } from "../../../utils/alea/shuffle.js";
|
|
14
|
+
const getHydrated = (identifiers) => {
|
|
15
|
+
const { graphIds1, graphIds2, graphNodes1, graphEdges1, graphNodes2, graphEdges2, } = identifiers;
|
|
16
|
+
const [graph1, graph2] = [graphIds1, graphIds2].map((graphIds) => GraphConstructor.fromIdentifiers(graphIds));
|
|
17
|
+
const isSameGraph = graph1.equals(graph2);
|
|
18
|
+
const graphNodeOnlyIn2 = (() => {
|
|
19
|
+
if (isSameGraph) {
|
|
20
|
+
return undefined;
|
|
21
|
+
}
|
|
22
|
+
else {
|
|
23
|
+
return graphNodes2.find(({ label: label2 }) => !graphNodes1.map(({ label }) => label).includes(label2));
|
|
24
|
+
}
|
|
25
|
+
})();
|
|
26
|
+
const graphEdgeOnlyIn2 = (() => {
|
|
27
|
+
if (isSameGraph) {
|
|
28
|
+
return undefined;
|
|
29
|
+
}
|
|
30
|
+
else {
|
|
31
|
+
return graphEdges2.find(({ from: from2, to: to2 }) => !graphEdges1
|
|
32
|
+
.map(({ from, to }) => `${from}-${to}`)
|
|
33
|
+
.includes(`${from2}-${to2}`));
|
|
34
|
+
}
|
|
35
|
+
})();
|
|
36
|
+
return {
|
|
37
|
+
graph1,
|
|
38
|
+
graph2,
|
|
39
|
+
isSameGraph,
|
|
40
|
+
graphNodeOnlyIn2,
|
|
41
|
+
graphEdgeOnlyIn2,
|
|
42
|
+
};
|
|
43
|
+
};
|
|
44
|
+
const getInstruction = () => {
|
|
45
|
+
return `Deux graphes sont représentés ci-dessous.
|
|
46
|
+
S'agit-il du même graphe ?
|
|
47
|
+
|
|
48
|
+
*On peut déplacer les points sur la figure.*`;
|
|
49
|
+
};
|
|
50
|
+
const getAnswer = (identifiers) => {
|
|
51
|
+
const { isSameGraph } = getHydrated(identifiers);
|
|
52
|
+
return isSameGraph ? "Oui" : "Non";
|
|
53
|
+
};
|
|
54
|
+
const getHint = () => {
|
|
55
|
+
return `Si les sommets et les arêtes correspondent deux à deux alors il s'agit du même graphe, représenté de deux façons différentes.`;
|
|
56
|
+
};
|
|
57
|
+
const getCorrection = (identifiers) => {
|
|
58
|
+
const { graph2, isSameGraph, graphNodeOnlyIn2, graphEdgeOnlyIn2 } = getHydrated(identifiers);
|
|
59
|
+
if (isSameGraph) {
|
|
60
|
+
return `Les sommets et les arêtes correspondent deux à deux donc il s'agit du même graphe, représenté de deux façons différentes.`;
|
|
61
|
+
}
|
|
62
|
+
else {
|
|
63
|
+
if (graphNodeOnlyIn2) {
|
|
64
|
+
return `Le sommet $${graphNodeOnlyIn2.label}$ est présent dans le graphe de droite et pas dans celui de gauche.
|
|
65
|
+
Ce sont donc des graphes différents.`;
|
|
66
|
+
}
|
|
67
|
+
else if (graphEdgeOnlyIn2) {
|
|
68
|
+
return `L'arête $${graph2.isDirected
|
|
69
|
+
? `${graphEdgeOnlyIn2.from} \\rightarrow ${graphEdgeOnlyIn2.to}`
|
|
70
|
+
: `${graphEdgeOnlyIn2.from}-${graphEdgeOnlyIn2.to}`}$ est présente dans le graphe de droite et pas dans celui de gauche.
|
|
71
|
+
Ce sont donc des graphes différents.`;
|
|
72
|
+
}
|
|
73
|
+
else {
|
|
74
|
+
throw new Error("!isSameGraph && !graphNodeOnlyIn2 && !graphEdgeOnlyIn2");
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
};
|
|
78
|
+
// const getCorrectionGGBOptions: GetGGBOptions<Identifiers> = (identifiers) => {
|
|
79
|
+
// const ggb = new GeogebraConstructor({
|
|
80
|
+
// commands: ["p = (0,1)"],
|
|
81
|
+
// fontSize: 16,
|
|
82
|
+
// hideAxes: true,
|
|
83
|
+
// hideGrid: true,
|
|
84
|
+
// });
|
|
85
|
+
// return ggb.getOptions({
|
|
86
|
+
// coords: ggb.getCoordsForPoints([
|
|
87
|
+
// new Point("O", 0, 0),
|
|
88
|
+
// new Point("A", 1, 0),
|
|
89
|
+
// ]),
|
|
90
|
+
// });
|
|
91
|
+
// };
|
|
92
|
+
const getGGBOptions = (identifiers) => {
|
|
93
|
+
const { graphNodes1, graphEdges1, scale1, graphNodes2, graphEdges2, scale2 } = identifiers;
|
|
94
|
+
const { graph1, graph2 } = getHydrated(identifiers);
|
|
95
|
+
function createDisplayObjForGraph(graph, graphNodes, graphEdges, scale, index, vecOffset = new Vector("offset", (0).toTree(), (0).toTree())) {
|
|
96
|
+
const arrDictPoint = graphNodes
|
|
97
|
+
.map(({ label, x, y }) => new Point(label, x * scale, y * scale))
|
|
98
|
+
.map((point) => {
|
|
99
|
+
const strNamePointOld = point.name;
|
|
100
|
+
const strNamePointNew = `${point.name}${index}`;
|
|
101
|
+
return {
|
|
102
|
+
label: strNamePointOld,
|
|
103
|
+
point: vecOffset.getEndPoint(point, strNamePointNew),
|
|
104
|
+
};
|
|
105
|
+
});
|
|
106
|
+
const pointCommands = arrDictPoint.flatMap(({ label, point }) => point.toGGBCommand({
|
|
107
|
+
isFixed: false,
|
|
108
|
+
isSelectionnable: true,
|
|
109
|
+
showLabel: true,
|
|
110
|
+
style: 0,
|
|
111
|
+
size: 8,
|
|
112
|
+
label,
|
|
113
|
+
}));
|
|
114
|
+
const edgeCommands = graphEdges.map((e, i) => graph.isDirected
|
|
115
|
+
? `v${index}I${i + 1} = Vector(${e.from}${index}, ${e.to}${index})`
|
|
116
|
+
: `s${index}I${i + 1} = Segment(${e.from}${index}, ${e.to}${index})`);
|
|
117
|
+
const arrGGBCommandForGraph = [...pointCommands, ...edgeCommands];
|
|
118
|
+
const arrPoint = arrDictPoint.map(({ point }) => point);
|
|
119
|
+
return {
|
|
120
|
+
arrPoint,
|
|
121
|
+
arrGGBCommandForGraph,
|
|
122
|
+
};
|
|
123
|
+
}
|
|
124
|
+
const { arrPoint: arrPoint1, arrGGBCommandForGraph: arrGGBCommandForGraph1 } = createDisplayObjForGraph(graph1, graphNodes1, graphEdges1, scale1, 1);
|
|
125
|
+
const xMin1 = Math.min(...arrPoint1.map((point) => point.x.evaluate()));
|
|
126
|
+
const xMax1 = Math.max(...arrPoint1.map((point) => point.x.evaluate()));
|
|
127
|
+
const width1 = xMax1 - xMin1;
|
|
128
|
+
const vecOffset = new Vector("offset", (xMax1 + 0.1 * width1).toTree(), (0).toTree());
|
|
129
|
+
const { arrPoint: arrPoint2, arrGGBCommandForGraph: arrGGBCommandForGraph2 } = createDisplayObjForGraph(graph2, graphNodes2, graphEdges2, scale2, 2, vecOffset);
|
|
130
|
+
const ggb = new GeogebraConstructor({
|
|
131
|
+
commands: [...arrGGBCommandForGraph1, ...arrGGBCommandForGraph2],
|
|
132
|
+
fontSize: 16,
|
|
133
|
+
hideAxes: true,
|
|
134
|
+
hideGrid: true,
|
|
135
|
+
});
|
|
136
|
+
return ggb.getOptions({
|
|
137
|
+
coords: ggb.getCoordsForPoints([...arrPoint1, ...arrPoint2]),
|
|
138
|
+
});
|
|
139
|
+
};
|
|
140
|
+
const getPropositions = (_, { answer }) => {
|
|
141
|
+
const propositions = [];
|
|
142
|
+
["Oui", "Non"].forEach((str) => {
|
|
143
|
+
if (str === answer) {
|
|
144
|
+
addValidProp(propositions, str, "raw");
|
|
145
|
+
}
|
|
146
|
+
else {
|
|
147
|
+
tryToAddWrongProp(propositions, str, "raw");
|
|
148
|
+
}
|
|
149
|
+
});
|
|
150
|
+
return propositions;
|
|
151
|
+
};
|
|
152
|
+
const createRandomIdentifiers = (isDirected) => {
|
|
153
|
+
const isSimple = true;
|
|
154
|
+
const graph0 = (() => {
|
|
155
|
+
const nbVertices = randint(6, 8);
|
|
156
|
+
const minDensity = (() => {
|
|
157
|
+
switch (nbVertices) {
|
|
158
|
+
case 5:
|
|
159
|
+
return isDirected ? 0.4 : 0.62;
|
|
160
|
+
case 6:
|
|
161
|
+
return isDirected ? 0.35 : 0.57;
|
|
162
|
+
case 7:
|
|
163
|
+
return isDirected ? 0.3 : 0.52;
|
|
164
|
+
case 8:
|
|
165
|
+
return isDirected ? 0.27 : 0.37;
|
|
166
|
+
case 9:
|
|
167
|
+
return isDirected ? 0.24 : 0.32;
|
|
168
|
+
}
|
|
169
|
+
})();
|
|
170
|
+
const graph = GraphConstructor.random(nbVertices, isSimple, isDirected, minDensity, "ABCDEFGHIJKLM".split(""), true);
|
|
171
|
+
return graph;
|
|
172
|
+
})();
|
|
173
|
+
const isSameGraph = coinFlip();
|
|
174
|
+
const [graph1, graph2] = (() => {
|
|
175
|
+
if (isSameGraph) {
|
|
176
|
+
return [graph0, graph0];
|
|
177
|
+
}
|
|
178
|
+
else {
|
|
179
|
+
const poolVertexName = "ABCDEFGHIJKLM".split("");
|
|
180
|
+
const poolVertexNameAvailable = poolVertexName.filter((str) => !graph0.vertexNames.includes(str));
|
|
181
|
+
const typeDiff = probaLawFlip([
|
|
182
|
+
["different vertex names", 0.25],
|
|
183
|
+
["extraneous vertex", 0.25],
|
|
184
|
+
["same vertices, extraneous edge", 0.5],
|
|
185
|
+
]);
|
|
186
|
+
switch (typeDiff) {
|
|
187
|
+
case "different vertex names": {
|
|
188
|
+
const [nameVertex1, nameVertex2] = randomMany(poolVertexNameAvailable, 2);
|
|
189
|
+
const indexReplacement = randint(0, graph0.vertexNames.length);
|
|
190
|
+
const [vertexNames1, vertexNames2] = [nameVertex1, nameVertex2].map((nameVertex) => {
|
|
191
|
+
const vertexNames = [...graph0.vertexNames];
|
|
192
|
+
vertexNames[indexReplacement] = nameVertex;
|
|
193
|
+
return vertexNames;
|
|
194
|
+
});
|
|
195
|
+
const [graph1, graph2] = [vertexNames1, vertexNames2].map((vertexNames) => new Graph(vertexNames, graph0.mat));
|
|
196
|
+
return [graph1, graph2];
|
|
197
|
+
}
|
|
198
|
+
case "extraneous vertex": {
|
|
199
|
+
const isGraph1Graph0 = coinFlip();
|
|
200
|
+
const graph1 = isGraph1Graph0
|
|
201
|
+
? graph0
|
|
202
|
+
: (() => {
|
|
203
|
+
const miniGraph = GraphConstructor.random(2, isSimple, graph0.isDirected, 0, [random(graph0.vertexNames), random(poolVertexNameAvailable)], true);
|
|
204
|
+
return GraphConstructor.graphByMergingSimpleGraphs([
|
|
205
|
+
graph0,
|
|
206
|
+
miniGraph,
|
|
207
|
+
]);
|
|
208
|
+
})();
|
|
209
|
+
const graph2 = (() => {
|
|
210
|
+
const poolVertexNameAvailable = poolVertexName.filter((str) => !graph1.vertexNames.includes(str));
|
|
211
|
+
const miniGraph = GraphConstructor.random(2, isSimple, graph0.isDirected, 0, [random(graph0.vertexNames), random(poolVertexNameAvailable)], true);
|
|
212
|
+
return GraphConstructor.graphByMergingSimpleGraphs([
|
|
213
|
+
graph0,
|
|
214
|
+
miniGraph,
|
|
215
|
+
]);
|
|
216
|
+
})();
|
|
217
|
+
return [graph1, graph2];
|
|
218
|
+
}
|
|
219
|
+
case "same vertices, extraneous edge": {
|
|
220
|
+
//it is possible that graph1===graph2
|
|
221
|
+
const isGraph1Graph0 = coinFlip();
|
|
222
|
+
const graph1 = isGraph1Graph0
|
|
223
|
+
? graph0
|
|
224
|
+
: GraphConstructor.graphByAddingRandomEdge(graph0);
|
|
225
|
+
const graph2 = GraphConstructor.graphByAddingRandomEdge(graph0);
|
|
226
|
+
return [graph1, graph2];
|
|
227
|
+
}
|
|
228
|
+
default:
|
|
229
|
+
throw new Error("Unsupported typeDiff: " + typeDiff);
|
|
230
|
+
}
|
|
231
|
+
}
|
|
232
|
+
})();
|
|
233
|
+
const [[layoutEngine1, scale1], [layoutEngine2, scale2]] = shuffle([
|
|
234
|
+
["fdp", 1.5],
|
|
235
|
+
["circo", 1.0],
|
|
236
|
+
]);
|
|
237
|
+
const [{ nodes: graphNodes1, edges: graphEdges1 }, { nodes: graphNodes2, edges: graphEdges2 },] = [
|
|
238
|
+
{ graph: graph1, layoutEngine: layoutEngine1 },
|
|
239
|
+
{ graph: graph2, layoutEngine: layoutEngine2 },
|
|
240
|
+
].map(({ graph, layoutEngine }) => GraphRenderer.renderToNodesAndEdges(graph, layoutEngine));
|
|
241
|
+
const identifiers = {
|
|
242
|
+
graphIds1: graph1.toIdentifiers(),
|
|
243
|
+
graphIds2: graph2.toIdentifiers(),
|
|
244
|
+
graphNodes1,
|
|
245
|
+
graphEdges1,
|
|
246
|
+
scale1,
|
|
247
|
+
graphNodes2,
|
|
248
|
+
graphEdges2,
|
|
249
|
+
scale2,
|
|
250
|
+
};
|
|
251
|
+
return identifiers;
|
|
252
|
+
};
|
|
253
|
+
const getGraphsCheckIsSameGraphQuestion = (optsIn) => {
|
|
254
|
+
const arrayedOpts = defaultArrayedOptsWhereNeeded(optsIn, arrayedOptsDefault);
|
|
255
|
+
const opts = {
|
|
256
|
+
graphType: random(arrayedOpts.graphType),
|
|
257
|
+
};
|
|
258
|
+
const isDirected = opts.graphType === "orienté";
|
|
259
|
+
const identifiers = createRandomIdentifiers(isDirected);
|
|
260
|
+
return getQuestionFromIdentifiers(identifiers);
|
|
261
|
+
};
|
|
262
|
+
const getQuestionFromIdentifiers = (identifiers, opts) => {
|
|
263
|
+
const question = {
|
|
264
|
+
answer: getAnswer(identifiers, opts),
|
|
265
|
+
instruction: getInstruction(identifiers, opts),
|
|
266
|
+
answerFormat: "raw",
|
|
267
|
+
identifiers,
|
|
268
|
+
hint: getHint(identifiers, opts),
|
|
269
|
+
correction: getCorrection(identifiers, opts),
|
|
270
|
+
ggbOptions: getGGBOptions(identifiers, opts),
|
|
271
|
+
};
|
|
272
|
+
return question;
|
|
273
|
+
};
|
|
274
|
+
const arrayedOptsDefault = {
|
|
275
|
+
graphType: ["non orienté"],
|
|
276
|
+
};
|
|
277
|
+
const options = [
|
|
278
|
+
{
|
|
279
|
+
id: "graphType",
|
|
280
|
+
label: "Types de graphes",
|
|
281
|
+
target: GeneratorOptionTarget.generation,
|
|
282
|
+
type: GeneratorOptionType.multiselect,
|
|
283
|
+
values: ["non orienté", "orienté"],
|
|
284
|
+
defaultValue: arrayedOptsDefault.graphType,
|
|
285
|
+
},
|
|
286
|
+
];
|
|
287
|
+
export const graphsCheckIsSameGraph = {
|
|
288
|
+
id: "graphsCheckIsSameGraph",
|
|
289
|
+
label: "Déterminer s'il s'agit du même graphe",
|
|
290
|
+
isSingleStep: true,
|
|
291
|
+
generator: (nb, opts) => getDistinctQuestions(() => getGraphsCheckIsSameGraphQuestion(opts), nb),
|
|
292
|
+
options,
|
|
293
|
+
qcmTimer: 60,
|
|
294
|
+
freeTimer: 60,
|
|
295
|
+
getPropositions,
|
|
296
|
+
subject: "Mathématiques",
|
|
297
|
+
getQuestionFromIdentifiers,
|
|
298
|
+
hasHintAndCorrection: true,
|
|
299
|
+
hasGeogebra: true,
|
|
300
|
+
answerType: "QCU",
|
|
301
|
+
};
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import { Exercise } from "../../../exercises/exercise.js";
|
|
2
|
+
import { GraphIdentifiers } from "../../../math/graphs/graph.js";
|
|
3
|
+
import { GraphEdge, GraphNode } from "../../../math/utils/graphs/graphRenderer.js";
|
|
4
|
+
type Identifiers = {
|
|
5
|
+
graphIds: GraphIdentifiers;
|
|
6
|
+
nameVertex1: string;
|
|
7
|
+
nameVertex2: string;
|
|
8
|
+
graphNodes: GraphNode[];
|
|
9
|
+
graphEdges: GraphEdge[];
|
|
10
|
+
};
|
|
11
|
+
type Options = {
|
|
12
|
+
graphType: string;
|
|
13
|
+
};
|
|
14
|
+
export declare const graphsCheckIsVerticesAdjacent: Exercise<Identifiers, Options>;
|
|
15
|
+
export {};
|
|
16
|
+
//# sourceMappingURL=graphsCheckIsVerticesAdjacent.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"graphsCheckIsVerticesAdjacent.d.ts","sourceRoot":"","sources":["../../../../src/exercises/math/graphs/graphsCheckIsVerticesAdjacent.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,QAAQ,EAgBT,MAAM,6BAA6B,CAAC;AAMrC,OAAO,EAAoB,gBAAgB,EAAE,MAAM,4BAA4B,CAAC;AAChF,OAAO,EACL,SAAS,EACT,SAAS,EAEV,MAAM,0CAA0C,CAAC;AAMlD,KAAK,WAAW,GAAG;IACjB,QAAQ,EAAE,gBAAgB,CAAC;IAC3B,WAAW,EAAE,MAAM,CAAC;IACpB,WAAW,EAAE,MAAM,CAAC;IAGpB,UAAU,EAAE,SAAS,EAAE,CAAC;IACxB,UAAU,EAAE,SAAS,EAAE,CAAC;CACzB,CAAC;AAkOF,KAAK,OAAO,GAAG;IACb,SAAS,EAAE,MAAM,CAAC;CACnB,CAAC;AAsBF,eAAO,MAAM,6BAA6B,EAAE,QAAQ,CAAC,WAAW,EAAE,OAAO,CAkBxE,CAAC"}
|
|
@@ -0,0 +1,207 @@
|
|
|
1
|
+
import { addValidProp, tryToAddWrongProp, GeneratorOptionTarget, GeneratorOptionType, } from "../../../exercises/exercise.js";
|
|
2
|
+
import { getDistinctQuestions } from "../../../exercises/utils/getDistinctQuestions.js";
|
|
3
|
+
import { defaultArrayedOptsWhereNeeded } from "../../../exercises/utils/options/arrayedOptions.js";
|
|
4
|
+
import { greenMain } from "../../../geogebra/colors.js";
|
|
5
|
+
import { GeogebraConstructor } from "../../../geogebra/geogebraConstructor.js";
|
|
6
|
+
import { Point } from "../../../math/geometry/point.js";
|
|
7
|
+
import { GraphConstructor } from "../../../math/graphs/graph.js";
|
|
8
|
+
import { GraphRenderer, } from "../../../math/utils/graphs/graphRenderer.js";
|
|
9
|
+
import { randint } from "../../../math/utils/random/randint.js";
|
|
10
|
+
import { coinFlip } from "../../../utils/alea/coinFlip.js";
|
|
11
|
+
import { random } from "../../../utils/alea/random.js";
|
|
12
|
+
import { shuffle } from "../../../utils/alea/shuffle.js";
|
|
13
|
+
const getHydrated = (identifiers) => {
|
|
14
|
+
const { graphIds, nameVertex1, nameVertex2 } = identifiers;
|
|
15
|
+
const graph = GraphConstructor.fromIdentifiers(graphIds);
|
|
16
|
+
const dictConnections = graph.dictConnections();
|
|
17
|
+
const isAdjacent = dictConnections[nameVertex1][nameVertex2] ||
|
|
18
|
+
dictConnections[nameVertex2][nameVertex1];
|
|
19
|
+
return {
|
|
20
|
+
graph,
|
|
21
|
+
isAdjacent,
|
|
22
|
+
};
|
|
23
|
+
};
|
|
24
|
+
const getInstruction = (identifiers) => {
|
|
25
|
+
const { nameVertex1, nameVertex2 } = identifiers;
|
|
26
|
+
return `Un graphe est représenté ci-dessous.
|
|
27
|
+
Les sommets $${nameVertex1}$ et $${nameVertex2}$ sont-ils adjacents ?`;
|
|
28
|
+
};
|
|
29
|
+
const getAnswer = (identifiers) => {
|
|
30
|
+
const { isAdjacent } = getHydrated(identifiers);
|
|
31
|
+
return isAdjacent ? "Oui" : "Non";
|
|
32
|
+
};
|
|
33
|
+
const getHint = () => {
|
|
34
|
+
return `Deux sommets sont adjacents si et seulement si ils sont reliés par une arête.`;
|
|
35
|
+
};
|
|
36
|
+
const getCorrection = (identifiers) => {
|
|
37
|
+
const { nameVertex1, nameVertex2 } = identifiers;
|
|
38
|
+
const { isAdjacent } = getHydrated(identifiers);
|
|
39
|
+
if (isAdjacent) {
|
|
40
|
+
return `Les sommets $${nameVertex1}$ et $${nameVertex2}$ sont reliés par au moins une arête.
|
|
41
|
+
Ils sont adjacents.`;
|
|
42
|
+
}
|
|
43
|
+
else {
|
|
44
|
+
return `Les sommets $${nameVertex1}$ et $${nameVertex2}$ ne sont pas reliés par une arête.
|
|
45
|
+
Ils ne sont pas adjacents.`;
|
|
46
|
+
}
|
|
47
|
+
};
|
|
48
|
+
const getCorrectionGGBOptions = (identifiers) => {
|
|
49
|
+
const { graphNodes, graphEdges, nameVertex1, nameVertex2 } = identifiers;
|
|
50
|
+
const { graph } = getHydrated(identifiers);
|
|
51
|
+
const arrPoint = graphNodes.map(({ label, x, y }) => new Point(label, x, y));
|
|
52
|
+
const pointCommands = arrPoint.flatMap((point) => point.toGGBCommand({
|
|
53
|
+
isFixed: false,
|
|
54
|
+
isSelectionnable: true,
|
|
55
|
+
showLabel: true,
|
|
56
|
+
style: 0,
|
|
57
|
+
size: 8,
|
|
58
|
+
color: point.name === nameVertex1 || point.name === nameVertex2
|
|
59
|
+
? greenMain
|
|
60
|
+
: "#000000",
|
|
61
|
+
}));
|
|
62
|
+
const edgeCommands = graphEdges.flatMap((e, i) => {
|
|
63
|
+
return [
|
|
64
|
+
graph.isDirected
|
|
65
|
+
? `edge${i + 1} = Vector(${e.from}, ${e.to})`
|
|
66
|
+
: `edge${i + 1} = Segment(${e.from}, ${e.to})`,
|
|
67
|
+
...((e.from === nameVertex1 && e.to === nameVertex2) ||
|
|
68
|
+
(e.from === nameVertex2 && e.to === nameVertex1)
|
|
69
|
+
? [`SetColor(edge${i + 1}, "${greenMain}")`]
|
|
70
|
+
: []),
|
|
71
|
+
];
|
|
72
|
+
});
|
|
73
|
+
const ggb = new GeogebraConstructor({
|
|
74
|
+
commands: [...pointCommands, ...edgeCommands],
|
|
75
|
+
fontSize: 16,
|
|
76
|
+
hideAxes: true,
|
|
77
|
+
hideGrid: true,
|
|
78
|
+
});
|
|
79
|
+
return ggb.getOptions({
|
|
80
|
+
coords: ggb.getCoordsForPoints(arrPoint),
|
|
81
|
+
});
|
|
82
|
+
};
|
|
83
|
+
const getGGBOptions = (identifiers) => {
|
|
84
|
+
const { graphNodes, graphEdges } = identifiers;
|
|
85
|
+
const { graph } = getHydrated(identifiers);
|
|
86
|
+
const arrPoint = graphNodes.map(({ label, x, y }) => new Point(label, x, y));
|
|
87
|
+
const pointCommands = arrPoint.flatMap((point) => point.toGGBCommand({
|
|
88
|
+
isFixed: false,
|
|
89
|
+
isSelectionnable: true,
|
|
90
|
+
showLabel: true,
|
|
91
|
+
style: 0,
|
|
92
|
+
size: 8,
|
|
93
|
+
}));
|
|
94
|
+
const edgeCommands = graphEdges.map((e, i) => graph.isDirected
|
|
95
|
+
? `v${i + 1} = Vector(${e.from}, ${e.to})`
|
|
96
|
+
: `s${i + 1} = Segment(${e.from}, ${e.to})`);
|
|
97
|
+
const arrGGBCommandForGraph = [...pointCommands, ...edgeCommands];
|
|
98
|
+
const ggb = new GeogebraConstructor({
|
|
99
|
+
commands: [...arrGGBCommandForGraph],
|
|
100
|
+
fontSize: 16,
|
|
101
|
+
hideAxes: true,
|
|
102
|
+
hideGrid: true,
|
|
103
|
+
});
|
|
104
|
+
return ggb.getOptions({
|
|
105
|
+
coords: ggb.getCoordsForPoints(arrPoint),
|
|
106
|
+
});
|
|
107
|
+
};
|
|
108
|
+
const getPropositions = (_, { answer }) => {
|
|
109
|
+
const propositions = [];
|
|
110
|
+
["Oui", "Non"].forEach((str) => {
|
|
111
|
+
if (str === answer) {
|
|
112
|
+
addValidProp(propositions, str, "raw");
|
|
113
|
+
}
|
|
114
|
+
else {
|
|
115
|
+
tryToAddWrongProp(propositions, str, "raw");
|
|
116
|
+
}
|
|
117
|
+
});
|
|
118
|
+
return propositions;
|
|
119
|
+
};
|
|
120
|
+
const createRandomIdentifiers = (isDirected) => {
|
|
121
|
+
const nbVertices = randint(5, 10);
|
|
122
|
+
const isSimple = true;
|
|
123
|
+
const minDensity = (() => {
|
|
124
|
+
switch (nbVertices) {
|
|
125
|
+
case 5:
|
|
126
|
+
return isDirected ? 0.4 : 0.62;
|
|
127
|
+
case 6:
|
|
128
|
+
return isDirected ? 0.35 : 0.57;
|
|
129
|
+
case 7:
|
|
130
|
+
return isDirected ? 0.3 : 0.52;
|
|
131
|
+
case 8:
|
|
132
|
+
return isDirected ? 0.27 : 0.37;
|
|
133
|
+
case 9:
|
|
134
|
+
return isDirected ? 0.24 : 0.32;
|
|
135
|
+
}
|
|
136
|
+
})();
|
|
137
|
+
const graph = GraphConstructor.random(nbVertices, isSimple, isDirected, minDensity, "ABCDEFGHIJKLM".split(""), true);
|
|
138
|
+
const { nodes: graphNodes, edges: graphEdges } = GraphRenderer.renderToNodesAndEdges(graph);
|
|
139
|
+
const [nameVertex1, nameVertex2] = shuffle((() => {
|
|
140
|
+
const isAdjacent = coinFlip();
|
|
141
|
+
const arrConnection = graph.arrConnection();
|
|
142
|
+
return random(arrConnection
|
|
143
|
+
.filter(([_nameVertexStart, _nameVertexEnd, isConnection]) => isConnection === isAdjacent)
|
|
144
|
+
.map(([nameVertexStart, nameVertexEnd, _]) => [
|
|
145
|
+
nameVertexStart,
|
|
146
|
+
nameVertexEnd,
|
|
147
|
+
]));
|
|
148
|
+
})());
|
|
149
|
+
const identifiers = {
|
|
150
|
+
graphIds: graph.toIdentifiers(),
|
|
151
|
+
nameVertex1,
|
|
152
|
+
nameVertex2,
|
|
153
|
+
graphNodes,
|
|
154
|
+
graphEdges,
|
|
155
|
+
};
|
|
156
|
+
return identifiers;
|
|
157
|
+
};
|
|
158
|
+
const getGraphsCheckIsVerticesAdjacentQuestion = (optsIn) => {
|
|
159
|
+
const arrayedOpts = defaultArrayedOptsWhereNeeded(optsIn, arrayedOptsDefault);
|
|
160
|
+
const opts = {
|
|
161
|
+
graphType: random(arrayedOpts.graphType),
|
|
162
|
+
};
|
|
163
|
+
const isDirected = opts.graphType === "orienté";
|
|
164
|
+
const identifiers = createRandomIdentifiers(isDirected);
|
|
165
|
+
return getQuestionFromIdentifiers(identifiers);
|
|
166
|
+
};
|
|
167
|
+
const getQuestionFromIdentifiers = (identifiers, opts) => {
|
|
168
|
+
const question = {
|
|
169
|
+
answer: getAnswer(identifiers, opts),
|
|
170
|
+
instruction: getInstruction(identifiers, opts),
|
|
171
|
+
answerFormat: "raw",
|
|
172
|
+
identifiers,
|
|
173
|
+
hint: getHint(identifiers, opts),
|
|
174
|
+
correction: getCorrection(identifiers, opts),
|
|
175
|
+
correctionGgbOptions: getCorrectionGGBOptions(identifiers, opts),
|
|
176
|
+
ggbOptions: getGGBOptions(identifiers, opts),
|
|
177
|
+
};
|
|
178
|
+
return question;
|
|
179
|
+
};
|
|
180
|
+
const arrayedOptsDefault = {
|
|
181
|
+
graphType: ["non orienté"],
|
|
182
|
+
};
|
|
183
|
+
const options = [
|
|
184
|
+
{
|
|
185
|
+
id: "graphType",
|
|
186
|
+
label: "Types de graphes",
|
|
187
|
+
target: GeneratorOptionTarget.generation,
|
|
188
|
+
type: GeneratorOptionType.multiselect,
|
|
189
|
+
values: ["non orienté", "orienté"],
|
|
190
|
+
defaultValue: arrayedOptsDefault.graphType,
|
|
191
|
+
},
|
|
192
|
+
];
|
|
193
|
+
export const graphsCheckIsVerticesAdjacent = {
|
|
194
|
+
id: "graphsCheckIsVerticesAdjacent",
|
|
195
|
+
label: "Déterminer si deux sommets sont adjacents",
|
|
196
|
+
isSingleStep: true,
|
|
197
|
+
generator: (nb, opts) => getDistinctQuestions(() => getGraphsCheckIsVerticesAdjacentQuestion(opts), nb),
|
|
198
|
+
options,
|
|
199
|
+
qcmTimer: 60,
|
|
200
|
+
freeTimer: 60,
|
|
201
|
+
getPropositions,
|
|
202
|
+
subject: "Mathématiques",
|
|
203
|
+
getQuestionFromIdentifiers,
|
|
204
|
+
hasHintAndCorrection: true,
|
|
205
|
+
hasGeogebra: true,
|
|
206
|
+
answerType: "QCU",
|
|
207
|
+
};
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import { Exercise } from "../../../exercises/exercise.js";
|
|
2
|
+
import { GraphIdentifiers } from "../../../math/graphs/graph.js";
|
|
3
|
+
import { GraphEdge, GraphNode } from "../../../math/utils/graphs/graphRenderer.js";
|
|
4
|
+
type Identifiers = {
|
|
5
|
+
graphIds: GraphIdentifiers;
|
|
6
|
+
indexAsked: number;
|
|
7
|
+
graphNodes: GraphNode[];
|
|
8
|
+
graphEdges: GraphEdge[];
|
|
9
|
+
};
|
|
10
|
+
type Options = {
|
|
11
|
+
graphType: string;
|
|
12
|
+
};
|
|
13
|
+
export declare const graphsDegreeOfVertex: Exercise<Identifiers, Options>;
|
|
14
|
+
export {};
|
|
15
|
+
//# sourceMappingURL=graphsDegreeOfVertex.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"graphsDegreeOfVertex.d.ts","sourceRoot":"","sources":["../../../../src/exercises/math/graphs/graphsDegreeOfVertex.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,QAAQ,EAoBT,MAAM,6BAA6B,CAAC;AAMrC,OAAO,EAAoB,gBAAgB,EAAE,MAAM,4BAA4B,CAAC;AAChF,OAAO,EACL,SAAS,EACT,SAAS,EAEV,MAAM,0CAA0C,CAAC;AASlD,KAAK,WAAW,GAAG;IACjB,QAAQ,EAAE,gBAAgB,CAAC;IAC3B,UAAU,EAAE,MAAM,CAAC;IAGnB,UAAU,EAAE,SAAS,EAAE,CAAC;IACxB,UAAU,EAAE,SAAS,EAAE,CAAC;CACzB,CAAC;AAmQF,KAAK,OAAO,GAAG;IACb,SAAS,EAAE,MAAM,CAAC;CACnB,CAAC;AAsBF,eAAO,MAAM,oBAAoB,EAAE,QAAQ,CAAC,WAAW,EAAE,OAAO,CAe/D,CAAC"}
|