pythonlib 0.1.0 → 0.2.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.
Files changed (65) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +41 -138
  3. package/dist/{chunk-P3SGIF72.js → chunk-4KYJT3DR.js} +8 -6
  4. package/dist/chunk-4KYJT3DR.js.map +1 -0
  5. package/dist/{chunk-3CSEXTA7.js → chunk-4QG3772L.js} +53 -53
  6. package/dist/chunk-4QG3772L.js.map +1 -0
  7. package/dist/{chunk-IVYYI2VR.js → chunk-6POEDI34.js} +1 -1
  8. package/dist/chunk-6POEDI34.js.map +1 -0
  9. package/dist/{chunk-UFMTN4T4.js → chunk-6ZAJ37MR.js} +6 -5
  10. package/dist/chunk-6ZAJ37MR.js.map +1 -0
  11. package/dist/{chunk-V63LKSA3.js → chunk-7TH4FCVQ.js} +24 -24
  12. package/dist/chunk-7TH4FCVQ.js.map +1 -0
  13. package/dist/{chunk-TJFGYXBJ.js → chunk-CXKGPD5D.js} +64 -61
  14. package/dist/chunk-CXKGPD5D.js.map +1 -0
  15. package/dist/{chunk-OMQNGE6T.js → chunk-EE7SK2GV.js} +33 -27
  16. package/dist/chunk-EE7SK2GV.js.map +1 -0
  17. package/dist/{chunk-WAONBJE5.js → chunk-H76SKASU.js} +36 -36
  18. package/dist/chunk-H76SKASU.js.map +1 -0
  19. package/dist/{chunk-TOI6IG3T.js → chunk-HQ42WNKZ.js} +43 -16
  20. package/dist/chunk-HQ42WNKZ.js.map +1 -0
  21. package/dist/{chunk-HA5Y7PKO.js → chunk-LWO6BIAD.js} +36 -35
  22. package/dist/chunk-LWO6BIAD.js.map +1 -0
  23. package/dist/{collections-xN9Gi0TA.d.ts → collections-CJur5Wg-.d.ts} +5 -3
  24. package/dist/collections.d.ts +1 -1
  25. package/dist/collections.js +1 -1
  26. package/dist/{datetime-DRwFAiGV.d.ts → datetime-Bpce8gG2.d.ts} +17 -15
  27. package/dist/datetime.d.ts +1 -1
  28. package/dist/datetime.js +1 -1
  29. package/dist/{functools-St5GqpKG.d.ts → functools-NrsZAqJk.d.ts} +42 -26
  30. package/dist/functools.d.ts +1 -1
  31. package/dist/functools.js +19 -17
  32. package/dist/index.d.ts +56 -158
  33. package/dist/index.js +47 -137
  34. package/dist/index.js.map +1 -1
  35. package/dist/{itertools-Bj8XivI6.d.ts → itertools-Sjl1LB_0.d.ts} +35 -17
  36. package/dist/itertools.d.ts +1 -1
  37. package/dist/itertools.js +15 -11
  38. package/dist/{json-Xpk0kwSd.d.ts → json-DAlvCadU.d.ts} +7 -5
  39. package/dist/json.d.ts +1 -1
  40. package/dist/json.js +1 -1
  41. package/dist/{math-BrT4Aw3E.d.ts → math-DwEGjjQ-.d.ts} +2 -0
  42. package/dist/math.d.ts +1 -1
  43. package/dist/math.js +1 -1
  44. package/dist/{os-FRSJbEUH.d.ts → os-C6Nt7Ijx.d.ts} +45 -42
  45. package/dist/os.d.ts +1 -1
  46. package/dist/os.js +23 -23
  47. package/dist/{random-D5S5iSV3.d.ts → random-BJv_rSpL.d.ts} +24 -22
  48. package/dist/random.d.ts +1 -1
  49. package/dist/random.js +21 -21
  50. package/dist/{re-DSxiURqN.d.ts → re-B1CHCgyr.d.ts} +17 -15
  51. package/dist/re.d.ts +1 -1
  52. package/dist/re.js +7 -7
  53. package/dist/string.d.ts +51 -48
  54. package/dist/string.js +13 -13
  55. package/package.json +30 -11
  56. package/dist/chunk-3CSEXTA7.js.map +0 -1
  57. package/dist/chunk-HA5Y7PKO.js.map +0 -1
  58. package/dist/chunk-IVYYI2VR.js.map +0 -1
  59. package/dist/chunk-OMQNGE6T.js.map +0 -1
  60. package/dist/chunk-P3SGIF72.js.map +0 -1
  61. package/dist/chunk-TJFGYXBJ.js.map +0 -1
  62. package/dist/chunk-TOI6IG3T.js.map +0 -1
  63. package/dist/chunk-UFMTN4T4.js.map +0 -1
  64. package/dist/chunk-V63LKSA3.js.map +0 -1
  65. package/dist/chunk-WAONBJE5.js.map +0 -1
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 Sebastian Software GmbH
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md CHANGED
@@ -1,24 +1,28 @@
1
1
  # pythonlib
2
2
 
