@oscarpalmer/atoms 0.174.0 → 0.176.0

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.
@@ -72,6 +72,15 @@ type Sorter<Item> = {
72
72
  * @returns Sorted array
73
73
  */
74
74
  (array: Item[]): Item[];
75
+ /**
76
+ * Get the index for an item _(to be inserted into an array of items)_
77
+ *
78
+ * _(If the array is not sorted, it will be treated as sorted, and the result may be inaccurate)_
79
+ * @param array Array to get the index from
80
+ * @param item Item to get the index for
81
+ * @returns Index for item
82
+ */
83
+ index(array: Item[], item: Item): number;
75
84
  /**
76
85
  * Is the array sorted?
77
86
  * @param array Array to check
@@ -79,6 +88,38 @@ type Sorter<Item> = {
79
88
  */
80
89
  is(array: Item[]): boolean;
81
90
  };
91
+ /**
92
+ * Get the index for an item _(to be inserted into an array of items)_ based on sorters _(and an optional default direction)_
93
+ *
94
+ * _(If the array is not sorted, it will be treated as sorted, and the result may be inaccurate)_
95
+ * @param array Array to get the index from
96
+ * @param item Item to get the index for
97
+ * @param sorters Sorters to use to determine sorting
98
+ * @param descending Sorted in descending order? _(defaults to `false`; overridden by individual sorters)_
99
+ * @returns Index for item
100
+ */
101
+ declare function getIndex<Item>(array: Item[], item: Item, sorters: Array<ArraySorter<Item>>, descending?: boolean): number;
102
+ /**
103
+ * Get the index for an item _(to be inserted into an array of items)_ based on a sorter _(and an optional default direction)_
104
+ *
105
+ * _(If the array is not sorted, it will be treated as sorted, and the result may be inaccurate)_
106
+ * @param array Array to get the index from
107
+ * @param item Item to get the index for
108
+ * @param sorter Sorter to use to determine sorting
109
+ * @param descending Sorted in descending order? _(defaults to `false`; overridden by individual sorters)_
110
+ * @returns Index for item
111
+ */
112
+ declare function getIndex<Item>(array: Item[], item: Item, sorter: ArraySorter<Item>, descending?: boolean): number;
113
+ /**
114
+ * Get the index for an item _(to be inserted into an array of items)_ based on an optional default direction_
115
+ *
116
+ * _(If the array is not sorted, it will be treated as sorted, and the result may be inaccurate)_
117
+ * @param array Array to get the index from
118
+ * @param item Item to get the index for
119
+ * @param descending Sorted in descending order? _(defaults to `false`)_
120
+ * @returns Index for item
121
+ */
122
+ declare function getIndex<Item>(array: Item[], item: Item, descending?: boolean): number;
82
123
  /**
83
124
  * Initialize a sort handler with sorters _(and an optional default direction)_
84
125
  * @param sorters Sorters to use for sorting
@@ -102,7 +143,7 @@ declare function initializeSort<Item>(descending?: boolean): Sorter<Item>;
102
143
  /**
103
144
  * Is the array sorted according to the sorters _(and the optional default direction)_?
104
145
  * @param array Array to check
105
- * @param sorters Sorters to use
146
+ * @param sorters Sorters to determine sorting
106
147
  * @param descending Sorted in descending order? _(defaults to `false`; overridden by individual sorters)_
107
148
  * @returns `true` if sorted, otherwise `false`
108
149
  */
