sejm-calculator/src/mandates.ts

62 wiersze
2.3 KiB
TypeScript
Czysty Zwykły widok Historia

2019-09-07 21:11:03 +00:00
import {committees, constituencies, pastSupport} from './data';
2024-01-10 21:58:43 +00:00
import type {Constituency} from './types';
2019-09-07 21:11:03 +00:00
const calculateLocalSupport = (
support: number[],
pastSupportProjection: number[],
constituency: Constituency,
): number[] => {
const localPastSupport = constituency.pastSupport;
2023-08-18 20:42:33 +00:00
const localPastSupportProjection = committees.map((committee) => (
committee.pastSupportEquivalence
2020-10-18 19:06:38 +00:00
.map((pastCommittee) => localPastSupport[pastCommittee[0]] * pastCommittee[1])
2019-09-07 21:11:03 +00:00
.reduce((a, b) => a + b, 0)
));
const localSupportDeviation = pastSupportProjection
.map((pastCommitteSupportProjection, index) => (
localPastSupportProjection[index] / pastCommitteSupportProjection
2020-10-18 19:06:38 +00:00
));
2019-09-07 21:11:03 +00:00
const localSupport = support.map((committeeSupport, index) => (
committeeSupport * localSupportDeviation[index]
));
2019-09-21 18:39:32 +00:00
if (constituency.name === 'Opole') {
2023-10-20 09:15:18 +00:00
localSupport.push(5.37);
2019-09-21 18:39:32 +00:00
}
2019-09-07 21:11:03 +00:00
return localSupport;
2020-10-18 19:06:38 +00:00
};
2019-09-07 21:11:03 +00:00
2020-11-02 16:56:39 +00:00
export default (support: number[]): number[] => {
2023-08-18 20:42:33 +00:00
const pastSupportProjection = committees.map((committee) => (
committee.pastSupportEquivalence
2020-10-18 19:06:38 +00:00
.map((pastCommittee) => pastSupport[pastCommittee[0]] * pastCommittee[1])
2019-09-07 21:11:03 +00:00
.reduce((a, b) => a + b, 0)
));
2024-01-10 21:58:43 +00:00
const mandates = new Array(support.length + 1).fill(0) as number[];
2020-10-18 19:06:38 +00:00
constituencies.forEach((constituency) => {
2019-09-07 21:11:03 +00:00
const localSupport = calculateLocalSupport(support, pastSupportProjection, constituency);
constituency.support = localSupport;
2019-09-24 17:21:02 +00:00
constituency.mandates = new Array(localSupport.length).fill(0);
2019-09-07 21:11:03 +00:00
const filteredLocalSupport = localSupport.map((localCommitteeSupport, index) => {
if (support[index] < committees[index].threshold) return 0;
return localCommitteeSupport;
});
2024-01-10 21:58:43 +00:00
const quotients: Array<{quotient: number, committeeIndex: number}> = [];
2020-11-02 16:56:39 +00:00
for (let divisor = 1; divisor <= constituency.size; divisor += 1) {
for (let committeeIndex = 0; committeeIndex < localSupport.length; committeeIndex += 1) {
2019-09-07 21:11:03 +00:00
quotients.push({
quotient: filteredLocalSupport[committeeIndex] / divisor,
committeeIndex,
});
}
}
quotients.sort((a, b) => b.quotient - a.quotient);
2020-10-18 19:06:38 +00:00
quotients.slice(0, constituency.size).forEach((quotient) => {
2019-09-24 09:57:02 +00:00
if (quotient.quotient > 0) {
2020-11-02 16:56:39 +00:00
mandates[quotient.committeeIndex] += 1;
constituency.mandates![quotient.committeeIndex] += 1;
2019-09-24 09:57:02 +00:00
}
2019-09-07 21:11:03 +00:00
});
});
return mandates;
2020-10-18 19:06:38 +00:00
};