@zoodogood/utils 5.1.1-change.4255 → 6.0.0-change.4442
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/discordjs/chain/configuration.d.ts +1 -1
- package/lib/discordjs/chain/configuration.d.ts.map +1 -1
- package/lib/discordjs/message_lifecycle.d.ts.map +1 -1
- package/lib/discordjs/message_lifecycle.js +4 -4
- package/lib/objectives/BusyNumeric.d.ts.map +1 -1
- package/lib/objectives/BusyNumeric.js +2 -1
- package/lib/objectives/getRandomElementFromArray.d.ts +13 -8
- package/lib/objectives/getRandomElementFromArray.d.ts.map +1 -1
- package/lib/objectives/getRandomElementFromArray.js +119 -16
- package/package.json +1 -1
|
@@ -2,6 +2,6 @@ import type { DiscordContentLimites } from "../message_content_limits.js";
|
|
|
2
2
|
export interface MaySplitConfiguration {
|
|
3
3
|
fields?: (keyof typeof DiscordContentLimites)[];
|
|
4
4
|
separateBy?: string;
|
|
5
|
-
splay
|
|
5
|
+
splay?: "balanced" | "rest";
|
|
6
6
|
}
|
|
7
7
|
//# sourceMappingURL=configuration.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"configuration.d.ts","sourceRoot":"","sources":["../../../src/discordjs/chain/configuration.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,qBAAqB,EAAE,MAAM,8BAA8B,CAAC;AAE1E,MAAM,WAAW,qBAAqB;IACrC,MAAM,CAAC,EAAE,CAAC,MAAM,OAAO,qBAAqB,CAAC,EAAE,CAAC;IAChD,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,KAAK,EAAE,UAAU,GAAG,MAAM,CAAC;
|
|
1
|
+
{"version":3,"file":"configuration.d.ts","sourceRoot":"","sources":["../../../src/discordjs/chain/configuration.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,qBAAqB,EAAE,MAAM,8BAA8B,CAAC;AAE1E,MAAM,WAAW,qBAAqB;IACrC,MAAM,CAAC,EAAE,CAAC,MAAM,OAAO,qBAAqB,CAAC,EAAE,CAAC;IAChD,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,KAAK,CAAC,EAAE,UAAU,GAAG,MAAM,CAAC;CAC5B"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"message_lifecycle.d.ts","sourceRoot":"","sources":["../../src/discordjs/message_lifecycle.ts"],"names":[],"mappings":"AAAA,OAAO,EACN,KAAK,iBAAiB,EAEtB,KAAK,eAAe,EACpB,YAAY,EACZ,OAAO,EACP,KAAK,oBAAoB,EAEzB,KAAK,gBAAgB,EACrB,IAAI,EAEJ,MAAM,YAAY,CAAC;
|
|
1
|
+
{"version":3,"file":"message_lifecycle.d.ts","sourceRoot":"","sources":["../../src/discordjs/message_lifecycle.ts"],"names":[],"mappings":"AAAA,OAAO,EACN,KAAK,iBAAiB,EAEtB,KAAK,eAAe,EACpB,YAAY,EACZ,OAAO,EACP,KAAK,oBAAoB,EAEzB,KAAK,gBAAgB,EACrB,IAAI,EAEJ,MAAM,YAAY,CAAC;AAQpB,OAAO,EAAE,cAAc,EAAE,MAAM,yBAAyB,CAAC;AAEzD,OAAO,EAEN,KAAK,qBAAqB,EAG1B,MAAM,UAAU,CAAC;AAElB,iBAAS,UAAU,CAClB,CAAC,SACE,IAAI,GACJ,gBAAgB,GAChB,OAAO,GACP,CAAC,EAAE,GAAG;IAAE,OAAO,EAAE,gBAAgB,CAAA;CAAE,CAAC,GACpC,CAAC,EAAE,GAAG;IAAE,IAAI,EAAE,CAAC,OAAO,EAAE,oBAAoB,KAAK,OAAO,CAAC,OAAO,CAAC,CAAA;CAAE,CAAC,EAEvE,MAAM,EAAE,CAAC,GACP;IACF,IAAI,EAAE,CAAC,OAAO,EAAE,oBAAoB,KAAK,OAAO,CAAC,OAAO,CAAC,CAAC;CAC1D,CAWA;AAED,MAAM,WAAW,eAAe;IAC/B,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,IAAI,CAAC,EAAE,OAAO,CAAC;IACf,MAAM,CAAC,EAAE;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,OAAO,CAAC,EAAE,MAAM,CAAA;KAAE,CAAC;IAC5C,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,KAAK,CAAC,EAAE,eAAe,CAAC;IACxB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,MAAM,CAAC,EAAE;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,MAAM,CAAC;QAAC,MAAM,CAAC,EAAE,OAAO,CAAA;KAAE,EAAE,CAAC;IAC7D,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,MAAM,CAAC,EAAE;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,OAAO,CAAC,EAAE,MAAM,CAAA;KAAE,CAAC;IAC5C,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,SAAS,CAAC,EAAE,MAAM,EAAE,CAAC;IACrB,eAAe,CAAC,EAAE,qBAAqB,CAAC;IACxC,YAAY,CAAC,EAAE,eAAe,CAAC;IAC/B,UAAU,CAAC,EAAE,UAAU,CAAC,OAAO,cAAc,CAAC,CAAC;IAC/C,KAAK,CAAC,EAAE,iBAAiB,EAAE,CAAC;CAC5B;AAED,wBAAgB,YAAY,CAC3B,KAAK,EAAE;KAAG,GAAG,IAAI,MAAM,YAAY,CAAC,MAAM,CAAC,GAAG,OAAO;CAAE,WAmBvD;AAED,wBAAgB,aAAa,CAAC,WAAW,EAAE,eAAe,wBA8DzD;AAED;;;GAGG;AAEH,wBAAsB,eAAe,CAAC,OAAO,SAAS,OAAO,EAC5D,MAAM,EAAE,UAAU,CAAC,OAAO,UAAU,CAAC,CAAC,CAAC,CAAC,EACxC,OAAO,EAAE,eAAe,+BAIxB;AAED,wBAAsB,WAAW,CAAC,OAAO,SAAS,OAAO,EACxD,MAAM,EAAE,UAAU,CAAC,OAAO,UAAU,CAAC,CAAC,CAAC,CAAC,EACxC,YAAY,EAAE,UAAU,CAAC,OAAO,aAAa,CAAC,EAC9C,WAAW,EAAE,eAAe,GAC1B,OAAO,CAAC,OAAO,CAAC,OAAO,CAAC,CAAC,CAoG3B"}
|
|
@@ -1,5 +1,4 @@
|
|
|
1
1
|
import { BaseInteraction, EmbedBuilder, Message, User, resolveColor, } from "discord.js";
|
|
2
|
-
import assert from "node:assert";
|
|
3
2
|
import { chain_map } from "./chain/map.js";
|
|
4
3
|
import { _rob_already_prepared, move_partial_data_to_chain, } from "./chain/move_partial_data_to_chain.js";
|
|
5
4
|
import { codeOfEmoji } from "./helpers.js";
|
|
@@ -32,6 +31,9 @@ export function isEmptyEmbed(embed) {
|
|
|
32
31
|
return isEveryPropertyDefault;
|
|
33
32
|
}
|
|
34
33
|
export function createMessage(mut_payload) {
|
|
34
|
+
if (mut_payload.ephemeral && mut_payload.maySplitMessage) {
|
|
35
|
+
throw new Error("Don't use ephemeral option with message spliting");
|
|
36
|
+
}
|
|
35
37
|
const { maySplitMessage } = mut_payload;
|
|
36
38
|
maySplitMessage &&
|
|
37
39
|
(() => {
|
|
@@ -114,7 +116,6 @@ export async function sendMessage(target, message_data, mut_payload) {
|
|
|
114
116
|
}, mut_payload.delete);
|
|
115
117
|
}
|
|
116
118
|
if (mut_payload._chain_child) {
|
|
117
|
-
assert(!mut_payload.ephemeral);
|
|
118
119
|
mut_payload._chain_child ||= {};
|
|
119
120
|
mut_payload._chain_child.reference = message.id;
|
|
120
121
|
let createdNow = false;
|
|
@@ -124,7 +125,6 @@ export async function sendMessage(target, message_data, mut_payload) {
|
|
|
124
125
|
if (!chain) {
|
|
125
126
|
return;
|
|
126
127
|
}
|
|
127
|
-
const channel = sendableOf(target);
|
|
128
128
|
const index = chain.indexOf(message.id);
|
|
129
129
|
if (index === 0) {
|
|
130
130
|
return;
|
|
@@ -133,7 +133,7 @@ export async function sendMessage(target, message_data, mut_payload) {
|
|
|
133
133
|
if (!child_message_id) {
|
|
134
134
|
return;
|
|
135
135
|
}
|
|
136
|
-
return await
|
|
136
|
+
return await sendableOf(target).messages.fetch(child_message_id);
|
|
137
137
|
})()) ||
|
|
138
138
|
(await (async () => {
|
|
139
139
|
const child_message = await justSendMessage(sendableOf(target), mut_payload._chain_child);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"BusyNumeric.d.ts","sourceRoot":"","sources":["../../src/objectives/BusyNumeric.ts"],"names":[],"mappings":"AAuBA;;;;;;;GAOG;AAQH,wBAAgB,YAAY,CAAC,IAAI,EAAE,SAAS,CAAC,MAAM,EAAE,MAAM,CAAC,UAE3D;AACD,qBAAa,WAAW;;IACtB,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,UAAU,EAAE,CAAC,SAAS,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,EAAE,CAAM;IACxD,SAAS,EAAE,MAAM,CAAC;IAElB,IAAI,eAAe,YASlB;IAED,IAAI,aAAa,YAShB;gBACW,KAAK,EAAE,MAAM;
|
|
1
|
+
{"version":3,"file":"BusyNumeric.d.ts","sourceRoot":"","sources":["../../src/objectives/BusyNumeric.ts"],"names":[],"mappings":"AAuBA;;;;;;;GAOG;AAQH,wBAAgB,YAAY,CAAC,IAAI,EAAE,SAAS,CAAC,MAAM,EAAE,MAAM,CAAC,UAE3D;AACD,qBAAa,WAAW;;IACtB,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,UAAU,EAAE,CAAC,SAAS,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,EAAE,CAAM;IACxD,SAAS,EAAE,MAAM,CAAC;IAElB,IAAI,eAAe,YASlB;IAED,IAAI,aAAa,YAShB;gBACW,KAAK,EAAE,MAAM;IAOzB,SAAS,CAAC,KAAK,EAAE,MAAM;IAIvB,cAAc;IAMd,OAAO,CAAC,EAAE,EAAE,MAAM;;;;;IAqClB,WAAW,CAAC,KAAK,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM;IAkEtC,OAAO;;;;MAUL;CACH"}
|
|
@@ -59,6 +59,7 @@ export class BusyNumeric {
|
|
|
59
59
|
}
|
|
60
60
|
constructor(range) {
|
|
61
61
|
assert(range > 0, "Range must be positive");
|
|
62
|
+
assert(range <= Number.MAX_SAFE_INTEGER, "range <= Number.MAX_SAFE_INTEGER");
|
|
62
63
|
this.range = range;
|
|
63
64
|
this.free_area = this.range + /* includes position 0 */ 1;
|
|
64
65
|
}
|
|
@@ -131,7 +132,7 @@ export class BusyNumeric {
|
|
|
131
132
|
const [index, points] = is_left_included
|
|
132
133
|
? [place_index - 1, [target[0], end]]
|
|
133
134
|
: [place_index, [start, target[1]]];
|
|
134
|
-
assert(!(target[0] <= start && target[1] >= end), "Assertion error: [start, end] in
|
|
135
|
+
assert(!(target[0] <= start && target[1] >= end), "Assertion error: range [start, end] already in busy area");
|
|
135
136
|
this.free_area -= size_of_area(points) - size_of_area(target);
|
|
136
137
|
this.busy_areas.splice(index, 1, points);
|
|
137
138
|
return;
|
|
@@ -1,17 +1,20 @@
|
|
|
1
|
-
import { create_default_preventable } from "../primitives/createDefaultPreventable.js";
|
|
2
1
|
import { BusyNumeric } from "./BusyNumeric.js";
|
|
2
|
+
export declare const _WEIGHT_AUTO = 1000001;
|
|
3
3
|
interface IParams<T> {
|
|
4
|
-
associatedWeights?: number[];
|
|
4
|
+
associatedWeights?: number[] | typeof _WEIGHT_AUTO;
|
|
5
5
|
filter?: (item: T) => boolean;
|
|
6
6
|
}
|
|
7
7
|
interface IPickContext<T> {
|
|
8
|
-
busy_preventable: ReturnType<typeof create_default_preventable> & {
|
|
9
|
-
require_insert(): void;
|
|
10
|
-
};
|
|
11
8
|
item: T;
|
|
12
9
|
pick: (context: IPickContext<T>) => boolean;
|
|
13
10
|
threshold: number;
|
|
14
11
|
point: number;
|
|
12
|
+
index_of_item: number;
|
|
13
|
+
}
|
|
14
|
+
interface ILotteryContext {
|
|
15
|
+
index_of_item: number;
|
|
16
|
+
point: number;
|
|
17
|
+
remove_current_from_pull(): void;
|
|
15
18
|
}
|
|
16
19
|
export declare class RandomizerContext<T> {
|
|
17
20
|
hotel: BusyNumeric;
|
|
@@ -20,13 +23,15 @@ export declare class RandomizerContext<T> {
|
|
|
20
23
|
constructor(array: T[], thresholds?: number[]);
|
|
21
24
|
static from<T>({ array, associatedWeights, }: {
|
|
22
25
|
array: T[];
|
|
23
|
-
associatedWeights?:
|
|
26
|
+
associatedWeights?: number[];
|
|
24
27
|
}): RandomizerContext<T>;
|
|
25
28
|
pickRandom(pick?: IPickContext<T>["pick"]): T | undefined;
|
|
29
|
+
playLottery(): ILotteryContext | undefined;
|
|
26
30
|
}
|
|
27
31
|
export declare function pickInThresholds(thresholds: number[], value: number): number;
|
|
28
|
-
export declare function thresholdsOf(weights: NonNullable<
|
|
29
|
-
export declare function getRandomElementIndexInWeights(weights: NonNullable<
|
|
32
|
+
export declare function thresholdsOf(weights: NonNullable<number[]>): number[];
|
|
33
|
+
export declare function getRandomElementIndexInWeights(weights: NonNullable<number[]>): number | never;
|
|
30
34
|
export declare function getRandomElementFromArray<T>(array: T[], { associatedWeights, filter }?: IParams<T>): T | undefined;
|
|
35
|
+
export declare function getRandomElementsFromArray<T>(array: T[], amount?: number, { associatedWeights, filter }?: IParams<T>): T[];
|
|
31
36
|
export {};
|
|
32
37
|
//# sourceMappingURL=getRandomElementFromArray.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"getRandomElementFromArray.d.ts","sourceRoot":"","sources":["../../src/objectives/getRandomElementFromArray.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,
|
|
1
|
+
{"version":3,"file":"getRandomElementFromArray.d.ts","sourceRoot":"","sources":["../../src/objectives/getRandomElementFromArray.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,WAAW,EAAgB,MAAM,kBAAkB,CAAC;AAG7D,eAAO,MAAM,YAAY,UAAY,CAAC;AACtC,UAAU,OAAO,CAAC,CAAC;IAClB,iBAAiB,CAAC,EAAE,MAAM,EAAE,GAAG,OAAO,YAAY,CAAC;IACnD,MAAM,CAAC,EAAE,CAAC,IAAI,EAAE,CAAC,KAAK,OAAO,CAAC;CAC9B;AAED,UAAU,YAAY,CAAC,CAAC;IACvB,IAAI,EAAE,CAAC,CAAC;IACR,IAAI,EAAE,CAAC,OAAO,EAAE,YAAY,CAAC,CAAC,CAAC,KAAK,OAAO,CAAC;IAC5C,SAAS,EAAE,MAAM,CAAC;IAClB,KAAK,EAAE,MAAM,CAAC;IACd,aAAa,EAAE,MAAM,CAAC;CACtB;AAED,UAAU,eAAe;IACxB,aAAa,EAAE,MAAM,CAAC;IACtB,KAAK,EAAE,MAAM,CAAC;IACd,wBAAwB,IAAI,IAAI,CAAC;CACjC;AAED,qBAAa,iBAAiB,CAAC,CAAC;IAC/B,KAAK,EAAE,WAAW,CAAC;IACnB,KAAK,EAAE,CAAC,EAAE,CAAC;IACX,UAAU,CAAC,EAAE,MAAM,EAAE,CAAC;gBACV,KAAK,EAAE,CAAC,EAAE,EAAE,UAAU,CAAC,EAAE,MAAM,EAAE;IAc7C,MAAM,CAAC,IAAI,CAAC,CAAC,EAAE,EACd,KAAK,EACL,iBAAiB,GACjB,EAAE;QACF,KAAK,EAAE,CAAC,EAAE,CAAC;QACX,iBAAiB,CAAC,EAAE,MAAM,EAAE,CAAC;KAC7B;IAID,UAAU,CAAC,IAAI,GAAE,YAAY,CAAC,CAAC,CAAC,CAAC,MAAM,CAAc,GAAG,CAAC,GAAG,SAAS;IAsDrE,WAAW,IAAI,eAAe,GAAG,SAAS;CAiD1C;AAED,wBAAgB,gBAAgB,CAAC,UAAU,EAAE,MAAM,EAAE,EAAE,KAAK,EAAE,MAAM,GAAG,MAAM,CAY5E;AAED,wBAAgB,YAAY,CAAC,OAAO,EAAE,WAAW,CAAC,MAAM,EAAE,CAAC,GAGG,MAAM,EAAE,CACrE;AAED,wBAAgB,8BAA8B,CAC7C,OAAO,EAAE,WAAW,CAAC,MAAM,EAAE,CAAC,GAC5B,MAAM,GAAG,KAAK,CAKhB;AAkBD,wBAAgB,yBAAyB,CAAC,CAAC,EAC1C,KAAK,EAAE,CAAC,EAAE,EACV,EAAE,iBAAiB,EAAE,MAAmB,EAAE,GAAE,OAAO,CAAC,CAAC,CAAM,iBA8B3D;AAED,wBAAgB,0BAA0B,CAAC,CAAC,EAC3C,KAAK,EAAE,CAAC,EAAE,EACV,MAAM,SAAI,EACV,EAAE,iBAAiB,EAAE,MAAmB,EAAE,GAAE,OAAO,CAAC,CAAC,CAAM,OAiD3D"}
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import assert from "node:assert";
|
|
2
2
|
import { binary_search } from "../primitives/binary_search.js";
|
|
3
|
-
import { create_default_preventable } from "../primitives/createDefaultPreventable.js";
|
|
4
3
|
import { BusyNumeric, size_of_area } from "./BusyNumeric.js";
|
|
5
4
|
import { getRandomNumberInRange } from "./getRandomNumberInRange.js";
|
|
5
|
+
export const _WEIGHT_AUTO = 1_000_001;
|
|
6
6
|
export class RandomizerContext {
|
|
7
7
|
hotel;
|
|
8
8
|
array;
|
|
@@ -13,6 +13,13 @@ export class RandomizerContext {
|
|
|
13
13
|
const range = thresholds?.at(-1) ?? array.length - 1;
|
|
14
14
|
this.hotel = new BusyNumeric(range);
|
|
15
15
|
}
|
|
16
|
+
/* Add to your code
|
|
17
|
+
if (associatedWeights === AUTO) {
|
|
18
|
+
// @ts-expect-error User known about AUTO keyword
|
|
19
|
+
associatedWeights = array.map(($) => $._weight);
|
|
20
|
+
}
|
|
21
|
+
associatedWeights?.length && assert(associatedWeights.at(-1)! < Number.MAX_SAFE_INTEGER)
|
|
22
|
+
*/
|
|
16
23
|
static from({ array, associatedWeights, }) {
|
|
17
24
|
const thresholds = associatedWeights && thresholdsOf(associatedWeights);
|
|
18
25
|
return new RandomizerContext(array, thresholds);
|
|
@@ -24,13 +31,17 @@ export class RandomizerContext {
|
|
|
24
31
|
if (!segments_count) {
|
|
25
32
|
break;
|
|
26
33
|
}
|
|
27
|
-
const target_of_free = getRandomNumberInRange({
|
|
34
|
+
const target_of_free = getRandomNumberInRange({
|
|
35
|
+
max: hotel.free_area - 1,
|
|
36
|
+
});
|
|
28
37
|
const position = (() => {
|
|
29
38
|
let segment = 0;
|
|
30
39
|
let distance = target_of_free;
|
|
31
40
|
let position = 0;
|
|
32
41
|
while (true) {
|
|
33
|
-
const free_area = (hotel.busy_areas[segment]?.[0] ?? hotel.range + 1) -
|
|
42
|
+
const free_area = (hotel.busy_areas[segment]?.[0] ?? hotel.range + 1) -
|
|
43
|
+
(hotel.busy_areas[segment - 1]?.[1] ?? -1) -
|
|
44
|
+
1;
|
|
34
45
|
distance -= free_area;
|
|
35
46
|
position += free_area;
|
|
36
47
|
if (distance < 0) {
|
|
@@ -40,33 +51,69 @@ export class RandomizerContext {
|
|
|
40
51
|
segment++;
|
|
41
52
|
}
|
|
42
53
|
})();
|
|
43
|
-
|
|
44
|
-
|
|
54
|
+
const index = thresholds
|
|
55
|
+
? pickInThresholds(thresholds, position)
|
|
56
|
+
: position;
|
|
45
57
|
const element = array[index];
|
|
46
58
|
const pickContext = {
|
|
47
|
-
busy_preventable: {
|
|
48
|
-
...create_default_preventable(),
|
|
49
|
-
require_insert() {
|
|
50
|
-
_require_insert = true;
|
|
51
|
-
}
|
|
52
|
-
},
|
|
53
59
|
item: element,
|
|
60
|
+
index_of_item: index,
|
|
54
61
|
pick,
|
|
55
62
|
threshold: index,
|
|
56
63
|
point: position,
|
|
57
64
|
};
|
|
58
65
|
const picked = pick(pickContext);
|
|
59
|
-
if (_require_insert || !picked && !pickContext.busy_preventable.default_prevented()) {
|
|
60
|
-
thresholds
|
|
61
|
-
? hotel.insert_area(thresholds[index - 1] + 1 || 0, thresholds[index])
|
|
62
|
-
: hotel.bifurcate(index);
|
|
63
|
-
}
|
|
64
66
|
if (picked) {
|
|
65
67
|
return element;
|
|
66
68
|
}
|
|
69
|
+
thresholds
|
|
70
|
+
? hotel.insert_area(thresholds[index - 1] + 1 || 0, thresholds[index])
|
|
71
|
+
: hotel.bifurcate(index);
|
|
67
72
|
}
|
|
68
73
|
return undefined;
|
|
69
74
|
}
|
|
75
|
+
playLottery() {
|
|
76
|
+
const { hotel, thresholds } = this;
|
|
77
|
+
while (true) {
|
|
78
|
+
const segments_count = hotel.segments_count();
|
|
79
|
+
if (!segments_count) {
|
|
80
|
+
break;
|
|
81
|
+
}
|
|
82
|
+
const target_of_free = getRandomNumberInRange({
|
|
83
|
+
max: hotel.free_area - 1,
|
|
84
|
+
});
|
|
85
|
+
const position = (() => {
|
|
86
|
+
let segment = 0;
|
|
87
|
+
let distance = target_of_free;
|
|
88
|
+
let position = 0;
|
|
89
|
+
while (true) {
|
|
90
|
+
const free_area = (hotel.busy_areas[segment]?.[0] ?? hotel.range + 1) -
|
|
91
|
+
(hotel.busy_areas[segment - 1]?.[1] ?? -1) -
|
|
92
|
+
1;
|
|
93
|
+
distance -= free_area;
|
|
94
|
+
position += free_area;
|
|
95
|
+
if (distance < 0) {
|
|
96
|
+
return position + distance;
|
|
97
|
+
}
|
|
98
|
+
position += size_of_area(hotel.busy_areas[segment] || [0, hotel.range + 1]);
|
|
99
|
+
segment++;
|
|
100
|
+
}
|
|
101
|
+
})();
|
|
102
|
+
const index = thresholds
|
|
103
|
+
? pickInThresholds(thresholds, position)
|
|
104
|
+
: position;
|
|
105
|
+
const lotteryContext = {
|
|
106
|
+
index_of_item: index,
|
|
107
|
+
point: position,
|
|
108
|
+
remove_current_from_pull() {
|
|
109
|
+
thresholds
|
|
110
|
+
? hotel.insert_area(thresholds[index - 1] + 1 || 0, thresholds[index])
|
|
111
|
+
: hotel.bifurcate(index);
|
|
112
|
+
},
|
|
113
|
+
};
|
|
114
|
+
return lotteryContext;
|
|
115
|
+
}
|
|
116
|
+
}
|
|
70
117
|
}
|
|
71
118
|
export function pickInThresholds(thresholds, value) {
|
|
72
119
|
assert(thresholds.length > 0);
|
|
@@ -108,9 +155,65 @@ export function getRandomElementIndexInWeights(weights) {
|
|
|
108
155
|
Повторяем
|
|
109
156
|
*/
|
|
110
157
|
export function getRandomElementFromArray(array, { associatedWeights, filter = () => true } = {}) {
|
|
158
|
+
assert(array.length, "Invalid array length");
|
|
159
|
+
if (associatedWeights === _WEIGHT_AUTO) {
|
|
160
|
+
// @ts-expect-error User know about AUTO keysymbol
|
|
161
|
+
associatedWeights = array.map(($) => $._weight);
|
|
162
|
+
}
|
|
163
|
+
associatedWeights?.length &&
|
|
164
|
+
assert(associatedWeights.at(-1) < Number.MAX_SAFE_INTEGER);
|
|
111
165
|
assert(!associatedWeights || associatedWeights.length === array.length, "Incorrectly passed argument associatedWeights: The length of the associatedWeights must exactly match the length of the weights array");
|
|
166
|
+
if (array.length === 1) {
|
|
167
|
+
return array[0];
|
|
168
|
+
}
|
|
169
|
+
// light strategy
|
|
170
|
+
if (!filter) {
|
|
171
|
+
if (associatedWeights) {
|
|
172
|
+
return array[getRandomElementIndexInWeights(associatedWeights)];
|
|
173
|
+
}
|
|
174
|
+
return array[Math.floor(Math.random() * array.length)];
|
|
175
|
+
}
|
|
112
176
|
return RandomizerContext.from({
|
|
113
177
|
array,
|
|
114
178
|
associatedWeights,
|
|
115
179
|
}).pickRandom(({ item }) => filter(item));
|
|
116
180
|
}
|
|
181
|
+
export function getRandomElementsFromArray(array, amount = 1, { associatedWeights, filter = () => true } = {}) {
|
|
182
|
+
assert(array.length);
|
|
183
|
+
assert(amount <= array.length);
|
|
184
|
+
assert(amount > 1, `Current amount: ${amount}, use getRandomElementFromArray instead of getRandomElement**s**FromArray if amount is 1`);
|
|
185
|
+
if (associatedWeights === _WEIGHT_AUTO) {
|
|
186
|
+
// @ts-expect-error User know about AUTO keysymbol
|
|
187
|
+
associatedWeights = array.map(($) => $._weight);
|
|
188
|
+
}
|
|
189
|
+
associatedWeights?.length &&
|
|
190
|
+
assert(associatedWeights.at(-1) < Number.MAX_SAFE_INTEGER);
|
|
191
|
+
assert(!associatedWeights || associatedWeights.length === array.length, "Incorrectly passed argument associatedWeights: The length of the associatedWeights must exactly match the length of the weights array");
|
|
192
|
+
if (amount === array.length) {
|
|
193
|
+
return Array.from(array);
|
|
194
|
+
}
|
|
195
|
+
// light strategy
|
|
196
|
+
if (!filter && !associatedWeights) {
|
|
197
|
+
const _array = Array.from(array);
|
|
198
|
+
return Array.from({ length: amount }, () => _array.splice(Math.floor(Math.random() * _array.length), 1)[0]);
|
|
199
|
+
}
|
|
200
|
+
const random_ctx = RandomizerContext.from({
|
|
201
|
+
array,
|
|
202
|
+
associatedWeights,
|
|
203
|
+
});
|
|
204
|
+
return Array.from({ length: amount }, (_, i) => {
|
|
205
|
+
while (true) {
|
|
206
|
+
const lottery_ctx = random_ctx.playLottery();
|
|
207
|
+
if (!lottery_ctx) {
|
|
208
|
+
// BEFORE PULL TO-DO вероятно неграммотное сообщение об ошибке
|
|
209
|
+
throw new Error("Not enought items was pass filter");
|
|
210
|
+
}
|
|
211
|
+
lottery_ctx.remove_current_from_pull();
|
|
212
|
+
const item = array[lottery_ctx.index_of_item];
|
|
213
|
+
if (!filter(item)) {
|
|
214
|
+
continue;
|
|
215
|
+
}
|
|
216
|
+
return item;
|
|
217
|
+
}
|
|
218
|
+
});
|
|
219
|
+
}
|