@@ -110,7 +151,7 @@ declare function isSorted<Item>(array: Item[], sorters: Array<ArraySorter<Item>>
110
151
  /**
111
152
  * Is the array sorted according to the sorter _(and the optional default direction)_?
112
153
  * @param array Array to check
113
- * @param sorter Sorter to use
154
+ * @param sorter Sorter to determine sorting
114
155
  * @param descending Sorted in descending order? _(defaults to `false`; overridden by individual sorters)_
115
156
  * @returns `true` if sorted, otherwise `false`
116
157
  */
@@ -118,7 +159,7 @@ declare function isSorted<Item>(array: Item[], sorter: ArraySorter<Item>, descen
118
159
  /**
119
160
  * Is the array sorted?
120
161
  * @param array Array to check
121
- * @param descending Sorted in descending order? _(defaults to `false)_
162
+ * @param descending Sorted in descending order? _(defaults to `false`)_
122
163
  * @returns `true` if sorted, otherwise `false`
123
164
  */
124
165
  declare function isSorted<Item>(array: Item[], descending?: boolean): boolean;
@@ -146,6 +187,7 @@ declare function sort<Item>(array: Item[], sorter: ArraySorter<Item>, descending
146
187
  */
147
188
  declare function sort<Item>(array: Item[], descending?: boolean): Item[];
148
189
  declare namespace sort {
190
+ var index: typeof getIndex;
149
191
  var initialize: typeof initializeSort;
150
192
  var is: typeof isSorted;
151
193
  }
@@ -18,6 +18,9 @@ function getComparisonValue(first, second, sorters, length) {
18
18
  }
19
19
  return 0;
20
20
  }
21
+ function getIndex(array, item, first, second) {
22
+ return getSortedIndex(array, item, getSorters(first, getModifier(first, second)));
23
+ }
21
24
  function getModifier(first, second) {
22
25
  return modifiers[first === true || second === true ? SORT_DIRECTION_DESCENDING : SORT_DIRECTION_ASCENDING];
23
26
  }
@@ -31,6 +34,22 @@ function getObjectSorter(obj, modifier) {
31
34
  if (sorter != null && typeof obj.direction === "string") sorter.modifier = modifiers[obj.direction] ?? modifier;
32
35
  return sorter;
33
36
  }
37
+ function getSortedIndex(array, item, sorters) {
38
+ if (!Array.isArray(array)) return -1;
39
+ const { length } = array;
40
+ if (length === 0) return 0;
41
+ const sortersLength = sorters.length;
42
+ if (getComparisonValue(item, array[0], sorters, sortersLength) < 0) return 0;
43
+ if (getComparisonValue(item, array[length - 1], sorters, sortersLength) >= 0) return length;
44
+ let low = 0;
45
+ let high = length - 1;
46
+ while (low <= high) {
47
+ const mid = Math.floor((low + high) / 2);
48
+ if (getComparisonValue(item, array[mid], sorters, sortersLength) < 0) high = mid - 1;
49
+ else low = mid + 1;
50
+ }
51
+ return low;
52
+ }
34
53
  function getSorter(value, modifier) {
35
54
  switch (true) {
36
55
  case typeof value === "function": return getComparisonSorter(value, modifier);
@@ -66,6 +85,7 @@ function getValueSorter(value, modifier) {
66
85
  function initializeSort(first, second) {
67
86
  const sorters = getSorters(first, getModifier(first, second));
68
87
  const sorter = (array) => sortArray(array, sorters);
88
+ sorter.index = (array, item) => getSortedIndex(array, item, sorters);
69
89
  sorter.is = (array) => isSortedArray(array, sorters);
70
90
  return sorter;
71
91
  }
@@ -104,6 +124,7 @@ function sortArray(array, sorters) {
104
124
  const { length } = sorters;
105
125
  return array.length > 1 ? array.sort((first, second) => getComparisonValue(first, second, sorters, length)) : array;
106
126
  }
127
+ sort.index = getIndex;
107
128
  sort.initialize = initializeSort;
108
129
  sort.is = isSorted;
109
130
  const ARRAY_PEEK_PERCENTAGE = 10;
package/dist/index.d.mts CHANGED
@@ -1173,6 +1173,15 @@ type Sorter<Item> = {
1173
1173
  * @returns Sorted array
1174
1174
  */
1175
1175
  (array: Item[]): Item[];
1176
+ /**
1177
+ * Get the index for an item _(to be inserted into an array of items)_
1178
+ *
1179
+ * _(If the array is not sorted, it will be treated as sorted, and the result may be inaccurate)_
1180
+ * @param array Array to get the index from
1181
+ * @param item Item to get the index for
1182
+ * @returns Index for item
1183
+ */
1184
+ index(array: Item[], item: Item): number;
1176
1185
  /**
1177
1186
  * Is the array sorted?
1178
1187
  * @param array Array to check
@@ -1180,6 +1189,38 @@ type Sorter<Item> = {
1180
1189
  */
1181
1190
  is(array: Item[]): boolean;
1182
1191
  };
1192
+ /**
1193
+ * Get the index for an item _(to be inserted into an array of items)_ based on sorters _(and an optional default direction)_
1194
+ *
1195
+ * _(If the array is not sorted, it will be treated as sorted, and the result may be inaccurate)_
1196
+ * @param array Array to get the index from
1197
+ * @param item Item to get the index for
1198
+ * @param sorters Sorters to use to determine sorting
1199
+ * @param descending Sorted in descending order? _(defaults to `false`; overridden by individual sorters)_
1200
+ * @returns Index for item
1201
+ */
1202
+ declare function getIndex<Item>(array: Item[], item: Item, sorters: Array<ArraySorter<Item>>, descending?: boolean): number;
1203
+ /**
1204
+ * Get the index for an item _(to be inserted into an array of items)_ based on a sorter _(and an optional default direction)_
1205
+ *
1206
+ * _(If the array is not sorted, it will be treated as sorted, and the result may be inaccurate)_
1207
+ * @param array Array to get the index from
1208
+ * @param item Item to get the index for
1209
+ * @param sorter Sorter to use to determine sorting
1210
+ * @param descending Sorted in descending order? _(defaults to `false`; overridden by individual sorters)_
1211
+ * @returns Index for item
1212
+ */
1213
+ declare function getIndex<Item>(array: Item[], item: Item, sorter: ArraySorter<Item>, descending?: boolean): number;
1214
+ /**
1215
+ * Get the index for an item _(to be inserted into an array of items)_ based on an optional default direction_
1216
+ *
1217
+ * _(If the array is not sorted, it will be treated as sorted, and the result may be inaccurate)_
1218
+ * @param array Array to get the index from
1219
+ * @param item Item to get the index for
1220
+ * @param descending Sorted in descending order? _(defaults to `false`)_
1221
+ * @returns Index for item
1222
+ */
1223
+ declare function getIndex<Item>(array: Item[], item: Item, descending?: boolean): number;
1183
1224
  /**
1184
1225
  * Initialize a sort handler with sorters _(and an optional default direction)_
1185
1226
  * @param sorters Sorters to use for sorting
@@ -1203,7 +1244,7 @@ declare function initializeSort<Item>(descending?: boolean): Sorter<Item>;
1203
1244
  /**
1204
1245
  * Is the array sorted according to the sorters _(and the optional default direction)_?
1205
1246
  * @param array Array to check
1206
- * @param sorters Sorters to use
1247
+ * @param sorters Sorters to determine sorting
1207
1248
  * @param descending Sorted in descending order? _(defaults to `false`; overridden by individual sorters)_
1208
1249
  * @returns `true` if sorted, otherwise `false`
1209
1250
  */
@@ -1211,7 +1252,7 @@ declare function isSorted<Item>(array: Item[], sorters: Array<ArraySorter<Item>>
1211
1252
  /**
1212
1253
  * Is the array sorted according to the sorter _(and the optional default direction)_?
1213
1254
  * @param array Array to check
1214
- * @param sorter Sorter to use
1255
+ * @param sorter Sorter to determine sorting
1215
1256
  * @param descending Sorted in descending order? _(defaults to `false`; overridden by individual sorters)_
1216
1257
  * @returns `true` if sorted, otherwise `false`
1217
1258
  */
@@ -1219,7 +1260,7 @@ declare function isSorted<Item>(array: Item[], sorter: ArraySorter<Item>, descen
1219
1260
  /**
1220
1261
  * Is the array sorted?
1221
1262
  * @param array Array to check
1222
- * @param descending Sorted in descending order? _(defaults to `false)_
1263
+ * @param descending Sorted in descending order? _(defaults to `false`)_
1223
1264
  * @returns `true` if sorted, otherwise `false`
1224
1265
  */
1225
1266
  declare function isSorted<Item>(array: Item[], descending?: boolean): boolean;
@@ -1247,6 +1288,7 @@ declare function sort<Item>(array: Item[], sorter: ArraySorter<Item>, descending
1247
1288
  */
1248
1289
  declare function sort<Item>(array: Item[], descending?: boolean): Item[];
1249
1290
  declare namespace sort {
1291
+ var index: typeof getIndex;
1250
1292
  var initialize: typeof initializeSort;
1251
1293
  var is: typeof isSorted;
1252
1294
  }
@@ -2510,6 +2552,30 @@ declare function registerCloner<Instance>(constructor: Constructor<Instance>, ha
2510
2552
  */
2511
2553
  declare function unregisterCloner<Instance>(constructor: Constructor<Instance>): void;
2512
2554
  //#endregion
2555
+ //#region src/value/collection.d.ts
2556
+ /**
2557
+ * Does the value exist for a key in a map?
2558
+ * @param map Map to check in
2559
+ * @param value Value to check for
2560
+ * @returns `true` if the value exists, otherwise `false`
2561
+ */
2562
+ declare function inMap<Value>(map: Map<unknown, Value>, value: Value): boolean;
2563
+ /**
2564
+ * Does the value exist for a key in a map?
2565
+ * @param map Map to check in
2566
+ * @param value Value to check for
2567
+ * @param key To return the key for the value
2568
+ * @return The key for the value if it exists, otherwise `undefined`
2569
+ */
2570
+ declare function inMap<Key, Value>(map: Map<Key, Value>, value: Value, key: true): Key;
2571
+ /**
2572
+ * Does the value exist in a set?
2573
+ * @param set Set to check in
2574
+ * @param value Value to check for
2575
+ * @returns `true` if the value exists, otherwise `false`
2576
+ */
2577
+ declare function inSet<Value>(set: Set<Value>, value: Value): boolean;
2578
+ //#endregion
2513
2579
  //#region src/value/diff.d.ts
2514
2580
  /**
2515
2581
  * Options for value comparison
@@ -4441,4 +4507,4 @@ declare class SizedSet<Value = unknown> extends Set<Value> {
4441
4507
  get(value: Value, update?: boolean): Value | undefined;
4442
4508
  }
4443
4509
  //#endregion
4444
- export { AnyResult, ArrayComparisonSorter, ArrayKeySorter, ArrayOrPlainObject, ArrayPosition, ArrayValueSorter, Asserter, AsyncCancelableCallback, AttemptFlow, AttemptFlowPromise, type Beacon, type BeaconOptions, BuiltIns, CancelableCallback, CancelablePromise, type Color, Constructor, DiffOptions, DiffResult, DiffValue, EqualOptions, Err, EventPosition, ExtendedErr, ExtendedResult, Flow, FlowPromise, FulfilledPromise, GenericAsyncCallback, GenericCallback, type HSLAColor, type HSLColor, HasValue, Key, KeyedValue, type Logger, type Memoized, type MemoizedOptions, MergeOptions, Merger, NestedArray, NestedKeys, NestedPartial, NestedValue, NestedValues, NumericalKeys, NumericalValues, type Observable, type Observer, Ok, OnceAsyncCallback, OnceCallback, PROMISE_ABORT_EVENT, PROMISE_ABORT_OPTIONS, PROMISE_ERROR_NAME, PROMISE_MESSAGE_EXPECTATION_ATTEMPT, PROMISE_MESSAGE_EXPECTATION_RESULT, PROMISE_MESSAGE_EXPECTATION_TIMED, PROMISE_MESSAGE_TIMEOUT, PROMISE_STRATEGY_ALL, PROMISE_STRATEGY_DEFAULT, PROMISE_TYPE_FULFILLED, PROMISE_TYPE_REJECTED, PlainObject, Primitive, PromiseData, PromiseHandlers, PromiseOptions, PromiseParameters, PromiseStrategy, PromiseTimeoutError, PromisesItems, PromisesOptions, PromisesResult, PromisesUnwrapped, PromisesValue, PromisesValues, type Queue, QueueError, type QueueOptions, type Queued, type QueuedResult, type RGBAColor, type RGBColor, RejectedPromise, RequiredKeys, Result, ResultMatch, RetryError, RetryOptions, SORT_DIRECTION_ASCENDING, SORT_DIRECTION_DESCENDING, Simplify, SizedMap, SizedSet, Smushed, SortDirection, Sorter, type Subscription, TemplateOptions, type Time, ToString, TypedArray, Unsmushed, UnwrapValue, assert, attempt, attemptFlow, attemptPipe, attemptPromise, average, beacon, between, camelCase, cancelable, capitalize, ceil, chunk, clamp, clone, compact, compare, count, debounce, delay, diff, difference, drop, endsWith, endsWithArray, equal, error, exists, filter, find, flatten, floor, flow, fromQuery, toPromise as fromResult, toPromise, getArray, getArrayPosition, getColor, getError, getForegroundColor, getHexColor, getHexaColor, getHslColor, getHslaColor, getNormalizedHex, getNumber, getRandomBoolean, getRandomCharacters, getRandomColor, getRandomFloat, getRandomHex, getRandomInteger, getRandomItem, getRandomItems, getRgbColor, getRgbaColor, getString, getTimedPromise, getUuid, getValue, groupBy, handleResult, hasValue, hexToHsl, hexToHsla, hexToRgb, hexToRgba, hslToHex, hslToRgb, hslToRgba, ignoreKey, includes, includesArray, indexOf, indexOfArray, insert, intersection, isArrayOrPlainObject, isColor, isConstructor, isEmpty, isError, isFulfilled, isHexColor, isHslColor, isHslLike, isHslaColor, isInstanceOf, isKey, isNonNullable, isNullable, isNullableOrEmpty, isNullableOrWhitespace, isNumber, isNumerical, isObject, isOk, isPlainObject, isPrimitive, isRejected, isResult, isRgbColor, isRgbLike, isRgbaColor, isTypedArray, join, kebabCase, logger, lowerCase, matchResult, max, median, memoize, merge, min, move, noop, ok, omit, once, parse, partition, pascalCase, pick, pipe, promises, push, queue, range, retry, rgbToHex, rgbToHsl, rgbToHsla, round, select, setValue, settlePromise, shuffle, slice, smush, snakeCase, sort, splice, startsWith, startsWithArray, sum, swap, take, template, throttle, timed, times, titleCase, toMap, toQuery, toRecord, toResult, toSet, toggle, trim, truncate, tryDecode, tryEncode, union, unique, unsmush, unwrap, update, upperCase, words };
4510
+ export { AnyResult, ArrayComparisonSorter, ArrayKeySorter, ArrayOrPlainObject, ArrayPosition, ArrayValueSorter, Asserter, AsyncCancelableCallback, AttemptFlow, AttemptFlowPromise, type Beacon, type BeaconOptions, BuiltIns, CancelableCallback, CancelablePromise, type Color, Constructor, DiffOptions, DiffResult, DiffValue, EqualOptions, Err, EventPosition, ExtendedErr, ExtendedResult, Flow, FlowPromise, FulfilledPromise, GenericAsyncCallback, GenericCallback, type HSLAColor, type HSLColor, HasValue, Key, KeyedValue, type Logger, type Memoized, type MemoizedOptions, MergeOptions, Merger, NestedArray, NestedKeys, NestedPartial, NestedValue, NestedValues, NumericalKeys, NumericalValues, type Observable, type Observer, Ok, OnceAsyncCallback, OnceCallback, PROMISE_ABORT_EVENT, PROMISE_ABORT_OPTIONS, PROMISE_ERROR_NAME, PROMISE_MESSAGE_EXPECTATION_ATTEMPT, PROMISE_MESSAGE_EXPECTATION_RESULT, PROMISE_MESSAGE_EXPECTATION_TIMED, PROMISE_MESSAGE_TIMEOUT, PROMISE_STRATEGY_ALL, PROMISE_STRATEGY_DEFAULT, PROMISE_TYPE_FULFILLED, PROMISE_TYPE_REJECTED, PlainObject, Primitive, PromiseData, PromiseHandlers, PromiseOptions, PromiseParameters, PromiseStrategy, PromiseTimeoutError, PromisesItems, PromisesOptions, PromisesResult, PromisesUnwrapped, PromisesValue, PromisesValues, type Queue, QueueError, type QueueOptions, type Queued, type QueuedResult, type RGBAColor, type RGBColor, RejectedPromise, RequiredKeys, Result, ResultMatch, RetryError, RetryOptions, SORT_DIRECTION_ASCENDING, SORT_DIRECTION_DESCENDING, Simplify, SizedMap, SizedSet, Smushed, SortDirection, Sorter, type Subscription, TemplateOptions, type Time, ToString, TypedArray, Unsmushed, UnwrapValue, assert, attempt, attemptFlow, attemptPipe, attemptPromise, average, beacon, between, camelCase, cancelable, capitalize, ceil, chunk, clamp, clone, compact, compare, count, debounce, delay, diff, difference, drop, endsWith, endsWithArray, equal, error, exists, filter, find, flatten, floor, flow, fromQuery, toPromise as fromResult, toPromise, getArray, getArrayPosition, getColor, getError, getForegroundColor, getHexColor, getHexaColor, getHslColor, getHslaColor, getNormalizedHex, getNumber, getRandomBoolean, getRandomCharacters, getRandomColor, getRandomFloat, getRandomHex, getRandomInteger, getRandomItem, getRandomItems, getRgbColor, getRgbaColor, getString, getTimedPromise, getUuid, getValue, groupBy, handleResult, hasValue, hexToHsl, hexToHsla, hexToRgb, hexToRgba, hslToHex, hslToRgb, hslToRgba, ignoreKey, inMap, inSet, includes, includesArray, indexOf, indexOfArray, insert, intersection, isArrayOrPlainObject, isColor, isConstructor, isEmpty, isError, isFulfilled, isHexColor, isHslColor, isHslLike, isHslaColor, isInstanceOf, isKey, isNonNullable, isNullable, isNullableOrEmpty, isNullableOrWhitespace, isNumber, isNumerical, isObject, isOk, isPlainObject, isPrimitive, isRejected, isResult, isRgbColor, isRgbLike, isRgbaColor, isTypedArray, join, kebabCase, logger, lowerCase, matchResult, max, median, memoize, merge, min, move, noop, ok, omit, once, parse, partition, pascalCase, pick, pipe, promises, push, queue, range, retry, rgbToHex, rgbToHsl, rgbToHsla, round, select, setValue, settlePromise, shuffle, slice, smush, snakeCase, sort, splice, startsWith, startsWithArray, sum, swap, take, template, throttle, timed, times, titleCase, toMap, toQuery, toRecord, toResult, toSet, toggle, trim, truncate, tryDecode, tryEncode, union, unique, unsmush, unwrap, update, upperCase, words };
package/dist/index.mjs CHANGED
@@ -928,6 +928,9 @@ function getComparisonValue(first, second, sorters, length) {
928
928
  }
929
929
  return 0;
930
930
  }
931
+ function getIndex(array, item, first, second) {
932
+ return getSortedIndex(array, item, getSorters(first, getModifier(first, second)));
933
+ }
931
934
  function getModifier(first, second) {
932
935
  return modifiers[first === true || second === true ? SORT_DIRECTION_DESCENDING : SORT_DIRECTION_ASCENDING];
933
936
  }
@@ -941,6 +944,22 @@ function getObjectSorter(obj, modifier) {
941
944
  if (sorter != null && typeof obj.direction === "string") sorter.modifier = modifiers[obj.direction] ?? modifier;
942
945
  return sorter;
943
946
  }
947
+ function getSortedIndex(array, item, sorters) {
948
+ if (!Array.isArray(array)) return -1;
949
+ const { length } = array;
950
+ if (length === 0) return 0;
951
+ const sortersLength = sorters.length;
952
+ if (getComparisonValue(item, array[0], sorters, sortersLength) < 0) return 0;
953
+ if (getComparisonValue(item, array[length - 1], sorters, sortersLength) >= 0) return length;
954
+ let low = 0;
955
+ let high = length - 1;
956
+ while (low <= high) {
957
+ const mid = Math.floor((low + high) / 2);
958
+ if (getComparisonValue(item, array[mid], sorters, sortersLength) < 0) high = mid - 1;
959
+ else low = mid + 1;
960
+ }
961
+ return low;
962
+ }
944
963
  function getSorter(value, modifier) {
945
964
  switch (true) {
946
965
  case typeof value === "function": return getComparisonSorter(value, modifier);
@@ -976,6 +995,7 @@ function getValueSorter(value, modifier) {
976
995
  function initializeSort(first, second) {
977
996
  const sorters = getSorters(first, getModifier(first, second));
978
997
  const sorter = (array) => sortArray(array, sorters);
998
+ sorter.index = (array, item) => getSortedIndex(array, item, sorters);
979
999
  sorter.is = (array) => isSortedArray(array, sorters);
980
1000
  return sorter;
981
1001
  }
@@ -1014,6 +1034,7 @@ function sortArray(array, sorters) {
1014
1034
  const { length } = sorters;
1015
1035
  return array.length > 1 ? array.sort((first, second) => getComparisonValue(first, second, sorters, length)) : array;
1016
1036
  }
1037
+ sort.index = getIndex;
1017
1038
  sort.initialize = initializeSort;
1018
1039
  sort.is = isSorted;
1019
1040
  const ARRAY_PEEK_PERCENTAGE$1 = 10;
@@ -2443,6 +2464,26 @@ function tryStructuredClone(value, depth, references) {
2443
2464
  }
2444
2465
  const MAX_CLONE_DEPTH = 100;
2445
2466
  //#endregion
2467
+ //#region src/value/collection.ts
2468
+ function inMap(map, value, key) {
2469
+ const getKey = key === true;
2470
+ if (!(map instanceof Map)) return getKey ? void 0 : false;
2471
+ if (!getKey) return inSet(new Set(map.values()), value);
2472
+ for (const [key, item] of map) if (equal(item, value)) return key;
2473
+ }
2474
+ /**
2475
+ * Does the value exist in a set?
2476
+ * @param set Set to check in
2477
+ * @param value Value to check for
2478
+ * @returns `true` if the value exists, otherwise `false`
2479
+ */
2480
+ function inSet(set, value) {
2481
+ if (!(set instanceof Set)) return false;
2482
+ if (set.has(value)) return true;
2483
+ for (const item of set) if (equal(item, value)) return true;
2484
+ return false;
2485
+ }
2486
+ //#endregion
2446
2487
  //#region src/value/diff.ts
2447
2488
  /**
2448
2489
  * Find the differences between two values
@@ -4567,4 +4608,4 @@ var SizedSet = class extends Set {
4567
4608
  }
4568
4609
  };
4569
4610
  //#endregion
4570
- export { CancelablePromise, PROMISE_ABORT_EVENT, PROMISE_ABORT_OPTIONS, PROMISE_ERROR_NAME, PROMISE_MESSAGE_EXPECTATION_ATTEMPT, PROMISE_MESSAGE_EXPECTATION_RESULT, PROMISE_MESSAGE_EXPECTATION_TIMED, PROMISE_MESSAGE_TIMEOUT, PROMISE_STRATEGY_ALL, PROMISE_STRATEGY_DEFAULT, PROMISE_TYPE_FULFILLED, PROMISE_TYPE_REJECTED, PromiseTimeoutError, QueueError, RetryError, SORT_DIRECTION_ASCENDING, SORT_DIRECTION_DESCENDING, SizedMap, SizedSet, assert, attempt, attemptFlow, attemptPipe, attemptPromise, average, beacon, between, camelCase, cancelable, capitalize, ceil, chunk, clamp, clone, compact, compare, count, debounce, delay, diff, difference, drop, endsWith, endsWithArray, equal, error, exists, filter, find, flatten, floor, flow, fromQuery, toPromise as fromResult, toPromise, getArray, getArrayPosition, getColor, getError, getForegroundColor, getHexColor, getHexaColor, getHslColor, getHslaColor, getNormalizedHex, getNumber, getRandomBoolean, getRandomCharacters, getRandomColor, getRandomFloat, getRandomHex, getRandomInteger, getRandomItem, getRandomItems, getRgbColor, getRgbaColor, getString, getTimedPromise, getUuid, getValue, groupBy, handleResult, hasValue, hexToHsl, hexToHsla, hexToRgb, hexToRgba, hslToHex, hslToRgb, hslToRgba, ignoreKey, includes, includesArray, indexOf, indexOfArray, insert, intersection, isArrayOrPlainObject, isColor, isConstructor, isEmpty, isError, isFulfilled, isHexColor, isHslColor, isHslLike, isHslaColor, isInstanceOf, isKey, isNonNullable, isNullable, isNullableOrEmpty, isNullableOrWhitespace, isNumber, isNumerical, isObject, isOk, isPlainObject, isPrimitive, isRejected, isResult, isRgbColor, isRgbLike, isRgbaColor, isTypedArray, join, kebabCase, logger, lowerCase, matchResult, max, median, memoize, merge, min, move, noop, ok, omit, once, parse, partition, pascalCase, pick, pipe, promises, push, queue, range, retry, rgbToHex, rgbToHsl, rgbToHsla, round, select, setValue, settlePromise, shuffle, slice, smush, snakeCase, sort, splice, startsWith, startsWithArray, sum, swap, take, template, throttle, timed, times, titleCase, toMap, toQuery, toRecord, toResult, toSet, toggle, trim, truncate, tryDecode, tryEncode, union, unique, unsmush, unwrap, update, upperCase, words };
4611
+ export { CancelablePromise, PROMISE_ABORT_EVENT, PROMISE_ABORT_OPTIONS, PROMISE_ERROR_NAME, PROMISE_MESSAGE_EXPECTATION_ATTEMPT, PROMISE_MESSAGE_EXPECTATION_RESULT, PROMISE_MESSAGE_EXPECTATION_TIMED, PROMISE_MESSAGE_TIMEOUT, PROMISE_STRATEGY_ALL, PROMISE_STRATEGY_DEFAULT, PROMISE_TYPE_FULFILLED, PROMISE_TYPE_REJECTED, PromiseTimeoutError, QueueError, RetryError, SORT_DIRECTION_ASCENDING, SORT_DIRECTION_DESCENDING, SizedMap, SizedSet, assert, attempt, attemptFlow, attemptPipe, attemptPromise, average, beacon, between, camelCase, cancelable, capitalize, ceil, chunk, clamp, clone, compact, compare, count, debounce, delay, diff, difference, drop, endsWith, endsWithArray, equal, error, exists, filter, find, flatten, floor, flow, fromQuery, toPromise as fromResult, toPromise, getArray, getArrayPosition, getColor, getError, getForegroundColor, getHexColor, getHexaColor, getHslColor, getHslaColor, getNormalizedHex, getNumber, getRandomBoolean, getRandomCharacters, getRandomColor, getRandomFloat, getRandomHex, getRandomInteger, getRandomItem, getRandomItems, getRgbColor, getRgbaColor, getString, getTimedPromise, getUuid, getValue, groupBy, handleResult, hasValue, hexToHsl, hexToHsla, hexToRgb, hexToRgba, hslToHex, hslToRgb, hslToRgba, ignoreKey, inMap, inSet, includes, includesArray, indexOf, indexOfArray, insert, intersection, isArrayOrPlainObject, isColor, isConstructor, isEmpty, isError, isFulfilled, isHexColor, isHslColor, isHslLike, isHslaColor, isInstanceOf, isKey, isNonNullable, isNullable, isNullableOrEmpty, isNullableOrWhitespace, isNumber, isNumerical, isObject, isOk, isPlainObject, isPrimitive, isRejected, isResult, isRgbColor, isRgbLike, isRgbaColor, isTypedArray, join, kebabCase, logger, lowerCase, matchResult, max, median, memoize, merge, min, move, noop, ok, omit, once, parse, partition, pascalCase, pick, pipe, promises, push, queue, range, retry, rgbToHex, rgbToHsl, rgbToHsla, round, select, setValue, settlePromise, shuffle, slice, smush, snakeCase, sort, splice, startsWith, startsWithArray, sum, swap, take, template, throttle, timed, times, titleCase, toMap, toQuery, toRecord, toResult, toSet, toggle, trim, truncate, tryDecode, tryEncode, union, unique, unsmush, unwrap, update, upperCase, words };
@@ -0,0 +1,25 @@
1
+ //#region src/value/collection.d.ts
2
+ /**
3
+ * Does the value exist for a key in a map?
4
+ * @param map Map to check in
5
+ * @param value Value to check for
6
+ * @returns `true` if the value exists, otherwise `false`
7
+ */
8
+ declare function inMap<Value>(map: Map<unknown, Value>, value: Value): boolean;
9
+ /**
10
+ * Does the value exist for a key in a map?
11
+ * @param map Map to check in
12
+ * @param value Value to check for
13
+ * @param key To return the key for the value
14
+ * @return The key for the value if it exists, otherwise `undefined`
15
+ */
16
+ declare function inMap<Key, Value>(map: Map<Key, Value>, value: Value, key: true): Key;
17
+ /**
18
+ * Does the value exist in a set?
19
+ * @param set Set to check in
20
+ * @param value Value to check for
21
+ * @returns `true` if the value exists, otherwise `false`
22
+ */
23
+ declare function inSet<Value>(set: Set<Value>, value: Value): boolean;
24
+ //#endregion
25
+ export { inMap, inSet };
@@ -0,0 +1,22 @@
1
+ import { equal } from "../internal/value/equal.mjs";
2
+ //#region src/value/collection.ts
3
+ function inMap(map, value, key) {
4
+ const getKey = key === true;
5
+ if (!(map instanceof Map)) return getKey ? void 0 : false;
6
+ if (!getKey) return inSet(new Set(map.values()), value);
7
+ for (const [key, item] of map) if (equal(item, value)) return key;
8
+ }
9
+ /**
10
+ * Does the value exist in a set?
11
+ * @param set Set to check in
12
+ * @param value Value to check for
13
+ * @returns `true` if the value exists, otherwise `false`
14
+ */
15
+ function inSet(set, value) {
16
+ if (!(set instanceof Set)) return false;
17
+ if (set.has(value)) return true;
18
+ for (const item of set) if (equal(item, value)) return true;
19
+ return false;
20
+ }
21
+ //#endregion
22
+ export { inMap, inSet };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@oscarpalmer/atoms",
3
- "version": "0.174.0",
3
+ "version": "0.176.0",
4
4
  "description": "Atomic utilities for making your JavaScript better.",
5
5
  "keywords": [
6
6
  "helper",
@@ -200,6 +200,10 @@
200
200
  "types": "./dist/value/clone.d.mts",
201
201
  "default": "./dist/value/clone.mjs"
202
202
  },
203
+ "./value/collection": {
204
+ "types": "./dist/value/collection.d.mts",
205
+ "default": "./dist/value/collection.mjs"
206
+ },
203
207
  "./value/compare": {
204
208
  "types": "./dist/internal/value/compare.d.mts",
205
209
  "default": "./dist/internal/value/compare.mjs"
package/src/array/sort.ts CHANGED
@@ -112,6 +112,16 @@ export type Sorter<Item> = {
112
112
  */
113
113
  (array: Item[]): Item[];
114
114
 
115
+ /**
116
+ * Get the index for an item _(to be inserted into an array of items)_
117
+ *
118
+ * _(If the array is not sorted, it will be treated as sorted, and the result may be inaccurate)_
119
+ * @param array Array to get the index from
120
+ * @param item Item to get the index for
121
+ * @returns Index for item
122
+ */
123
+ index(array: Item[], item: Item): number;
124
+
115
125
  /**
116
126
  * Is the array sorted?
117
127
  * @param array Array to check
@@ -162,6 +172,55 @@ function getComparisonValue(
162
172
  return 0;
163
173
  }
164
174
 
175
+ /**
176
+ * Get the index for an item _(to be inserted into an array of items)_ based on sorters _(and an optional default direction)_
177
+ *
178
+ * _(If the array is not sorted, it will be treated as sorted, and the result may be inaccurate)_
179
+ * @param array Array to get the index from
180
+ * @param item Item to get the index for
181
+ * @param sorters Sorters to use to determine sorting
182
+ * @param descending Sorted in descending order? _(defaults to `false`; overridden by individual sorters)_
183
+ * @returns Index for item
184
+ */
185
+ function getIndex<Item>(
186
+ array: Item[],
187
+ item: Item,
188
+ sorters: Array<ArraySorter<Item>>,
189
+ descending?: boolean,
190
+ ): number;
191
+
192
+ /**
193
+ * Get the index for an item _(to be inserted into an array of items)_ based on a sorter _(and an optional default direction)_
194
+ *
195
+ * _(If the array is not sorted, it will be treated as sorted, and the result may be inaccurate)_
196
+ * @param array Array to get the index from
197
+ * @param item Item to get the index for
198
+ * @param sorter Sorter to use to determine sorting
199
+ * @param descending Sorted in descending order? _(defaults to `false`; overridden by individual sorters)_
200
+ * @returns Index for item
201
+ */
202
+ function getIndex<Item>(
203
+ array: Item[],
204
+ item: Item,
205
+ sorter: ArraySorter<Item>,
206
+ descending?: boolean,
207
+ ): number;
208
+
209
+ /**
210
+ * Get the index for an item _(to be inserted into an array of items)_ based on an optional default direction_
211
+ *
212
+ * _(If the array is not sorted, it will be treated as sorted, and the result may be inaccurate)_
213
+ * @param array Array to get the index from
214
+ * @param item Item to get the index for
215
+ * @param descending Sorted in descending order? _(defaults to `false`)_
216
+ * @returns Index for item
217
+ */
218
+ function getIndex<Item>(array: Item[], item: Item, descending?: boolean): number;
219
+
220
+ function getIndex(array: unknown[], item: unknown, first?: unknown, second?: unknown): number {
221
+ return getSortedIndex(array, item, getSorters(first, getModifier(first, second)));
222
+ }
223
+
165
224
  function getModifier(first: unknown, second: unknown): number {
166
225
  const direction =
167
226
  first === true || second === true ? SORT_DIRECTION_DESCENDING : SORT_DIRECTION_ASCENDING;
@@ -193,6 +252,43 @@ function getObjectSorter(obj: PlainObject, modifier: number): InternalSorter | u
193
252
  return sorter;
194
253
  }
195
254
 
255
+ function getSortedIndex(array: unknown[], item: unknown, sorters: InternalSorter[]): number {
256
+ if (!Array.isArray(array)) {
257
+ return -1;
258
+ }
259
+
260
+ const {length} = array;
261
+
262
+ if (length === 0) {
263
+ return 0;
264
+ }
265
+
266
+ const sortersLength = sorters.length;
267
+
268
+ if (getComparisonValue(item, array[0], sorters, sortersLength) < 0) {
269
+ return 0;
270
+ }
271
+
272
+ if (getComparisonValue(item, array[length - 1], sorters, sortersLength) >= 0) {
273
+ return length;
274
+ }
275
+
276
+ let low = 0;
277
+ let high = length - 1;
278
+
279
+ while (low <= high) {
280
+ const mid = Math.floor((low + high) / 2);
281
+
282
+ if (getComparisonValue(item, array[mid], sorters, sortersLength) < 0) {
283
+ high = mid - 1;
284
+ } else {
285
+ low = mid + 1;
286
+ }
287
+ }
288
+
289
+ return low;
290
+ }
291
+
196
292
  function getSorter(value: unknown, modifier: number): InternalSorter | undefined {
197
293
  switch (true) {
198
294
  case typeof value === 'function':
@@ -281,6 +377,7 @@ function initializeSort(first?: unknown, second?: unknown): Sorter<unknown> {
281
377
 
282
378
  const sorter = (array: unknown[]) => sortArray(array, sorters);
283
379
 
380
+ sorter.index = (array: unknown[], item: unknown) => getSortedIndex(array, item, sorters);
284
381
  sorter.is = (array: unknown[]) => isSortedArray(array, sorters);
285
382
 
286
383
  return sorter as unknown as Sorter<unknown>;
@@ -289,7 +386,7 @@ function initializeSort(first?: unknown, second?: unknown): Sorter<unknown> {
289
386
  /**
290
387
  * Is the array sorted according to the sorters _(and the optional default direction)_?
291
388
  * @param array Array to check
292
- * @param sorters Sorters to use
389
+ * @param sorters Sorters to determine sorting
293
390
  * @param descending Sorted in descending order? _(defaults to `false`; overridden by individual sorters)_
294
391
  * @returns `true` if sorted, otherwise `false`
295
392
  */
@@ -302,7 +399,7 @@ function isSorted<Item>(
302
399
  /**
303
400
  * Is the array sorted according to the sorter _(and the optional default direction)_?
304
401
  * @param array Array to check
305
- * @param sorter Sorter to use
402
+ * @param sorter Sorter to determine sorting
306
403
  * @param descending Sorted in descending order? _(defaults to `false`; overridden by individual sorters)_
307
404
  * @returns `true` if sorted, otherwise `false`
308
405
  */
@@ -311,7 +408,7 @@ function isSorted<Item>(array: Item[], sorter: ArraySorter<Item>, descending?: b
311
408
  /**
312
409
  * Is the array sorted?
313
410
  * @param array Array to check
314
- * @param descending Sorted in descending order? _(defaults to `false)_
411
+ * @param descending Sorted in descending order? _(defaults to `false`)_
315
412
  * @returns `true` if sorted, otherwise `false`
316
413
  */
317
414
  function isSorted<Item>(array: Item[], descending?: boolean): boolean;
@@ -416,6 +513,8 @@ function sortArray(array: unknown[], sorters: InternalSorter[]): unknown[] {
416
513
  : array;
417
514
  }
418
515
 
516
+ sort.index = getIndex;
517
+
419
518
  sort.initialize = initializeSort;
420
519
 
421
520
  sort.is = isSorted;
package/src/index.ts CHANGED
@@ -29,6 +29,7 @@ export * from './string/match';
29
29
  export * from './string/template';
30
30
 
31
31
  export * from './value/clone';
32
+ export * from './value/collection';
32
33
  export * from './value/diff';
33
34
  export * from './value/index';
34
35
  export * from './value/merge';
@@ -0,0 +1,60 @@
1
+ import {equal} from '../internal/value/equal';
2
+
3
+ /**
4
+ * Does the value exist for a key in a map?
5
+ * @param map Map to check in
6
+ * @param value Value to check for
7
+ * @returns `true` if the value exists, otherwise `false`
8
+ */
9
+ export function inMap<Value>(map: Map<unknown, Value>, value: Value): boolean;
10
+
11
+ /**
12
+ * Does the value exist for a key in a map?
13
+ * @param map Map to check in
14
+ * @param value Value to check for
15
+ * @param key To return the key for the value
16
+ * @return The key for the value if it exists, otherwise `undefined`
17
+ */
18
+ export function inMap<Key, Value>(map: Map<Key, Value>, value: Value, key: true): Key;
19
+
20
+ export function inMap<Key, Value>(map: Map<Key, Value>, value: Value, key?: unknown): unknown {
21
+ const getKey = key === true;
22
+
23
+ if (!(map instanceof Map)) {
24
+ return getKey ? undefined : false;
25
+ }
26
+
27
+ if (!getKey) {
28
+ return inSet(new Set(map.values()), value);
29
+ }
30
+
31
+ for (const [key, item] of map) {
32
+ if (equal(item, value)) {
33
+ return key;
34
+ }
35
+ }
36
+ }
37
+
38
+ /**
39
+ * Does the value exist in a set?
40
+ * @param set Set to check in
41
+ * @param value Value to check for
42
+ * @returns `true` if the value exists, otherwise `false`
43
+ */
44
+ export function inSet<Value>(set: Set<Value>, value: Value): boolean {
45
+ if (!(set instanceof Set)) {
46
+ return false;
47
+ }
48
+
49
+ if (set.has(value)) {
50
+ return true;
51
+ }
52
+
53
+ for (const item of set) {
54
+ if (equal(item, value)) {
55
+ return true;
56
+ }
57
+ }
58
+
59
+ return false;
60
+ }