@xcpcio/core 0.33.1 → 0.34.1
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/dist/index.cjs +65 -21
- package/dist/index.d.ts +5 -2
- package/dist/index.mjs +65 -21
- package/package.json +2 -2
- package/src/contest.ts +31 -26
- package/src/rank-statistics.ts +6 -0
- package/src/rank.ts +46 -0
- package/src/team.ts +4 -0
package/dist/index.cjs
CHANGED
|
@@ -657,6 +657,9 @@ class Team {
|
|
|
657
657
|
}
|
|
658
658
|
return this.members?.join(", ");
|
|
659
659
|
}
|
|
660
|
+
get isEffectiveTeam() {
|
|
661
|
+
return this.solvedProblemNum > 0;
|
|
662
|
+
}
|
|
660
663
|
calcSolvedData(options) {
|
|
661
664
|
this.solvedProblemNum = 0;
|
|
662
665
|
this.attemptedProblemNum = 0;
|
|
@@ -1053,32 +1056,34 @@ function createContest(contestJSON) {
|
|
|
1053
1056
|
return;
|
|
1054
1057
|
}
|
|
1055
1058
|
c.awards = /* @__PURE__ */ new Map();
|
|
1056
|
-
|
|
1057
|
-
const
|
|
1058
|
-
|
|
1059
|
-
|
|
1060
|
-
|
|
1061
|
-
|
|
1062
|
-
|
|
1059
|
+
if (typeof contestJSON.medal === "string") ; else {
|
|
1060
|
+
for (const k in contestJSON.medal) {
|
|
1061
|
+
const v = contestJSON.medal[k];
|
|
1062
|
+
{
|
|
1063
|
+
const award = [];
|
|
1064
|
+
let rank = 1;
|
|
1065
|
+
const work = (key, medalType) => {
|
|
1066
|
+
if (Object.keys(v).includes(key)) {
|
|
1067
|
+
const a = new Award();
|
|
1068
|
+
a.medalType = medalType;
|
|
1069
|
+
a.minRank = rank;
|
|
1070
|
+
rank += Number(v[key]);
|
|
1071
|
+
a.maxRank = rank - 1;
|
|
1072
|
+
award.push(a);
|
|
1073
|
+
}
|
|
1074
|
+
};
|
|
1075
|
+
work("gold", MedalType.GOLD);
|
|
1076
|
+
work("silver", MedalType.SILVER);
|
|
1077
|
+
work("bronze", MedalType.BRONZE);
|
|
1078
|
+
{
|
|
1063
1079
|
const a = new Award();
|
|
1064
|
-
a.medalType =
|
|
1080
|
+
a.medalType = MedalType.HONORABLE;
|
|
1065
1081
|
a.minRank = rank;
|
|
1066
|
-
|
|
1067
|
-
a.maxRank = rank - 1;
|
|
1082
|
+
a.maxRank = 1061109567;
|
|
1068
1083
|
award.push(a);
|
|
1069
1084
|
}
|
|
1070
|
-
|
|
1071
|
-
work("gold", MedalType.GOLD);
|
|
1072
|
-
work("silver", MedalType.SILVER);
|
|
1073
|
-
work("bronze", MedalType.BRONZE);
|
|
1074
|
-
{
|
|
1075
|
-
const a = new Award();
|
|
1076
|
-
a.medalType = MedalType.HONORABLE;
|
|
1077
|
-
a.minRank = rank;
|
|
1078
|
-
a.maxRank = 1061109567;
|
|
1079
|
-
award.push(a);
|
|
1085
|
+
c.awards.set(k, award);
|
|
1080
1086
|
}
|
|
1081
|
-
c.awards.set(k, award);
|
|
1082
1087
|
}
|
|
1083
1088
|
}
|
|
1084
1089
|
})();
|
|
@@ -1190,11 +1195,13 @@ class RankStatistics {
|
|
|
1190
1195
|
this.teamSolvedNum = [];
|
|
1191
1196
|
this.teamSolvedNumIndex = [];
|
|
1192
1197
|
this.maxSolvedProblems = 0;
|
|
1198
|
+
this.effectiveTeamNum = 0;
|
|
1193
1199
|
}
|
|
1194
1200
|
reset() {
|
|
1195
1201
|
this.teamSolvedNum = [];
|
|
1196
1202
|
this.teamSolvedNumIndex = [];
|
|
1197
1203
|
this.maxSolvedProblems = 0;
|
|
1204
|
+
this.effectiveTeamNum = 0;
|
|
1198
1205
|
}
|
|
1199
1206
|
getTeamSolvedNumIndex(solvedNum) {
|
|
1200
1207
|
return this.teamSolvedNumIndex[solvedNum] ?? 0;
|
|
@@ -1420,6 +1427,8 @@ class Rank {
|
|
|
1420
1427
|
this.teams.sort(Team.compare);
|
|
1421
1428
|
this.buildTeamRank();
|
|
1422
1429
|
this.buildOrgRank();
|
|
1430
|
+
this.rankStatistics.effectiveTeamNum = this.teams.filter((t) => t.isEffectiveTeam).length;
|
|
1431
|
+
this.buildAwards();
|
|
1423
1432
|
this.teams.forEach((t) => t.calcAwards(this.contest.awards?.get(this.options.group)));
|
|
1424
1433
|
this.teams.forEach((t) => t.postProcessPlaceChartPoints());
|
|
1425
1434
|
})();
|
|
@@ -1496,6 +1505,41 @@ class Rank {
|
|
|
1496
1505
|
res.sort();
|
|
1497
1506
|
return res;
|
|
1498
1507
|
}
|
|
1508
|
+
buildAwards() {
|
|
1509
|
+
if (this.contest.medal === "ccpc") {
|
|
1510
|
+
this.contest.awards = /* @__PURE__ */ new Map();
|
|
1511
|
+
const tot = this.rankStatistics.effectiveTeamNum;
|
|
1512
|
+
const award = [];
|
|
1513
|
+
const gold = new Award();
|
|
1514
|
+
const silver = new Award();
|
|
1515
|
+
const bronze = new Award();
|
|
1516
|
+
{
|
|
1517
|
+
gold.medalType = MedalType.GOLD;
|
|
1518
|
+
gold.minRank = 1;
|
|
1519
|
+
gold.maxRank = Math.ceil(tot * 0.1);
|
|
1520
|
+
if (gold.maxRank >= gold.minRank) {
|
|
1521
|
+
award.push(gold);
|
|
1522
|
+
}
|
|
1523
|
+
}
|
|
1524
|
+
{
|
|
1525
|
+
silver.medalType = MedalType.SILVER;
|
|
1526
|
+
silver.minRank = gold.maxRank + 1;
|
|
1527
|
+
silver.maxRank = Math.ceil(tot * 0.3);
|
|
1528
|
+
if (silver.maxRank >= silver.minRank) {
|
|
1529
|
+
award.push(silver);
|
|
1530
|
+
}
|
|
1531
|
+
}
|
|
1532
|
+
{
|
|
1533
|
+
bronze.medalType = MedalType.BRONZE;
|
|
1534
|
+
bronze.minRank = silver.maxRank + 1;
|
|
1535
|
+
bronze.maxRank = Math.ceil(tot * 0.6);
|
|
1536
|
+
if (bronze.maxRank >= bronze.minRank) {
|
|
1537
|
+
award.push(bronze);
|
|
1538
|
+
}
|
|
1539
|
+
}
|
|
1540
|
+
this.contest.awards.set("official", award);
|
|
1541
|
+
}
|
|
1542
|
+
}
|
|
1499
1543
|
filterTeamByOrg(team) {
|
|
1500
1544
|
const o = this.options;
|
|
1501
1545
|
if (o.enableFilterTeamsByGroup) {
|
package/dist/index.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { TimeUnit, SubmissionStatus, Submission as Submission$1, Submissions as Submissions$1, BalloonColor, Problem as Problem$1, Problems as Problems$1, Lang, CalculationOfPenalty, StatusTimeDisplay, Image, ContestState, Contest as Contest$1, Team as Team$1, Teams as Teams$1, ContestIndex as ContestIndex$1 } from '@xcpcio/types';
|
|
1
|
+
import { TimeUnit, SubmissionStatus, Submission as Submission$1, Submissions as Submissions$1, BalloonColor, Problem as Problem$1, Problems as Problems$1, Lang, CalculationOfPenalty, StatusTimeDisplay, MedalPreset, Image, ContestState, Contest as Contest$1, Team as Team$1, Teams as Teams$1, ContestIndex as ContestIndex$1 } from '@xcpcio/types';
|
|
2
2
|
import dayjs from 'dayjs';
|
|
3
3
|
export { default as dayjs } from 'dayjs';
|
|
4
4
|
import * as XLSX from 'xlsx-js-style';
|
|
@@ -133,7 +133,7 @@ declare class Contest {
|
|
|
133
133
|
problemsMap: Map<string, Problem>;
|
|
134
134
|
statusTimeDisplay: StatusTimeDisplay;
|
|
135
135
|
badge?: string;
|
|
136
|
-
medal?: Record<string, Record<string, number
|
|
136
|
+
medal?: Record<string, Record<string, number>> | MedalPreset;
|
|
137
137
|
awards?: Awards;
|
|
138
138
|
organization?: string;
|
|
139
139
|
group: Map<string, Group>;
|
|
@@ -187,6 +187,7 @@ declare class Team {
|
|
|
187
187
|
get penaltyToMinute(): number;
|
|
188
188
|
get dirt(): number;
|
|
189
189
|
get membersToString(): string | undefined;
|
|
190
|
+
get isEffectiveTeam(): boolean;
|
|
190
191
|
calcSolvedData(options: ContestOptions): void;
|
|
191
192
|
calcAwards(awards?: Award[]): void;
|
|
192
193
|
isEqualRank(otherTeam: Team): boolean;
|
|
@@ -201,6 +202,7 @@ declare class RankStatistics {
|
|
|
201
202
|
teamSolvedNum: Array<number>;
|
|
202
203
|
teamSolvedNumIndex: Array<number>;
|
|
203
204
|
maxSolvedProblems: number;
|
|
205
|
+
effectiveTeamNum: number;
|
|
204
206
|
constructor();
|
|
205
207
|
reset(): void;
|
|
206
208
|
getTeamSolvedNumIndex(solvedNum: number): number;
|
|
@@ -259,6 +261,7 @@ declare class Rank {
|
|
|
259
261
|
buildTeamRank(): void;
|
|
260
262
|
buildOrgRank(): void;
|
|
261
263
|
buildOrganizations(): string[];
|
|
264
|
+
buildAwards(): void;
|
|
262
265
|
filterTeamByOrg(team: Team): boolean;
|
|
263
266
|
getSubmissions(): Submissions;
|
|
264
267
|
buildBalloons(): void;
|
package/dist/index.mjs
CHANGED
|
@@ -626,6 +626,9 @@ class Team {
|
|
|
626
626
|
}
|
|
627
627
|
return this.members?.join(", ");
|
|
628
628
|
}
|
|
629
|
+
get isEffectiveTeam() {
|
|
630
|
+
return this.solvedProblemNum > 0;
|
|
631
|
+
}
|
|
629
632
|
calcSolvedData(options) {
|
|
630
633
|
this.solvedProblemNum = 0;
|
|
631
634
|
this.attemptedProblemNum = 0;
|
|
@@ -1022,32 +1025,34 @@ function createContest(contestJSON) {
|
|
|
1022
1025
|
return;
|
|
1023
1026
|
}
|
|
1024
1027
|
c.awards = /* @__PURE__ */ new Map();
|
|
1025
|
-
|
|
1026
|
-
const
|
|
1027
|
-
|
|
1028
|
-
|
|
1029
|
-
|
|
1030
|
-
|
|
1031
|
-
|
|
1028
|
+
if (typeof contestJSON.medal === "string") ; else {
|
|
1029
|
+
for (const k in contestJSON.medal) {
|
|
1030
|
+
const v = contestJSON.medal[k];
|
|
1031
|
+
{
|
|
1032
|
+
const award = [];
|
|
1033
|
+
let rank = 1;
|
|
1034
|
+
const work = (key, medalType) => {
|
|
1035
|
+
if (Object.keys(v).includes(key)) {
|
|
1036
|
+
const a = new Award();
|
|
1037
|
+
a.medalType = medalType;
|
|
1038
|
+
a.minRank = rank;
|
|
1039
|
+
rank += Number(v[key]);
|
|
1040
|
+
a.maxRank = rank - 1;
|
|
1041
|
+
award.push(a);
|
|
1042
|
+
}
|
|
1043
|
+
};
|
|
1044
|
+
work("gold", MedalType.GOLD);
|
|
1045
|
+
work("silver", MedalType.SILVER);
|
|
1046
|
+
work("bronze", MedalType.BRONZE);
|
|
1047
|
+
{
|
|
1032
1048
|
const a = new Award();
|
|
1033
|
-
a.medalType =
|
|
1049
|
+
a.medalType = MedalType.HONORABLE;
|
|
1034
1050
|
a.minRank = rank;
|
|
1035
|
-
|
|
1036
|
-
a.maxRank = rank - 1;
|
|
1051
|
+
a.maxRank = 1061109567;
|
|
1037
1052
|
award.push(a);
|
|
1038
1053
|
}
|
|
1039
|
-
|
|
1040
|
-
work("gold", MedalType.GOLD);
|
|
1041
|
-
work("silver", MedalType.SILVER);
|
|
1042
|
-
work("bronze", MedalType.BRONZE);
|
|
1043
|
-
{
|
|
1044
|
-
const a = new Award();
|
|
1045
|
-
a.medalType = MedalType.HONORABLE;
|
|
1046
|
-
a.minRank = rank;
|
|
1047
|
-
a.maxRank = 1061109567;
|
|
1048
|
-
award.push(a);
|
|
1054
|
+
c.awards.set(k, award);
|
|
1049
1055
|
}
|
|
1050
|
-
c.awards.set(k, award);
|
|
1051
1056
|
}
|
|
1052
1057
|
}
|
|
1053
1058
|
})();
|
|
@@ -1159,11 +1164,13 @@ class RankStatistics {
|
|
|
1159
1164
|
this.teamSolvedNum = [];
|
|
1160
1165
|
this.teamSolvedNumIndex = [];
|
|
1161
1166
|
this.maxSolvedProblems = 0;
|
|
1167
|
+
this.effectiveTeamNum = 0;
|
|
1162
1168
|
}
|
|
1163
1169
|
reset() {
|
|
1164
1170
|
this.teamSolvedNum = [];
|
|
1165
1171
|
this.teamSolvedNumIndex = [];
|
|
1166
1172
|
this.maxSolvedProblems = 0;
|
|
1173
|
+
this.effectiveTeamNum = 0;
|
|
1167
1174
|
}
|
|
1168
1175
|
getTeamSolvedNumIndex(solvedNum) {
|
|
1169
1176
|
return this.teamSolvedNumIndex[solvedNum] ?? 0;
|
|
@@ -1389,6 +1396,8 @@ class Rank {
|
|
|
1389
1396
|
this.teams.sort(Team.compare);
|
|
1390
1397
|
this.buildTeamRank();
|
|
1391
1398
|
this.buildOrgRank();
|
|
1399
|
+
this.rankStatistics.effectiveTeamNum = this.teams.filter((t) => t.isEffectiveTeam).length;
|
|
1400
|
+
this.buildAwards();
|
|
1392
1401
|
this.teams.forEach((t) => t.calcAwards(this.contest.awards?.get(this.options.group)));
|
|
1393
1402
|
this.teams.forEach((t) => t.postProcessPlaceChartPoints());
|
|
1394
1403
|
})();
|
|
@@ -1465,6 +1474,41 @@ class Rank {
|
|
|
1465
1474
|
res.sort();
|
|
1466
1475
|
return res;
|
|
1467
1476
|
}
|
|
1477
|
+
buildAwards() {
|
|
1478
|
+
if (this.contest.medal === "ccpc") {
|
|
1479
|
+
this.contest.awards = /* @__PURE__ */ new Map();
|
|
1480
|
+
const tot = this.rankStatistics.effectiveTeamNum;
|
|
1481
|
+
const award = [];
|
|
1482
|
+
const gold = new Award();
|
|
1483
|
+
const silver = new Award();
|
|
1484
|
+
const bronze = new Award();
|
|
1485
|
+
{
|
|
1486
|
+
gold.medalType = MedalType.GOLD;
|
|
1487
|
+
gold.minRank = 1;
|
|
1488
|
+
gold.maxRank = Math.ceil(tot * 0.1);
|
|
1489
|
+
if (gold.maxRank >= gold.minRank) {
|
|
1490
|
+
award.push(gold);
|
|
1491
|
+
}
|
|
1492
|
+
}
|
|
1493
|
+
{
|
|
1494
|
+
silver.medalType = MedalType.SILVER;
|
|
1495
|
+
silver.minRank = gold.maxRank + 1;
|
|
1496
|
+
silver.maxRank = Math.ceil(tot * 0.3);
|
|
1497
|
+
if (silver.maxRank >= silver.minRank) {
|
|
1498
|
+
award.push(silver);
|
|
1499
|
+
}
|
|
1500
|
+
}
|
|
1501
|
+
{
|
|
1502
|
+
bronze.medalType = MedalType.BRONZE;
|
|
1503
|
+
bronze.minRank = silver.maxRank + 1;
|
|
1504
|
+
bronze.maxRank = Math.ceil(tot * 0.6);
|
|
1505
|
+
if (bronze.maxRank >= bronze.minRank) {
|
|
1506
|
+
award.push(bronze);
|
|
1507
|
+
}
|
|
1508
|
+
}
|
|
1509
|
+
this.contest.awards.set("official", award);
|
|
1510
|
+
}
|
|
1511
|
+
}
|
|
1468
1512
|
filterTeamByOrg(team) {
|
|
1469
1513
|
const o = this.options;
|
|
1470
1514
|
if (o.enableFilterTeamsByGroup) {
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@xcpcio/core",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.34.1",
|
|
4
4
|
"description": "XCPCIO Core",
|
|
5
5
|
"author": "Dup4 <lyuzhi.pan@gmail.com>",
|
|
6
6
|
"license": "MIT",
|
|
@@ -46,7 +46,7 @@
|
|
|
46
46
|
"lodash": "^4.17.21",
|
|
47
47
|
"string-width": "^6.1.0",
|
|
48
48
|
"xlsx-js-style": "^1.2.0",
|
|
49
|
-
"@xcpcio/types": "0.
|
|
49
|
+
"@xcpcio/types": "0.34.1"
|
|
50
50
|
},
|
|
51
51
|
"devDependencies": {
|
|
52
52
|
"@babel/types": "^7.22.4",
|
package/src/contest.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type { Contest as IContest, Image, StatusTimeDisplay } from "@xcpcio/types";
|
|
1
|
+
import type { Contest as IContest, Image, MedalPreset, StatusTimeDisplay } from "@xcpcio/types";
|
|
2
2
|
import { ContestState } from "@xcpcio/types";
|
|
3
3
|
|
|
4
4
|
import type { Problem, Problems } from "./problem";
|
|
@@ -28,7 +28,7 @@ export class Contest {
|
|
|
28
28
|
statusTimeDisplay: StatusTimeDisplay;
|
|
29
29
|
|
|
30
30
|
badge?: string;
|
|
31
|
-
medal?: Record<string, Record<string, number
|
|
31
|
+
medal?: Record<string, Record<string, number>> | MedalPreset;
|
|
32
32
|
awards?: Awards;
|
|
33
33
|
organization?: string;
|
|
34
34
|
|
|
@@ -217,37 +217,42 @@ export function createContest(contestJSON: IContest): Contest {
|
|
|
217
217
|
|
|
218
218
|
c.awards = new Map<string, Award[]>();
|
|
219
219
|
|
|
220
|
-
|
|
221
|
-
|
|
220
|
+
if (typeof contestJSON.medal === "string") {
|
|
221
|
+
// eslint-disable-next-line no-empty
|
|
222
|
+
{}
|
|
223
|
+
} else {
|
|
224
|
+
for (const k in contestJSON.medal) {
|
|
225
|
+
const v = contestJSON.medal[k];
|
|
222
226
|
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
227
|
+
{
|
|
228
|
+
const award: Award[] = [];
|
|
229
|
+
|
|
230
|
+
let rank = 1;
|
|
231
|
+
const work = (key: string, medalType: MedalType) => {
|
|
232
|
+
if (Object.keys(v).includes(key)) {
|
|
233
|
+
const a = new Award();
|
|
234
|
+
a.medalType = medalType;
|
|
235
|
+
a.minRank = rank;
|
|
236
|
+
rank += Number(v[key]);
|
|
237
|
+
a.maxRank = rank - 1;
|
|
238
|
+
award.push(a);
|
|
239
|
+
}
|
|
240
|
+
};
|
|
241
|
+
|
|
242
|
+
work("gold", MedalType.GOLD);
|
|
243
|
+
work("silver", MedalType.SILVER);
|
|
244
|
+
work("bronze", MedalType.BRONZE);
|
|
245
|
+
|
|
246
|
+
{
|
|
229
247
|
const a = new Award();
|
|
230
|
-
a.medalType =
|
|
248
|
+
a.medalType = MedalType.HONORABLE;
|
|
231
249
|
a.minRank = rank;
|
|
232
|
-
|
|
233
|
-
a.maxRank = rank - 1;
|
|
250
|
+
a.maxRank = 0x3F3F3F3F;
|
|
234
251
|
award.push(a);
|
|
235
252
|
}
|
|
236
|
-
};
|
|
237
|
-
|
|
238
|
-
work("gold", MedalType.GOLD);
|
|
239
|
-
work("silver", MedalType.SILVER);
|
|
240
|
-
work("bronze", MedalType.BRONZE);
|
|
241
253
|
|
|
242
|
-
|
|
243
|
-
const a = new Award();
|
|
244
|
-
a.medalType = MedalType.HONORABLE;
|
|
245
|
-
a.minRank = rank;
|
|
246
|
-
a.maxRank = 0x3F3F3F3F;
|
|
247
|
-
award.push(a);
|
|
254
|
+
c.awards.set(k, award);
|
|
248
255
|
}
|
|
249
|
-
|
|
250
|
-
c.awards.set(k, award);
|
|
251
256
|
}
|
|
252
257
|
}
|
|
253
258
|
})();
|
package/src/rank-statistics.ts
CHANGED
|
@@ -3,16 +3,22 @@ export class RankStatistics {
|
|
|
3
3
|
teamSolvedNumIndex: Array<number>;
|
|
4
4
|
maxSolvedProblems: number;
|
|
5
5
|
|
|
6
|
+
effectiveTeamNum: number;
|
|
7
|
+
|
|
6
8
|
constructor() {
|
|
7
9
|
this.teamSolvedNum = [];
|
|
8
10
|
this.teamSolvedNumIndex = [];
|
|
9
11
|
this.maxSolvedProblems = 0;
|
|
12
|
+
|
|
13
|
+
this.effectiveTeamNum = 0;
|
|
10
14
|
}
|
|
11
15
|
|
|
12
16
|
reset() {
|
|
13
17
|
this.teamSolvedNum = [];
|
|
14
18
|
this.teamSolvedNumIndex = [];
|
|
15
19
|
this.maxSolvedProblems = 0;
|
|
20
|
+
|
|
21
|
+
this.effectiveTeamNum = 0;
|
|
16
22
|
}
|
|
17
23
|
|
|
18
24
|
getTeamSolvedNumIndex(solvedNum: number): number {
|
package/src/rank.ts
CHANGED
|
@@ -10,6 +10,7 @@ import { Submission } from "./submission";
|
|
|
10
10
|
import { TeamProblemStatistics } from "./problem";
|
|
11
11
|
import { RankStatistics } from "./rank-statistics";
|
|
12
12
|
import { Balloon, type Balloons } from "./balloon";
|
|
13
|
+
import { Award, MedalType } from "./award";
|
|
13
14
|
|
|
14
15
|
export interface SelectOptionItem {
|
|
15
16
|
value: string;
|
|
@@ -342,6 +343,9 @@ export class Rank {
|
|
|
342
343
|
this.buildTeamRank();
|
|
343
344
|
this.buildOrgRank();
|
|
344
345
|
|
|
346
|
+
this.rankStatistics.effectiveTeamNum = this.teams.filter(t => t.isEffectiveTeam).length;
|
|
347
|
+
this.buildAwards();
|
|
348
|
+
|
|
345
349
|
this.teams.forEach(t => t.calcAwards(this.contest.awards?.get(this.options.group)));
|
|
346
350
|
this.teams.forEach(t => t.postProcessPlaceChartPoints());
|
|
347
351
|
})();
|
|
@@ -440,6 +444,48 @@ export class Rank {
|
|
|
440
444
|
return res;
|
|
441
445
|
}
|
|
442
446
|
|
|
447
|
+
buildAwards() {
|
|
448
|
+
if (this.contest.medal === "ccpc") {
|
|
449
|
+
this.contest.awards = new Map<string, Award[]>();
|
|
450
|
+
|
|
451
|
+
const tot = this.rankStatistics.effectiveTeamNum;
|
|
452
|
+
const award: Award[] = [];
|
|
453
|
+
|
|
454
|
+
const gold = new Award();
|
|
455
|
+
const silver = new Award();
|
|
456
|
+
const bronze = new Award();
|
|
457
|
+
|
|
458
|
+
{
|
|
459
|
+
gold.medalType = MedalType.GOLD;
|
|
460
|
+
gold.minRank = 1;
|
|
461
|
+
gold.maxRank = Math.ceil(tot * 0.1);
|
|
462
|
+
if (gold.maxRank >= gold.minRank) {
|
|
463
|
+
award.push(gold);
|
|
464
|
+
}
|
|
465
|
+
}
|
|
466
|
+
|
|
467
|
+
{
|
|
468
|
+
silver.medalType = MedalType.SILVER;
|
|
469
|
+
silver.minRank = gold.maxRank + 1;
|
|
470
|
+
silver.maxRank = Math.ceil(tot * 0.3);
|
|
471
|
+
if (silver.maxRank >= silver.minRank) {
|
|
472
|
+
award.push(silver);
|
|
473
|
+
}
|
|
474
|
+
}
|
|
475
|
+
|
|
476
|
+
{
|
|
477
|
+
bronze.medalType = MedalType.BRONZE;
|
|
478
|
+
bronze.minRank = silver.maxRank + 1;
|
|
479
|
+
bronze.maxRank = Math.ceil(tot * 0.6);
|
|
480
|
+
if (bronze.maxRank >= bronze.minRank) {
|
|
481
|
+
award.push(bronze);
|
|
482
|
+
}
|
|
483
|
+
}
|
|
484
|
+
|
|
485
|
+
this.contest.awards.set("official", award);
|
|
486
|
+
}
|
|
487
|
+
}
|
|
488
|
+
|
|
443
489
|
filterTeamByOrg(team: Team) {
|
|
444
490
|
const o = this.options;
|
|
445
491
|
|
package/src/team.ts
CHANGED
|
@@ -127,6 +127,10 @@ export class Team {
|
|
|
127
127
|
return this.members?.join(", ");
|
|
128
128
|
}
|
|
129
129
|
|
|
130
|
+
get isEffectiveTeam() {
|
|
131
|
+
return this.solvedProblemNum > 0;
|
|
132
|
+
}
|
|
133
|
+
|
|
130
134
|
calcSolvedData(options: ContestOptions) {
|
|
131
135
|
this.solvedProblemNum = 0;
|
|
132
136
|
this.attemptedProblemNum = 0;
|