3
3
  [![npm version](https://img.shields.io/npm/v/pythonlib.svg)](https://www.npmjs.com/package/pythonlib)
4
+ [![npm downloads](https://img.shields.io/npm/dm/pythonlib.svg)](https://www.npmjs.com/package/pythonlib)
5
+ [![Bundle Size](https://img.shields.io/bundlephobia/minzip/pythonlib)](https://bundlephobia.com/package/pythonlib)
6
+ [![TypeScript](https://img.shields.io/badge/TypeScript-5.6-blue.svg)](https://www.typescriptlang.org/)
4
7
  [![License](https://img.shields.io/npm/l/pythonlib.svg)](https://github.com/sebastian-software/python2ts/blob/main/LICENSE)
5
8
 
6
- **Python standard library for TypeScript** — itertools, functools, collections, and more.
9
+ **Python's powerful standard library, TypeScript's familiar style** — itertools, functools,
10
+ collections, and more.
7
11
 
8
- Zero dependencies. Full TypeScript support. Tree-shakeable.
12
+ > Zero dependencies · Full TypeScript support · Tree-shakeable · camelCase API · Works everywhere JS
13
+ > runs
9
14
 
10
- ## Installation
15
+ ## Quick Start
11
16
 
12
17
  ```bash
13
18
  npm install pythonlib
14
19
  ```
15
20
 
16
- ## Quick Start
17
-
18
21
  ```typescript
19
- import { range, enumerate, sorted, len } from "pythonlib"
22
+ import { range, enumerate, sorted } from "pythonlib"
20
23
  import { combinations } from "pythonlib/itertools"
21
24
  import { Counter } from "pythonlib/collections"
25
+ import { lruCache } from "pythonlib/functools"
22
26
 
23
27
  // Python-style iteration
24
28
  for (const i of range(10)) {
@@ -32,152 +36,51 @@ for (const combo of combinations([1, 2, 3], 2)) {
32
36
 
33
37
  // Count occurrences
34
38
  const counter = new Counter("mississippi")
35
- console.log(counter.mostCommon(2)) // [["i", 4], ["s", 4]]
36
- ```
37
-
38
- ## Import Structure
39
-
40
- pythonlib uses subpath exports for tree-shakeable imports:
41
-
42
- | Import Path | Contents |
43
- | ----------------------- | -------------------------------------------------- |
44
- | `pythonlib` | Builtins: `len`, `range`, `sorted`, `enumerate` |
45
- | `pythonlib/itertools` | `chain`, `combinations`, `permutations`, `product` |
46
- | `pythonlib/functools` | `partial`, `reduce`, `lru_cache`, `cache` |
47
- | `pythonlib/collections` | `Counter`, `defaultdict`, `deque` |
48
- | `pythonlib/math` | `sqrt`, `floor`, `ceil`, `factorial`, `pi`, `e` |
49
- | `pythonlib/random` | `randint`, `choice`, `shuffle`, `sample` |
50
- | `pythonlib/datetime` | `datetime`, `date`, `time`, `timedelta` |
51
- | `pythonlib/json` | `loads`, `dumps`, `load`, `dump` |
52
- | `pythonlib/re` | `search`, `match`, `findall`, `sub`, `compile` |
53
- | `pythonlib/os` | `path`, `getcwd`, `sep` |
54
- | `pythonlib/string` | `Template`, `capwords`, `ascii_lowercase` |
55
-
56
- ## Modules
57
-
58
- ### Builtins
59
-
60
- ```typescript
61
- import { range, enumerate, zip, len, sorted, reversed, sum, min, max } from "pythonlib"
62
-
63
- for (const i of range(5)) {
64
- } // 0, 1, 2, 3, 4
65
- for (const i of range(1, 5)) {
66
- } // 1, 2, 3, 4
67
- for (const i of range(0, 10, 2)) {
68
- } // 0, 2, 4, 6, 8
69
-
70
- for (const [i, v] of enumerate(["a", "b", "c"])) {
71
- } // [0,"a"], [1,"b"], [2,"c"]
72
- for (const [a, b] of zip([1, 2], ["x", "y"])) {
73
- } // [1,"x"], [2,"y"]
74
-
75
- len([1, 2, 3]) // 3
76
- sorted([3, 1, 2]) // [1, 2, 3]
77
- reversed([1, 2, 3]) // [3, 2, 1]
78
- sum([1, 2, 3]) // 6
79
- min([1, 2, 3]) // 1
80
- max([1, 2, 3]) // 3
81
- ```
82
-
83
- ### itertools
84
-
85
- ```typescript
86
- import { chain, combinations, permutations, product, groupby } from "pythonlib/itertools"
39
+ counter.mostCommon(2) // [["i", 4], ["s", 4]]
87
40
 
88
- chain([1, 2], [3, 4]) // [1, 2, 3, 4]
89
- combinations([1, 2, 3], 2) // [[1,2], [1,3], [2,3]]
90
- permutations([1, 2, 3], 2) // [[1,2], [1,3], [2,1], [2,3], [3,1], [3,2]]
91
- product([1, 2], ["a", "b"]) // [[1,"a"], [1,"b"], [2,"a"], [2,"b"]]
41
+ // Memoization
42
+ const fib = lruCache((n: number): number => (n <= 1 ? n : fib(n - 1) + fib(n - 2)))
92
43
  ```
93
44
 
94
- ### functools
45
+ ## Available Modules
95
46
 
96
- ```typescript
97
- import { partial, reduce, lru_cache } from "pythonlib/functools"
47
+ | Import Path | Contents | API Docs |
48
+ | ----------------------- | -------------------------------------------------- | ------------------------------------------------------------------------ |
49
+ | `pythonlib` | Builtins: `len`, `range`, `sorted`, `enumerate`... | [→](https://sebastian-software.github.io/python2ts/docs/api/index) |
50
+ | `pythonlib/itertools` | `chain`, `combinations`, `zipLongest`, `takeWhile` | [→](https://sebastian-software.github.io/python2ts/docs/api/itertools) |
51
+ | `pythonlib/functools` | `partial`, `reduce`, `lruCache`, `pipe` | [→](https://sebastian-software.github.io/python2ts/docs/api/functools) |
52
+ | `pythonlib/collections` | `Counter`, `defaultdict`, `deque` | [→](https://sebastian-software.github.io/python2ts/docs/api/collections) |
53
+ | `pythonlib/math` | `sqrt`, `floor`, `ceil`, `factorial`, `pi`, `e` | [→](https://sebastian-software.github.io/python2ts/docs/api/math) |
54
+ | `pythonlib/random` | `randInt`, `choice`, `shuffle`, `sample` | [→](https://sebastian-software.github.io/python2ts/docs/api/random) |
55
+ | `pythonlib/datetime` | `datetime`, `date`, `time`, `timedelta` | [→](https://sebastian-software.github.io/python2ts/docs/api/datetime) |
56
+ | `pythonlib/json` | `loads`, `dumps` | [→](https://sebastian-software.github.io/python2ts/docs/api/json) |
57
+ | `pythonlib/re` | `search`, `match`, `findAll`, `sub`, `compile` | [→](https://sebastian-software.github.io/python2ts/docs/api/re) |
58
+ | `pythonlib/string` | `Template`, `capWords`, `asciiLowercase` | [→](https://sebastian-software.github.io/python2ts/docs/api/string) |
98
59
 
99
- const add5 = partial((a, b) => a + b, 5)
100
- add5(3) // 8
60
+ > All function names use **camelCase** to feel native in TypeScript.
101
61
 
102
- reduce((a, b) => a + b, [1, 2, 3, 4, 5]) // 15
62
+ ## Documentation
103
63
 
104
- const cached = lru_cache((n: number) => expensiveComputation(n))
105
- cached(5) // computes
106
- cached(5) // returns cached result
107
- ```
64
+ **[📚 View Full Documentation](https://sebastian-software.github.io/python2ts/)**
108
65
 
109
- ### collections
66
+ | Resource | Description |
67
+ | ------------------------------------------------------------------------------ | ------------------------------------------- |
68
+ | [Homepage](https://sebastian-software.github.io/python2ts/) | Project overview, features, and quick start |
69
+ | [Runtime Guide](https://sebastian-software.github.io/python2ts/docs/runtime) | How to use pythonlib in your projects |
70
+ | [API Reference](https://sebastian-software.github.io/python2ts/docs/api) | Complete API documentation for all modules |
71
+ | [Syntax Reference](https://sebastian-software.github.io/python2ts/docs/syntax) | Python → TypeScript transformation rules |
110
72
 
111
- ```typescript
112
- import { Counter, defaultdict, deque } from "pythonlib/collections"
113
-
114
- const counter = new Counter("abracadabra")
115
- counter.get("a") // 5
116
- counter.mostCommon(2) // [["a", 5], ["b", 2]]
117
-
118
- const dd = defaultdict(() => [])
119
- dd.get("key").push(1) // auto-creates array
120
-
121
- const d = new deque([1, 2, 3])
122
- d.appendleft(0) // [0, 1, 2, 3]
123
- d.pop() // 3
124
- ```
73
+ ## Runtime Support
125
74
 
126
- ### datetime
75
+ Tested on every commit: **Node.js** (v22, v24) · **Bun** · **Deno** · **Browsers**
127
76
 
128
- ```typescript
129
- import { datetime, date, timedelta } from "pythonlib/datetime"
130
-
131
- const now = datetime.now()
132
- now.strftime("%Y-%m-%d %H:%M:%S")
133
-
134
- const d = new date(2024, 6, 15)
135
- d.isoformat() // "2024-06-15"
136
-
137
- const delta = new timedelta({ days: 7 })
138
- delta.total_seconds() // 604800
139
- ```
140
-
141
- ### re
142
-
143
- ```typescript
144
- import { search, findall, sub, compile } from "pythonlib/re"
145
-
146
- const m = search("(?P<name>\\w+)@(?P<domain>\\w+)", "user@example")
147
- m?.group("name") // "user"
148
- m?.groupdict() // { name: "user", domain: "example" }
149
-
150
- findall("\\d+", "a1b2c3") // ["1", "2", "3"]
151
- sub("\\d", "X", "a1b2") // "aXbX"
152
- ```
153
-
154
- ### math
155
-
156
- ```typescript
157
- import { sqrt, factorial, gcd, lcm, pi, e } from "pythonlib/math"
158
-
159
- sqrt(16) // 4
160
- factorial(5) // 120
161
- gcd(12, 8) // 4
162
- lcm(4, 6) // 12
163
- ```
164
-
165
- ### random
166
-
167
- ```typescript
168
- import { randint, choice, shuffle, sample } from "pythonlib/random"
169
-
170
- randint(1, 10) // random integer 1-10
171
- choice(["a", "b", "c"]) // random element
172
- shuffle([1, 2, 3]) // shuffles in place
173
- sample([1, 2, 3, 4, 5], 3) // 3 unique random elements
174
- ```
77
+ Also works in Cloudflare Workers, AWS Lambda, and other JS environments.
175
78
 
176
79
  ## Related
177
80
 
178
- - [python2ts](https://www.npmjs.com/package/python2ts) — Transpile Python to TypeScript (uses
179
- pythonlib as runtime)
81
+ - [**python2ts**](https://www.npmjs.com/package/python2ts) — Transpile Python to TypeScript
82
+ - [**GitHub**](https://github.com/sebastian-software/python2ts) — Source code and issue tracker
180
83
 
181
84
  ## License
182
85
 
183
- MIT
86
+ MIT © [Sebastian Software GmbH](https://sebastian-software.de)
@@ -12,9 +12,9 @@ __export(json_exports, {
12
12
  });
13
13
  function dumps(obj, options) {
14
14
  const indent = options?.indent;
15
- const sortKeys = options?.sort_keys ?? false;
15
+ const sortKeys = options?.sortKeys ?? false;
16
16
  const defaultFn = options?.default;
17
- const ensureAscii = options?.ensure_ascii ?? true;
17
+ const ensureAscii = options?.ensureAscii ?? true;
18
18
  const replacer = sortKeys ? (_key, value) => {
19
19
  if (value && typeof value === "object" && !Array.isArray(value)) {
20
20
  const sorted = {};
@@ -62,9 +62,9 @@ function dumps(obj, options) {
62
62
  return result;
63
63
  }
64
64
  function loads(s, options) {
65
- const objectHook = options?.object_hook;
66
- const parseFloat = options?.parse_float;
67
- const parseInt = options?.parse_int;
65
+ const objectHook = options?.objectHook;
66
+ const parseFloat = options?.parseFloatFn;
67
+ const parseInt = options?.parseIntFn;
68
68
  let reviver;
69
69
  if (objectHook || parseFloat || parseInt) {
70
70
  reviver = (key, value) => {
@@ -104,4 +104,6 @@ export {
104
104
  load,
105
105
  json_exports
106
106
  };
107
- //# sourceMappingURL=chunk-P3SGIF72.js.map
107
+ /* v8 ignore start -- error handling for invalid JSON @preserve */
108
+ /* v8 ignore start -- advanced custom parser hooks @preserve */
109
+ //# sourceMappingURL=chunk-4KYJT3DR.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/json.ts"],"sourcesContent":["/**\n * Python json module for TypeScript\n *\n * Provides JSON encoding and decoding functions matching Python's json module.\n * Maps directly to JavaScript's JSON object with Python-compatible options.\n *\n * @see {@link https://docs.python.org/3/library/json.html | Python json documentation}\n */\n\ntype JsonValue = string | number | boolean | null | JsonValue[] | { [key: string]: JsonValue }\ntype JsonReplacer = (key: string, value: unknown) => unknown\ntype JsonReviver = (key: string, value: unknown) => unknown\n\ninterface DumpsOptions {\n /** If specified, use this many spaces for indentation */\n indent?: number\n /** Separators for items and key-value pairs [item_sep, key_sep] */\n separators?: [string, string]\n /** Sort dictionary keys */\n sortKeys?: boolean\n /** If false, non-ASCII characters are escaped. Default true */\n ensureAscii?: boolean\n /** Custom serialization function */\n default?: (obj: unknown) => JsonValue\n}\n\ninterface LoadsOptions {\n /** Custom deserialization function */\n objectHook?: (obj: Record<string, unknown>) => unknown\n /** Parse floats with this function */\n parseFloatFn?: (s: string) => number\n /** Parse integers with this function */\n parseIntFn?: (s: string) => number\n}\n\n/**\n * Serialize obj to a JSON formatted string.\n *\n * @param obj - The object to serialize\n * @param options - Serialization options\n * @returns JSON string\n */\nexport function dumps(obj: unknown, options?: DumpsOptions): string {\n const indent = options?.indent\n const sortKeys = options?.sortKeys ?? false\n const defaultFn = options?.default\n const ensureAscii = options?.ensureAscii ?? true\n\n const replacer: JsonReplacer | undefined = sortKeys\n ? (_key, value) => {\n if (value && typeof value === \"object\" && !Array.isArray(value)) {\n const sorted: Record<string, unknown> = {}\n for (const k of Object.keys(value as Record<string, unknown>).sort()) {\n sorted[k] = (value as Record<string, unknown>)[k]\n }\n return sorted\n }\n return value\n }\n : undefined\n\n let result: string\n\n try {\n if (defaultFn) {\n // Custom serialization with default function\n result = JSON.stringify(\n obj,\n (key, value: unknown) => {\n const processed: unknown = replacer ? replacer(key, value) : value\n try {\n // Try default serialization first\n JSON.stringify(processed)\n return processed as JsonValue\n } catch {\n // If it fails, use the default function\n return defaultFn(processed)\n }\n },\n indent\n )\n } else {\n result = JSON.stringify(obj, replacer, indent)\n }\n /* v8 ignore start -- error handling for invalid JSON @preserve */\n } catch (e) {\n const error = e as Error\n throw new Error(`Object of type ${typeof obj} is not JSON serializable: ${error.message}`)\n }\n /* v8 ignore stop */\n\n // Handle separators if specified\n if (options?.separators) {\n const [itemSep, keySep] = options.separators\n // This is a simplified implementation - full separator support would require custom serialization\n if (itemSep !== \", \" || keySep !== \": \") {\n result = result.replace(/,\\s*/g, itemSep).replace(/:\\s*/g, keySep)\n }\n }\n\n // Handle ensureAscii\n if (ensureAscii) {\n result = result.replace(/[\\u007f-\\uffff]/g, (char) => {\n return \"\\\\u\" + (\"0000\" + char.charCodeAt(0).toString(16)).slice(-4)\n })\n }\n\n return result\n}\n\n/**\n * Deserialize a JSON string to a Python object.\n *\n * @param s - JSON string to parse\n * @param options - Deserialization options\n * @returns Parsed object\n */\nexport function loads(s: string, options?: LoadsOptions): unknown {\n const objectHook = options?.objectHook\n const parseFloat = options?.parseFloatFn\n const parseInt = options?.parseIntFn\n\n let reviver: JsonReviver | undefined\n\n /* v8 ignore start -- advanced custom parser hooks @preserve */\n if (objectHook || parseFloat || parseInt) {\n reviver = (key, value) => {\n if (typeof value === \"number\") {\n const str = String(value)\n if (str.includes(\".\") || str.includes(\"e\") || str.includes(\"E\")) {\n return parseFloat ? parseFloat(str) : value\n }\n return parseInt ? parseInt(str) : value\n }\n if (objectHook && value && typeof value === \"object\" && !Array.isArray(value) && key === \"\") {\n return objectHook(value as Record<string, unknown>)\n }\n return value\n }\n }\n /* v8 ignore stop */\n\n try {\n return JSON.parse(s, reviver)\n } catch (e) {\n const error = e as Error\n throw new Error(`JSON decode error: ${error.message}`)\n }\n}\n\n/**\n * Serialize obj to a JSON formatted string and write to file.\n * Note: This is a no-op in browser environments.\n *\n * @param obj - The object to serialize\n * @param fp - File-like object with write method\n * @param options - Serialization options\n */\nexport function dump(\n obj: unknown,\n fp: { write: (s: string) => void },\n options?: DumpsOptions\n): void {\n const s = dumps(obj, options)\n fp.write(s)\n}\n\n/**\n * Deserialize a JSON string from file to a Python object.\n * Note: This is a no-op in browser environments.\n *\n * @param fp - File-like object with read method\n * @param options - Deserialization options\n * @returns Parsed object\n */\nexport function load(fp: { read: () => string }, options?: LoadsOptions): unknown {\n const s = fp.read()\n return loads(s, options)\n}\n"],"mappings":";;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AA0CO,SAAS,MAAM,KAAc,SAAgC;AAClE,QAAM,SAAS,SAAS;AACxB,QAAM,WAAW,SAAS,YAAY;AACtC,QAAM,YAAY,SAAS;AAC3B,QAAM,cAAc,SAAS,eAAe;AAE5C,QAAM,WAAqC,WACvC,CAAC,MAAM,UAAU;AACf,QAAI,SAAS,OAAO,UAAU,YAAY,CAAC,MAAM,QAAQ,KAAK,GAAG;AAC/D,YAAM,SAAkC,CAAC;AACzC,iBAAW,KAAK,OAAO,KAAK,KAAgC,EAAE,KAAK,GAAG;AACpE,eAAO,CAAC,IAAK,MAAkC,CAAC;AAAA,MAClD;AACA,aAAO;AAAA,IACT;AACA,WAAO;AAAA,EACT,IACA;AAEJ,MAAI;AAEJ,MAAI;AACF,QAAI,WAAW;AAEb,eAAS,KAAK;AAAA,QACZ;AAAA,QACA,CAAC,KAAK,UAAmB;AACvB,gBAAM,YAAqB,WAAW,SAAS,KAAK,KAAK,IAAI;AAC7D,cAAI;AAEF,iBAAK,UAAU,SAAS;AACxB,mBAAO;AAAA,UACT,QAAQ;AAEN,mBAAO,UAAU,SAAS;AAAA,UAC5B;AAAA,QACF;AAAA,QACA;AAAA,MACF;AAAA,IACF,OAAO;AACL,eAAS,KAAK,UAAU,KAAK,UAAU,MAAM;AAAA,IAC/C;AAAA,EAEF,SAAS,GAAG;AACV,UAAM,QAAQ;AACd,UAAM,IAAI,MAAM,kBAAkB,OAAO,GAAG,8BAA8B,MAAM,OAAO,EAAE;AAAA,EAC3F;AAIA,MAAI,SAAS,YAAY;AACvB,UAAM,CAAC,SAAS,MAAM,IAAI,QAAQ;AAElC,QAAI,YAAY,QAAQ,WAAW,MAAM;AACvC,eAAS,OAAO,QAAQ,SAAS,OAAO,EAAE,QAAQ,SAAS,MAAM;AAAA,IACnE;AAAA,EACF;AAGA,MAAI,aAAa;AACf,aAAS,OAAO,QAAQ,oBAAoB,CAAC,SAAS;AACpD,aAAO,SAAS,SAAS,KAAK,WAAW,CAAC,EAAE,SAAS,EAAE,GAAG,MAAM,EAAE;AAAA,IACpE,CAAC;AAAA,EACH;AAEA,SAAO;AACT;AASO,SAAS,MAAM,GAAW,SAAiC;AAChE,QAAM,aAAa,SAAS;AAC5B,QAAM,aAAa,SAAS;AAC5B,QAAM,WAAW,SAAS;AAE1B,MAAI;AAGJ,MAAI,cAAc,cAAc,UAAU;AACxC,cAAU,CAAC,KAAK,UAAU;AACxB,UAAI,OAAO,UAAU,UAAU;AAC7B,cAAM,MAAM,OAAO,KAAK;AACxB,YAAI,IAAI,SAAS,GAAG,KAAK,IAAI,SAAS,GAAG,KAAK,IAAI,SAAS,GAAG,GAAG;AAC/D,iBAAO,aAAa,WAAW,GAAG,IAAI;AAAA,QACxC;AACA,eAAO,WAAW,SAAS,GAAG,IAAI;AAAA,MACpC;AACA,UAAI,cAAc,SAAS,OAAO,UAAU,YAAY,CAAC,MAAM,QAAQ,KAAK,KAAK,QAAQ,IAAI;AAC3F,eAAO,WAAW,KAAgC;AAAA,MACpD;AACA,aAAO;AAAA,IACT;AAAA,EACF;AAGA,MAAI;AACF,WAAO,KAAK,MAAM,GAAG,OAAO;AAAA,EAC9B,SAAS,GAAG;AACV,UAAM,QAAQ;AACd,UAAM,IAAI,MAAM,sBAAsB,MAAM,OAAO,EAAE;AAAA,EACvD;AACF;AAUO,SAAS,KACd,KACA,IACA,SACM;AACN,QAAM,IAAI,MAAM,KAAK,OAAO;AAC5B,KAAG,MAAM,CAAC;AACZ;AAUO,SAAS,KAAK,IAA4B,SAAiC;AAChF,QAAM,IAAI,GAAG,KAAK;AAClB,SAAO,MAAM,GAAG,OAAO;AACzB;","names":[]}
@@ -2,15 +2,15 @@
2
2
  function escapeRegex(str) {
3
3
  return str.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
4
4
  }
5
- var ascii_lowercase = "abcdefghijklmnopqrstuvwxyz";
6
- var ascii_uppercase = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";
7
- var ascii_letters = ascii_lowercase + ascii_uppercase;
5
+ var asciiLowercase = "abcdefghijklmnopqrstuvwxyz";
6
+ var asciiUppercase = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";
7
+ var asciiLetters = asciiLowercase + asciiUppercase;
8
8
  var digits = "0123456789";
9
- var hexdigits = "0123456789abcdefABCDEF";
10
- var octdigits = "01234567";
9
+ var hexDigits = "0123456789abcdefABCDEF";
10
+ var octDigits = "01234567";
11
11
  var punctuation = "!\"#$%&'()*+,-./:;<=>?@[\\]^_`{|}~";
12
12
  var whitespace = " \n\r\v\f";
13
- var printable = digits + ascii_letters + punctuation + whitespace;
13
+ var printable = digits + asciiLetters + punctuation + whitespace;
14
14
  var Template = class {
15
15
  template;
16
16
  constructor(template) {
@@ -32,7 +32,7 @@ var Template = class {
32
32
  );
33
33
  }
34
34
  /** Perform substitution, returning original placeholder for missing keys */
35
- safe_substitute(mapping) {
35
+ safeSubstitute(mapping) {
36
36
  const combined = { ...mapping };
37
37
  return this.template.replace(
38
38
  /\$\$|\$(\w+)|\$\{(\w+)\}/g,
@@ -47,7 +47,7 @@ var Template = class {
47
47
  );
48
48
  }
49
49
  /** Get identifiers in template */
50
- get_identifiers() {
50
+ getIdentifiers() {
51
51
  const identifiers = [];
52
52
  const regex = /\$(\w+)|\$\{(\w+)\}/g;
53
53
  let match;
@@ -60,7 +60,7 @@ var Template = class {
60
60
  return identifiers;
61
61
  }
62
62
  };
63
- function capwords(s, sep) {
63
+ function capWords(s, sep) {
64
64
  const separator = sep ?? " ";
65
65
  return s.split(separator).map((word) => {
66
66
  if (!word) return "";
@@ -102,9 +102,9 @@ var string = {
102
102
  return s.split(sep);
103
103
  },
104
104
  /**
105
- * Python str.rsplit()
105
+ * Python str.rSplit()
106
106
  */
107
- rsplit(s, sep, maxsplit) {
107
+ rSplit(s, sep, maxsplit) {
108
108
  if (sep === void 0) {
109
109
  const parts2 = s.trim().split(/\s+/);
110
110
  if (maxsplit === void 0) return parts2;
@@ -131,9 +131,9 @@ var string = {
131
131
  return s.replace(regex, "");
132
132
  },
133
133
  /**
134
- * Python str.lstrip()
134
+ * Python str.lStrip()
135
135
  */
136
- lstrip(s, chars) {
136
+ lStrip(s, chars) {
137
137
  if (chars === void 0) {
138
138
  return s.trimStart();
139
139
  }
@@ -141,9 +141,9 @@ var string = {
141
141
  return s.replace(regex, "");
142
142
  },
143
143
  /**
144
- * Python str.rstrip()
144
+ * Python str.rStrip()
145
145
  */
146
- rstrip(s, chars) {
146
+ rStrip(s, chars) {
147
147
  if (chars === void 0) {
148
148
  return s.trimEnd();
149
149
  }
@@ -176,22 +176,22 @@ var string = {
176
176
  return s.replace(/\b\w/g, (c) => c.toUpperCase());
177
177
  },
178
178
  /**
179
- * Python str.swapcase()
179
+ * Python str.swapCase()
180
180
  */
181
- swapcase(s) {
181
+ swapCase(s) {
182
182
  return s.split("").map((c) => c === c.toUpperCase() ? c.toLowerCase() : c.toUpperCase()).join("");
183
183
  },
184
184
  /**
185
- * Python str.startswith()
185
+ * Python str.startsWith()
186
186
  */
187
- startswith(s, prefix, start, end) {
187
+ startsWith(s, prefix, start, end) {
188
188
  const substr = s.slice(start, end);
189
189
  return substr.startsWith(prefix);
190
190
  },
191
191
  /**
192
- * Python str.endswith()
192
+ * Python str.endsWith()
193
193
  */
194
- endswith(s, suffix, start, end) {
194
+ endsWith(s, suffix, start, end) {
195
195
  const substr = s.slice(start, end);
196
196
  return substr.endsWith(suffix);
197
197
  },
@@ -205,9 +205,9 @@ var string = {
205
205
  return (start ?? 0) + index;
206
206
  },
207
207
  /**
208
- * Python str.rfind()
208
+ * Python str.rFind()
209
209
  */
210
- rfind(s, sub, start, end) {
210
+ rFind(s, sub, start, end) {
211
211
  const substr = s.slice(start, end);
212
212
  const index = substr.lastIndexOf(sub);
213
213
  if (index === -1) return -1;
@@ -224,10 +224,10 @@ var string = {
224
224
  return result;
225
225
  },
226
226
  /**
227
- * Python str.rindex() - raises error if not found
227
+ * Python str.rIndex() - raises error if not found
228
228
  */
229
- rindex(s, sub, start, end) {
230
- const result = string.rfind(s, sub, start, end);
229
+ rIndex(s, sub, start, end) {
230
+ const result = string.rFind(s, sub, start, end);
231
231
  if (result === -1) {
232
232
  throw new Error("substring not found");
233
233
  }
@@ -263,9 +263,9 @@ var string = {
263
263
  return result;
264
264
  },
265
265
  /**
266
- * Python str.zfill()
266
+ * Python str.zFill()
267
267
  */
268
- zfill(s, width) {
268
+ zFill(s, width) {
269
269
  if (s.length >= width) return s;
270
270
  const sign = s[0] === "-" || s[0] === "+" ? s[0] : "";
271
271
  const digits2 = sign ? s.slice(1) : s;
@@ -282,16 +282,16 @@ var string = {
282
282
  return fillchar.repeat(left) + s + fillchar.repeat(right);
283
283
  },
284
284
  /**
285
- * Python str.ljust()
285
+ * Python str.lJust()
286
286
  */
287
- ljust(s, width, fillchar = " ") {
287
+ lJust(s, width, fillchar = " ") {
288
288
  if (s.length >= width) return s;
289
289
  return s + fillchar.repeat(width - s.length);
290
290
  },
291
291
  /**
292
- * Python str.rjust()
292
+ * Python str.rJust()
293
293
  */
294
- rjust(s, width, fillchar = " ") {
294
+ rJust(s, width, fillchar = " ") {
295
295
  if (s.length >= width) return s;
296
296
  return fillchar.repeat(width - s.length) + s;
297
297
  },
@@ -304,47 +304,47 @@ var string = {
304
304
  return [s.slice(0, index), sep, s.slice(index + sep.length)];
305
305
  },
306
306
  /**
307
- * Python str.rpartition()
307
+ * Python str.rPartition()
308
308
  */
309
- rpartition(s, sep) {
309
+ rPartition(s, sep) {
310
310
  const index = s.lastIndexOf(sep);
311
311
  if (index === -1) return ["", "", s];
312
312
  return [s.slice(0, index), sep, s.slice(index + sep.length)];
313
313
  },
314
314
  /**
315
- * Python str.isalpha()
315
+ * Python str.isAlpha()
316
316
  */
317
- isalpha(s) {
317
+ isAlpha(s) {
318
318
  return s.length > 0 && /^[a-zA-Z]+$/.test(s);
319
319
  },
320
320
  /**
321
- * Python str.isdigit()
321
+ * Python str.isDigit()
322
322
  */
323
- isdigit(s) {
323
+ isDigit(s) {
324
324
  return s.length > 0 && /^[0-9]+$/.test(s);
325
325
  },
326
326
  /**
327
- * Python str.isalnum()
327
+ * Python str.isAlnum()
328
328
  */
329
- isalnum(s) {
329
+ isAlnum(s) {
330
330
  return s.length > 0 && /^[a-zA-Z0-9]+$/.test(s);
331
331
  },
332
332
  /**
333
- * Python str.isspace()
333
+ * Python str.isSpace()
334
334
  */
335
- isspace(s) {
335
+ isSpace(s) {
336
336
  return s.length > 0 && /^\s+$/.test(s);
337
337
  },
338
338
  /**
339
- * Python str.isupper()
339
+ * Python str.isUpper()
340
340
  */
341
- isupper(s) {
341
+ isUpper(s) {
342
342
  return s.length > 0 && s === s.toUpperCase() && s !== s.toLowerCase();
343
343
  },
344
344
  /**
345
- * Python str.islower()
345
+ * Python str.isLower()
346
346
  */
347
- islower(s) {
347
+ isLower(s) {
348
348
  return s.length > 0 && s === s.toLowerCase() && s !== s.toUpperCase();
349
349
  },
350
350
  /**
@@ -360,17 +360,17 @@ var string = {
360
360
  };
361
361
 
362
362
  export {
363
- ascii_lowercase,
364
- ascii_uppercase,
365
- ascii_letters,
363
+ asciiLowercase,
364
+ asciiUppercase,
365
+ asciiLetters,
366
366
  digits,
367
- hexdigits,
368
- octdigits,
367
+ hexDigits,
368
+ octDigits,
369
369
  punctuation,
370
370
  whitespace,
371
371
  printable,
372
372
  Template,
373
- capwords,
373
+ capWords,
374
374
  string
375
375
  };
376
- //# sourceMappingURL=chunk-3CSEXTA7.js.map
376
+ //# sourceMappingURL=chunk-4QG3772L.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/string.ts"],"sourcesContent":["/**\n * Python string module for TypeScript\n *\n * Provides string constants and utility classes matching Python's string module.\n *\n * @see {@link https://docs.python.org/3/library/string.html | Python string documentation}\n */\n\nfunction escapeRegex(str: string): string {\n return str.replace(/[.*+?^${}()|[\\]\\\\]/g, \"\\\\$&\")\n}\n\n// ============================================================================\n// String constants (Python string module)\n// ============================================================================\n\n/** The lowercase letters 'abcdefghijklmnopqrstuvwxyz' */\nexport const asciiLowercase = \"abcdefghijklmnopqrstuvwxyz\"\n\n/** The uppercase letters 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' */\nexport const asciiUppercase = \"ABCDEFGHIJKLMNOPQRSTUVWXYZ\"\n\n/** The concatenation of asciiLowercase and asciiUppercase */\nexport const asciiLetters = asciiLowercase + asciiUppercase\n\n/** The string '0123456789' */\nexport const digits = \"0123456789\"\n\n/** The string '0123456789abcdefABCDEF' */\nexport const hexDigits = \"0123456789abcdefABCDEF\"\n\n/** The string '01234567' */\nexport const octDigits = \"01234567\"\n\n/** String of ASCII characters which are considered punctuation */\nexport const punctuation = \"!\\\"#$%&'()*+,-./:;<=>?@[\\\\]^_`{|}~\"\n\n/** String of ASCII characters which are considered whitespace */\nexport const whitespace = \" \\t\\n\\r\\x0b\\x0c\"\n\n/** String of ASCII characters which are considered printable */\nexport const printable = digits + asciiLetters + punctuation + whitespace\n\n// ============================================================================\n// Template class\n// ============================================================================\n\nexport class Template {\n readonly template: string\n\n constructor(template: string) {\n this.template = template\n }\n\n /** Perform substitution, raising KeyError for missing keys */\n substitute(mapping?: Record<string, unknown>): string {\n const combined = { ...mapping }\n return this.template.replace(\n /\\$\\$|\\$(\\w+)|\\$\\{(\\w+)\\}/g,\n (match, name1: string, name2: string) => {\n if (match === \"$$\") return \"$\"\n const name = name1 || name2\n if (!(name in combined)) {\n throw new Error(`KeyError: '${name}'`)\n }\n return String(combined[name])\n }\n )\n }\n\n /** Perform substitution, returning original placeholder for missing keys */\n safeSubstitute(mapping?: Record<string, unknown>): string {\n const combined = { ...mapping }\n return this.template.replace(\n /\\$\\$|\\$(\\w+)|\\$\\{(\\w+)\\}/g,\n (match, name1: string, name2: string) => {\n if (match === \"$$\") return \"$\"\n const name = name1 || name2\n if (!(name in combined)) {\n return match\n }\n return String(combined[name])\n }\n )\n }\n\n /** Get identifiers in template */\n getIdentifiers(): string[] {\n const identifiers: string[] = []\n const regex = /\\$(\\w+)|\\$\\{(\\w+)\\}/g\n let match: RegExpExecArray | null\n while ((match = regex.exec(this.template)) !== null) {\n const name = match[1] || match[2]\n if (name && !identifiers.includes(name)) {\n identifiers.push(name)\n }\n }\n return identifiers\n }\n}\n\n/** Capitalize words in string */\nexport function capWords(s: string, sep?: string): string {\n const separator = sep ?? \" \"\n return s\n .split(separator)\n .map((word) => {\n if (!word) return \"\"\n const first = word[0]\n return first ? first.toUpperCase() + word.slice(1).toLowerCase() : word\n })\n .join(separator)\n}\n\nexport const string = {\n /**\n * Python str.join()\n */\n join(sep: string, iterable: Iterable<string>): string {\n return Array.from(iterable).join(sep)\n },\n\n /**\n * Python str.split()\n */\n split(s: string, sep?: string, maxsplit?: number): string[] {\n if (sep === undefined) {\n // Split on whitespace\n const result = s.trim().split(/\\s+/)\n if (maxsplit !== undefined && maxsplit >= 0) {\n if (result.length > maxsplit + 1) {\n const limited = result.slice(0, maxsplit)\n limited.push(result.slice(maxsplit).join(\" \"))\n return limited\n }\n }\n return result\n }\n\n if (maxsplit !== undefined && maxsplit >= 0) {\n const parts = s.split(sep)\n if (parts.length > maxsplit + 1) {\n const limited = parts.slice(0, maxsplit)\n limited.push(parts.slice(maxsplit).join(sep))\n return limited\n }\n return parts\n }\n\n return s.split(sep)\n },\n\n /**\n * Python str.rSplit()\n */\n rSplit(s: string, sep?: string, maxsplit?: number): string[] {\n if (sep === undefined) {\n const parts = s.trim().split(/\\s+/)\n if (maxsplit === undefined) return parts\n if (maxsplit <= 0) return [s]\n if (parts.length <= maxsplit + 1) return parts\n const keep = parts.slice(-maxsplit)\n const rest = parts.slice(0, parts.length - maxsplit).join(\" \")\n return [rest, ...keep]\n }\n\n const parts = s.split(sep)\n if (maxsplit === undefined || parts.length <= maxsplit + 1) return parts\n const keep = parts.slice(-maxsplit)\n const rest = parts.slice(0, parts.length - maxsplit).join(sep)\n return [rest, ...keep]\n },\n\n /**\n * Python str.strip()\n */\n strip(s: string, chars?: string): string {\n if (chars === undefined) {\n return s.trim()\n }\n const regex = new RegExp(`^[${escapeRegex(chars)}]+|[${escapeRegex(chars)}]+$`, \"g\")\n return s.replace(regex, \"\")\n },\n\n /**\n * Python str.lStrip()\n */\n lStrip(s: string, chars?: string): string {\n if (chars === undefined) {\n return s.trimStart()\n }\n const regex = new RegExp(`^[${escapeRegex(chars)}]+`)\n return s.replace(regex, \"\")\n },\n\n /**\n * Python str.rStrip()\n */\n rStrip(s: string, chars?: string): string {\n if (chars === undefined) {\n return s.trimEnd()\n }\n const regex = new RegExp(`[${escapeRegex(chars)}]+$`)\n return s.replace(regex, \"\")\n },\n\n /**\n * Python str.upper()\n */\n upper(s: string): string {\n return s.toUpperCase()\n },\n\n /**\n * Python str.lower()\n */\n lower(s: string): string {\n return s.toLowerCase()\n },\n\n /**\n * Python str.capitalize()\n */\n capitalize(s: string): string {\n if (s.length === 0) return s\n return s.charAt(0).toUpperCase() + s.slice(1).toLowerCase()\n },\n\n /**\n * Python str.title()\n */\n title(s: string): string {\n return s.replace(/\\b\\w/g, (c) => c.toUpperCase())\n },\n\n /**\n * Python str.swapCase()\n */\n swapCase(s: string): string {\n return s\n .split(\"\")\n .map((c) => (c === c.toUpperCase() ? c.toLowerCase() : c.toUpperCase()))\n .join(\"\")\n },\n\n /**\n * Python str.startsWith()\n */\n startsWith(s: string, prefix: string, start?: number, end?: number): boolean {\n const substr = s.slice(start, end)\n return substr.startsWith(prefix)\n },\n\n /**\n * Python str.endsWith()\n */\n endsWith(s: string, suffix: string, start?: number, end?: number): boolean {\n const substr = s.slice(start, end)\n return substr.endsWith(suffix)\n },\n\n /**\n * Python str.find()\n */\n find(s: string, sub: string, start?: number, end?: number): number {\n const substr = s.slice(start, end)\n const index = substr.indexOf(sub)\n if (index === -1) return -1\n return (start ?? 0) + index\n },\n\n /**\n * Python str.rFind()\n */\n rFind(s: string, sub: string, start?: number, end?: number): number {\n const substr = s.slice(start, end)\n const index = substr.lastIndexOf(sub)\n if (index === -1) return -1\n return (start ?? 0) + index\n },\n\n /**\n * Python str.index() - raises error if not found\n */\n index(s: string, sub: string, start?: number, end?: number): number {\n const result = string.find(s, sub, start, end)\n if (result === -1) {\n throw new Error(\"substring not found\")\n }\n return result\n },\n\n /**\n * Python str.rIndex() - raises error if not found\n */\n rIndex(s: string, sub: string, start?: number, end?: number): number {\n const result = string.rFind(s, sub, start, end)\n if (result === -1) {\n throw new Error(\"substring not found\")\n }\n return result\n },\n\n /**\n * Python str.count()\n */\n count(s: string, sub: string, start?: number, end?: number): number {\n const substr = s.slice(start, end)\n if (sub.length === 0) return substr.length + 1\n let count = 0\n let pos = 0\n while ((pos = substr.indexOf(sub, pos)) !== -1) {\n count++\n pos += sub.length\n }\n return count\n },\n\n /**\n * Python str.replace()\n */\n replace(s: string, old: string, newStr: string, count?: number): string {\n if (count === undefined || count < 0) {\n return s.split(old).join(newStr)\n }\n\n let result = s\n for (let i = 0; i < count; i++) {\n const index = result.indexOf(old)\n if (index === -1) break\n result = result.slice(0, index) + newStr + result.slice(index + old.length)\n }\n return result\n },\n\n /**\n * Python str.zFill()\n */\n zFill(s: string, width: number): string {\n if (s.length >= width) return s\n const sign = s[0] === \"-\" || s[0] === \"+\" ? s[0] : \"\"\n const digits = sign ? s.slice(1) : s\n return sign + digits.padStart(width - sign.length, \"0\")\n },\n\n /**\n * Python str.center()\n */\n center(s: string, width: number, fillchar = \" \"): string {\n if (s.length >= width) return s\n const total = width - s.length\n const left = Math.floor(total / 2)\n const right = total - left\n return fillchar.repeat(left) + s + fillchar.repeat(right)\n },\n\n /**\n * Python str.lJust()\n */\n lJust(s: string, width: number, fillchar = \" \"): string {\n if (s.length >= width) return s\n return s + fillchar.repeat(width - s.length)\n },\n\n /**\n * Python str.rJust()\n */\n rJust(s: string, width: number, fillchar = \" \"): string {\n if (s.length >= width) return s\n return fillchar.repeat(width - s.length) + s\n },\n\n /**\n * Python str.partition()\n */\n partition(s: string, sep: string): [string, string, string] {\n const index = s.indexOf(sep)\n if (index === -1) return [s, \"\", \"\"]\n return [s.slice(0, index), sep, s.slice(index + sep.length)]\n },\n\n /**\n * Python str.rPartition()\n */\n rPartition(s: string, sep: string): [string, string, string] {\n const index = s.lastIndexOf(sep)\n if (index === -1) return [\"\", \"\", s]\n return [s.slice(0, index), sep, s.slice(index + sep.length)]\n },\n\n /**\n * Python str.isAlpha()\n */\n isAlpha(s: string): boolean {\n return s.length > 0 && /^[a-zA-Z]+$/.test(s)\n },\n\n /**\n * Python str.isDigit()\n */\n isDigit(s: string): boolean {\n return s.length > 0 && /^[0-9]+$/.test(s)\n },\n\n /**\n * Python str.isAlnum()\n */\n isAlnum(s: string): boolean {\n return s.length > 0 && /^[a-zA-Z0-9]+$/.test(s)\n },\n\n /**\n * Python str.isSpace()\n */\n isSpace(s: string): boolean {\n return s.length > 0 && /^\\s+$/.test(s)\n },\n\n /**\n * Python str.isUpper()\n */\n isUpper(s: string): boolean {\n return s.length > 0 && s === s.toUpperCase() && s !== s.toLowerCase()\n },\n\n /**\n * Python str.isLower()\n */\n isLower(s: string): boolean {\n return s.length > 0 && s === s.toLowerCase() && s !== s.toUpperCase()\n },\n\n /**\n * Python str.format() - basic implementation\n */\n format(s: string, ...args: unknown[]): string {\n let index = 0\n return s.replace(/\\{(\\d*)\\}/g, (_, num: string) => {\n const i = num === \"\" ? index++ : parseInt(num, 10)\n return String(args[i])\n })\n }\n}\n"],"mappings":"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","names":["parts","keep","rest","digits"]}
@@ -258,4 +258,4 @@ export {
258
258
  prod,
259
259
  math_exports
260
260
  };
261
- //# sourceMappingURL=chunk-IVYYI2VR.js.map
261
+ //# sourceMappingURL=chunk-6POEDI34.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/math.ts"],"sourcesContent":["/**\n * Python math module for TypeScript\n *\n * Provides mathematical functions and constants matching Python's math module.\n * Most functions map directly to JavaScript's Math object.\n *\n * @see {@link https://docs.python.org/3/library/math.html | Python math documentation}\n */\n\n// ============================================================================\n// Constants\n// ============================================================================\n\n/** Mathematical constant π = 3.141592... */\nexport const pi = Math.PI\n\n/** Mathematical constant e = 2.718281... */\nexport const e = Math.E\n\n/** Mathematical constant τ = 2π = 6.283185... */\nexport const tau = 2 * Math.PI\n\n/** Positive infinity */\nexport const inf = Infinity\n\n/** Not a Number (NaN) */\nexport const nan = NaN\n\n// ============================================================================\n// Number-theoretic and representation functions\n// ============================================================================\n\n/** Return the ceiling of x, the smallest integer greater than or equal to x */\nexport function ceil(x: number): number {\n return Math.ceil(x)\n}\n\n/** Return the floor of x, the largest integer less than or equal to x */\nexport function floor(x: number): number {\n return Math.floor(x)\n}\n\n/** Return the truncated integer part of x (rounds toward zero) */\nexport function trunc(x: number): number {\n return Math.trunc(x)\n}\n\n/** Return the absolute value of x */\nexport function fabs(x: number): number {\n return Math.abs(x)\n}\n\n/** Return x with the sign of y */\nexport function copysign(x: number, y: number): number {\n const sign = y < 0 || (y === 0 && 1 / y < 0) ? -1 : 1\n return sign * Math.abs(x)\n}\n\n/** Return the fractional and integer parts of x */\nexport function modf(x: number): [number, number] {\n const intPart = Math.trunc(x)\n const fracPart = x - intPart\n return [fracPart, intPart]\n}\n\n/** Return the greatest common divisor of a and b */\nexport function gcd(a: number, b: number): number {\n a = Math.abs(Math.floor(a))\n b = Math.abs(Math.floor(b))\n while (b) {\n const t = b\n b = a % b\n a = t\n }\n return a\n}\n\n/** Return the least common multiple of a and b */\nexport function lcm(a: number, b: number): number {\n if (a === 0 || b === 0) return 0\n return Math.abs(Math.floor(a) * Math.floor(b)) / gcd(a, b)\n}\n\n/** Return True if x is neither infinity nor NaN */\nexport function isfinite(x: number): boolean {\n return Number.isFinite(x)\n}\n\n/** Return True if x is positive or negative infinity */\nexport function isinf(x: number): boolean {\n return !Number.isFinite(x) && !Number.isNaN(x)\n}\n\n/** Return True if x is NaN */\nexport function isnan(x: number): boolean {\n return Number.isNaN(x)\n}\n\n/** Return True if the values a and b are close to each other */\nexport function isclose(\n a: number,\n b: number,\n rel_tol: number = 1e-9,\n abs_tol: number = 0.0\n): boolean {\n return Math.abs(a - b) <= Math.max(rel_tol * Math.max(Math.abs(a), Math.abs(b)), abs_tol)\n}\n\n// ============================================================================\n// Power and logarithmic functions\n// ============================================================================\n\n/** Return e raised to the power x */\nexport function exp(x: number): number {\n return Math.exp(x)\n}\n\n/** Return e raised to the power x, minus 1 (more accurate for small x) */\nexport function expm1(x: number): number {\n return Math.expm1(x)\n}\n\n/** Return the natural logarithm of x */\nexport function log(x: number, base?: number): number {\n if (base === undefined) {\n return Math.log(x)\n }\n return Math.log(x) / Math.log(base)\n}\n\n/** Return the natural logarithm of 1+x (more accurate for small x) */\nexport function log1p(x: number): number {\n return Math.log1p(x)\n}\n\n/** Return the base-2 logarithm of x */\nexport function log2(x: number): number {\n return Math.log2(x)\n}\n\n/** Return the base-10 logarithm of x */\nexport function log10(x: number): number {\n return Math.log10(x)\n}\n\n/** Return x raised to the power y */\nexport function pow(x: number, y: number): number {\n return Math.pow(x, y)\n}\n\n/** Return the square root of x */\nexport function sqrt(x: number): number {\n return Math.sqrt(x)\n}\n\n/** Return the cube root of x */\nexport function cbrt(x: number): number {\n return Math.cbrt(x)\n}\n\n/** Return the Euclidean norm, sqrt(sum(x**2 for x in args)) */\nexport function hypot(...args: number[]): number {\n return Math.hypot(...args)\n}\n\n// ============================================================================\n// Trigonometric functions\n// ============================================================================\n\n/** Return the sine of x (x in radians) */\nexport function sin(x: number): number {\n return Math.sin(x)\n}\n\n/** Return the cosine of x (x in radians) */\nexport function cos(x: number): number {\n return Math.cos(x)\n}\n\n/** Return the tangent of x (x in radians) */\nexport function tan(x: number): number {\n return Math.tan(x)\n}\n\n/** Return the arc sine of x, in radians */\nexport function asin(x: number): number {\n return Math.asin(x)\n}\n\n/** Return the arc cosine of x, in radians */\nexport function acos(x: number): number {\n return Math.acos(x)\n}\n\n/** Return the arc tangent of x, in radians */\nexport function atan(x: number): number {\n return Math.atan(x)\n}\n\n/** Return atan(y / x), in radians. The result is between -π and π */\nexport function atan2(y: number, x: number): number {\n return Math.atan2(y, x)\n}\n\n// ============================================================================\n// Hyperbolic functions\n// ============================================================================\n\n/** Return the hyperbolic sine of x */\nexport function sinh(x: number): number {\n return Math.sinh(x)\n}\n\n/** Return the hyperbolic cosine of x */\nexport function cosh(x: number): number {\n return Math.cosh(x)\n}\n\n/** Return the hyperbolic tangent of x */\nexport function tanh(x: number): number {\n return Math.tanh(x)\n}\n\n/** Return the inverse hyperbolic sine of x */\nexport function asinh(x: number): number {\n return Math.asinh(x)\n}\n\n/** Return the inverse hyperbolic cosine of x */\nexport function acosh(x: number): number {\n return Math.acosh(x)\n}\n\n/** Return the inverse hyperbolic tangent of x */\nexport function atanh(x: number): number {\n return Math.atanh(x)\n}\n\n// ============================================================================\n// Angular conversion\n// ============================================================================\n\n/** Convert angle x from radians to degrees */\nexport function degrees(x: number): number {\n return (x * 180) / Math.PI\n}\n\n/** Convert angle x from degrees to radians */\nexport function radians(x: number): number {\n return (x * Math.PI) / 180\n}\n\n// ============================================================================\n// Special functions\n// ============================================================================\n\n/** Return the factorial of n as an integer */\nexport function factorial(n: number): number {\n n = Math.floor(n)\n if (n < 0) throw new Error(\"factorial() not defined for negative values\")\n if (n === 0 || n === 1) return 1\n let result = 1\n for (let i = 2; i <= n; i++) {\n result *= i\n }\n return result\n}\n\n/** Return the sum of products of values from iterables (dot product) */\nexport function fsum(iterable: Iterable<number>): number {\n // Use Kahan summation for better precision\n let sum = 0\n let c = 0\n for (const x of iterable) {\n const y = x - c\n const t = sum + y\n c = t - sum - y\n sum = t\n }\n return sum\n}\n\n/** Return the product of all elements in the iterable */\nexport function prod(iterable: Iterable<number>, start: number = 1): number {\n let result = start\n for (const x of iterable) {\n result *= x\n }\n return result\n}\n"],"mappings":"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","names":[]}