@kensio/pinyinjs 1.7.3 → 1.7.5

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 (695) hide show
  1. package/dist/accuracy/score-case.d.ts +23 -0
  2. package/dist/accuracy/score-case.d.ts.map +1 -0
  3. package/dist/accuracy/score-case.js +63 -0
  4. package/dist/accuracy/score-case.js.map +1 -0
  5. package/dist/accuracy/score.d.ts +1 -8
  6. package/dist/accuracy/score.d.ts.map +1 -1
  7. package/dist/accuracy/score.js +1 -55
  8. package/dist/accuracy/score.js.map +1 -1
  9. package/dist/cli/arguments.d.ts +4 -290
  10. package/dist/cli/arguments.d.ts.map +1 -1
  11. package/dist/cli/arguments.js +5 -357
  12. package/dist/cli/arguments.js.map +1 -1
  13. package/dist/cli/check-command.d.ts +9 -0
  14. package/dist/cli/check-command.d.ts.map +1 -0
  15. package/dist/cli/check-command.js +95 -0
  16. package/dist/cli/check-command.js.map +1 -0
  17. package/dist/cli/cli-input.d.ts +49 -0
  18. package/dist/cli/cli-input.d.ts.map +1 -0
  19. package/dist/cli/cli-input.js +31 -0
  20. package/dist/cli/cli-input.js.map +1 -0
  21. package/dist/cli/command.d.ts +97 -0
  22. package/dist/cli/command.d.ts.map +1 -0
  23. package/dist/cli/command.js +40 -0
  24. package/dist/cli/command.js.map +1 -0
  25. package/dist/cli/commands.d.ts +7 -110
  26. package/dist/cli/commands.d.ts.map +1 -1
  27. package/dist/cli/commands.js +14 -991
  28. package/dist/cli/commands.js.map +1 -1
  29. package/dist/cli/convert-command.d.ts +6 -0
  30. package/dist/cli/convert-command.d.ts.map +1 -0
  31. package/dist/cli/convert-command.js +52 -0
  32. package/dist/cli/convert-command.js.map +1 -0
  33. package/dist/cli/environment.d.ts +1 -1
  34. package/dist/cli/environment.d.ts.map +1 -1
  35. package/dist/cli/explain-command.d.ts +6 -0
  36. package/dist/cli/explain-command.d.ts.map +1 -0
  37. package/dist/cli/explain-command.js +40 -0
  38. package/dist/cli/explain-command.js.map +1 -0
  39. package/dist/cli/explain-syllable.d.ts +10 -0
  40. package/dist/cli/explain-syllable.d.ts.map +1 -0
  41. package/dist/cli/explain-syllable.js +70 -0
  42. package/dist/cli/explain-syllable.js.map +1 -0
  43. package/dist/cli/flag-help.d.ts +18 -0
  44. package/dist/cli/flag-help.d.ts.map +1 -0
  45. package/dist/cli/flag-help.js +78 -0
  46. package/dist/cli/flag-help.js.map +1 -0
  47. package/dist/cli/flag-lists.d.ts +49 -0
  48. package/dist/cli/flag-lists.d.ts.map +1 -0
  49. package/dist/cli/flag-lists.js +58 -0
  50. package/dist/cli/flag-lists.js.map +1 -0
  51. package/dist/cli/flag-values.d.ts +44 -0
  52. package/dist/cli/flag-values.d.ts.map +1 -0
  53. package/dist/cli/flag-values.js +56 -0
  54. package/dist/cli/flag-values.js.map +1 -0
  55. package/dist/cli/flags.d.ts +193 -0
  56. package/dist/cli/flags.d.ts.map +1 -0
  57. package/dist/cli/flags.js +133 -0
  58. package/dist/cli/flags.js.map +1 -0
  59. package/dist/cli/format-options.d.ts +29 -0
  60. package/dist/cli/format-options.d.ts.map +1 -0
  61. package/dist/cli/format-options.js +72 -0
  62. package/dist/cli/format-options.js.map +1 -0
  63. package/dist/cli/global-help.d.ts +23 -0
  64. package/dist/cli/global-help.d.ts.map +1 -0
  65. package/dist/cli/global-help.js +40 -0
  66. package/dist/cli/global-help.js.map +1 -0
  67. package/dist/cli/help.d.ts +1 -1
  68. package/dist/cli/help.d.ts.map +1 -1
  69. package/dist/cli/help.js +5 -99
  70. package/dist/cli/help.js.map +1 -1
  71. package/dist/cli/html-commands.d.ts +13 -0
  72. package/dist/cli/html-commands.d.ts.map +1 -0
  73. package/dist/cli/html-commands.js +49 -0
  74. package/dist/cli/html-commands.js.map +1 -0
  75. package/dist/cli/info-command.d.ts +7 -0
  76. package/dist/cli/info-command.d.ts.map +1 -0
  77. package/dist/cli/info-command.js +39 -0
  78. package/dist/cli/info-command.js.map +1 -0
  79. package/dist/cli/lookup-commands.d.ts +10 -0
  80. package/dist/cli/lookup-commands.d.ts.map +1 -0
  81. package/dist/cli/lookup-commands.js +101 -0
  82. package/dist/cli/lookup-commands.js.map +1 -0
  83. package/dist/cli/match-command.d.ts +11 -0
  84. package/dist/cli/match-command.d.ts.map +1 -0
  85. package/dist/cli/match-command.js +76 -0
  86. package/dist/cli/match-command.js.map +1 -0
  87. package/dist/cli/number-command.d.ts +12 -0
  88. package/dist/cli/number-command.d.ts.map +1 -0
  89. package/dist/cli/number-command.js +89 -0
  90. package/dist/cli/number-command.js.map +1 -0
  91. package/dist/cli/options.d.ts +30 -0
  92. package/dist/cli/options.d.ts.map +1 -0
  93. package/dist/cli/options.js +54 -0
  94. package/dist/cli/options.js.map +1 -0
  95. package/dist/cli/run-command.d.ts +24 -0
  96. package/dist/cli/run-command.d.ts.map +1 -0
  97. package/dist/cli/run-command.js +40 -0
  98. package/dist/cli/run-command.js.map +1 -0
  99. package/dist/cli/run.d.ts +4 -42
  100. package/dist/cli/run.d.ts.map +1 -1
  101. package/dist/cli/run.js +6 -61
  102. package/dist/cli/run.js.map +1 -1
  103. package/dist/cli/script-command.d.ts +10 -0
  104. package/dist/cli/script-command.d.ts.map +1 -0
  105. package/dist/cli/script-command.js +58 -0
  106. package/dist/cli/script-command.js.map +1 -0
  107. package/dist/cli/segment-command.d.ts +11 -0
  108. package/dist/cli/segment-command.d.ts.map +1 -0
  109. package/dist/cli/segment-command.js +53 -0
  110. package/dist/cli/segment-command.js.map +1 -0
  111. package/dist/cli/slug-command.d.ts +10 -0
  112. package/dist/cli/slug-command.d.ts.map +1 -0
  113. package/dist/cli/slug-command.js +28 -0
  114. package/dist/cli/slug-command.js.map +1 -0
  115. package/dist/cli/syllable-command.d.ts +14 -0
  116. package/dist/cli/syllable-command.d.ts.map +1 -0
  117. package/dist/cli/syllable-command.js +82 -0
  118. package/dist/cli/syllable-command.js.map +1 -0
  119. package/dist/cli/system-table.d.ts +12 -0
  120. package/dist/cli/system-table.d.ts.map +1 -0
  121. package/dist/cli/system-table.js +48 -0
  122. package/dist/cli/system-table.js.map +1 -0
  123. package/dist/cli/systems.d.ts +57 -0
  124. package/dist/cli/systems.d.ts.map +1 -0
  125. package/dist/cli/systems.js +27 -0
  126. package/dist/cli/systems.js.map +1 -0
  127. package/dist/cli/transcribe-command.d.ts +18 -0
  128. package/dist/cli/transcribe-command.d.ts.map +1 -0
  129. package/dist/cli/transcribe-command.js +86 -0
  130. package/dist/cli/transcribe-command.js.map +1 -0
  131. package/dist/cli/transcribe-reading.d.ts +15 -0
  132. package/dist/cli/transcribe-reading.d.ts.map +1 -0
  133. package/dist/cli/transcribe-reading.js +90 -0
  134. package/dist/cli/transcribe-reading.js.map +1 -0
  135. package/dist/cli/transcribe-rows.d.ts +26 -0
  136. package/dist/cli/transcribe-rows.d.ts.map +1 -0
  137. package/dist/cli/transcribe-rows.js +30 -0
  138. package/dist/cli/transcribe-rows.js.map +1 -0
  139. package/dist/cli/usage-error.d.ts +9 -0
  140. package/dist/cli/usage-error.d.ts.map +1 -0
  141. package/dist/cli/usage-error.js +9 -0
  142. package/dist/cli/usage-error.js.map +1 -0
  143. package/dist/decode/alternatives.d.ts +16 -0
  144. package/dist/decode/alternatives.d.ts.map +1 -0
  145. package/dist/decode/alternatives.js +31 -0
  146. package/dist/decode/alternatives.js.map +1 -0
  147. package/dist/decode/confidence.d.ts.map +1 -1
  148. package/dist/decode/confidence.js +3 -118
  149. package/dist/decode/confidence.js.map +1 -1
  150. package/dist/decode/convert-options.d.ts +116 -0
  151. package/dist/decode/convert-options.d.ts.map +1 -0
  152. package/dist/decode/convert-options.js +2 -0
  153. package/dist/decode/convert-options.js.map +1 -0
  154. package/dist/decode/convert-pipeline.d.ts +18 -0
  155. package/dist/decode/convert-pipeline.d.ts.map +1 -0
  156. package/dist/decode/convert-pipeline.js +66 -0
  157. package/dist/decode/convert-pipeline.js.map +1 -0
  158. package/dist/decode/convert.d.ts +9 -118
  159. package/dist/decode/convert.d.ts.map +1 -1
  160. package/dist/decode/convert.js +5 -453
  161. package/dist/decode/convert.js.map +1 -1
  162. package/dist/decode/decode.d.ts +2 -15
  163. package/dist/decode/decode.d.ts.map +1 -1
  164. package/dist/decode/decode.js +2 -121
  165. package/dist/decode/decode.js.map +1 -1
  166. package/dist/decode/decoders.d.ts +32 -0
  167. package/dist/decode/decoders.d.ts.map +1 -0
  168. package/dist/decode/decoders.js +29 -0
  169. package/dist/decode/decoders.js.map +1 -0
  170. package/dist/decode/edge-context.d.ts +38 -0
  171. package/dist/decode/edge-context.d.ts.map +1 -0
  172. package/dist/decode/edge-context.js +57 -0
  173. package/dist/decode/edge-context.js.map +1 -0
  174. package/dist/decode/hint-lattice.d.ts +45 -0
  175. package/dist/decode/hint-lattice.d.ts.map +1 -0
  176. package/dist/decode/hint-lattice.js +140 -0
  177. package/dist/decode/hint-lattice.js.map +1 -0
  178. package/dist/decode/hints.d.ts +2 -45
  179. package/dist/decode/hints.d.ts.map +1 -1
  180. package/dist/decode/hints.js +1 -139
  181. package/dist/decode/hints.js.map +1 -1
  182. package/dist/decode/jiao-rule.d.ts +58 -0
  183. package/dist/decode/jiao-rule.d.ts.map +1 -0
  184. package/dist/decode/jiao-rule.js +76 -0
  185. package/dist/decode/jiao-rule.js.map +1 -0
  186. package/dist/decode/lattice-costs.d.ts +55 -0
  187. package/dist/decode/lattice-costs.d.ts.map +1 -0
  188. package/dist/decode/lattice-costs.js +90 -0
  189. package/dist/decode/lattice-costs.js.map +1 -0
  190. package/dist/decode/lattice-edges.d.ts +29 -0
  191. package/dist/decode/lattice-edges.d.ts.map +1 -0
  192. package/dist/decode/lattice-edges.js +78 -0
  193. package/dist/decode/lattice-edges.js.map +1 -0
  194. package/dist/decode/lattice-slice.d.ts +37 -0
  195. package/dist/decode/lattice-slice.d.ts.map +1 -0
  196. package/dist/decode/lattice-slice.js +43 -0
  197. package/dist/decode/lattice-slice.js.map +1 -0
  198. package/dist/decode/lattice-types.d.ts +82 -0
  199. package/dist/decode/lattice-types.d.ts.map +1 -0
  200. package/dist/decode/lattice-types.js +44 -0
  201. package/dist/decode/lattice-types.js.map +1 -0
  202. package/dist/decode/lattice.d.ts +2 -59
  203. package/dist/decode/lattice.d.ts.map +1 -1
  204. package/dist/decode/lattice.js +2 -118
  205. package/dist/decode/lattice.js.map +1 -1
  206. package/dist/decode/number-pieces.d.ts +62 -0
  207. package/dist/decode/number-pieces.d.ts.map +1 -0
  208. package/dist/decode/number-pieces.js +106 -0
  209. package/dist/decode/number-pieces.js.map +1 -0
  210. package/dist/decode/numbers.d.ts +53 -0
  211. package/dist/decode/numbers.d.ts.map +1 -0
  212. package/dist/decode/numbers.js +69 -0
  213. package/dist/decode/numbers.js.map +1 -0
  214. package/dist/decode/pieces.d.ts +78 -0
  215. package/dist/decode/pieces.d.ts.map +1 -0
  216. package/dist/decode/pieces.js +136 -0
  217. package/dist/decode/pieces.js.map +1 -0
  218. package/dist/decode/polyphone-rules.d.ts +31 -0
  219. package/dist/decode/polyphone-rules.d.ts.map +1 -0
  220. package/dist/decode/polyphone-rules.js +159 -0
  221. package/dist/decode/polyphone-rules.js.map +1 -0
  222. package/dist/decode/reading-rules.d.ts +2 -97
  223. package/dist/decode/reading-rules.d.ts.map +1 -1
  224. package/dist/decode/reading-rules.js +4 -365
  225. package/dist/decode/reading-rules.js.map +1 -1
  226. package/dist/decode/rules.d.ts +1 -17
  227. package/dist/decode/rules.d.ts.map +1 -1
  228. package/dist/decode/rules.js +1 -43
  229. package/dist/decode/rules.js.map +1 -1
  230. package/dist/decode/run-lattice.d.ts +52 -0
  231. package/dist/decode/run-lattice.d.ts.map +1 -0
  232. package/dist/decode/run-lattice.js +91 -0
  233. package/dist/decode/run-lattice.js.map +1 -0
  234. package/dist/decode/sandhi-tones.d.ts +69 -0
  235. package/dist/decode/sandhi-tones.d.ts.map +1 -0
  236. package/dist/decode/sandhi-tones.js +88 -0
  237. package/dist/decode/sandhi-tones.js.map +1 -0
  238. package/dist/decode/sandhi.d.ts +1 -1
  239. package/dist/decode/sandhi.d.ts.map +1 -1
  240. package/dist/decode/sandhi.js +1 -81
  241. package/dist/decode/sandhi.js.map +1 -1
  242. package/dist/decode/script-types.d.ts +76 -0
  243. package/dist/decode/script-types.d.ts.map +1 -0
  244. package/dist/decode/script-types.js +35 -0
  245. package/dist/decode/script-types.js.map +1 -0
  246. package/dist/decode/script-words.d.ts +32 -0
  247. package/dist/decode/script-words.d.ts.map +1 -0
  248. package/dist/decode/script-words.js +77 -0
  249. package/dist/decode/script-words.js.map +1 -0
  250. package/dist/decode/script.d.ts +3 -73
  251. package/dist/decode/script.d.ts.map +1 -1
  252. package/dist/decode/script.js +3 -109
  253. package/dist/decode/script.js.map +1 -1
  254. package/dist/decode/tan-rule.d.ts +68 -0
  255. package/dist/decode/tan-rule.d.ts.map +1 -0
  256. package/dist/decode/tan-rule.js +131 -0
  257. package/dist/decode/tan-rule.js.map +1 -0
  258. package/dist/decode/write-run.d.ts +28 -0
  259. package/dist/decode/write-run.d.ts.map +1 -0
  260. package/dist/decode/write-run.js +77 -0
  261. package/dist/decode/write-run.js.map +1 -0
  262. package/dist/dictionary/artifact-claims.d.ts +25 -0
  263. package/dist/dictionary/artifact-claims.d.ts.map +1 -0
  264. package/dist/dictionary/artifact-claims.js +47 -0
  265. package/dist/dictionary/artifact-claims.js.map +1 -0
  266. package/dist/dictionary/artifact-format.d.ts +86 -0
  267. package/dist/dictionary/artifact-format.d.ts.map +1 -0
  268. package/dist/dictionary/artifact-format.js +91 -0
  269. package/dist/dictionary/artifact-format.js.map +1 -0
  270. package/dist/dictionary/artifact-read.d.ts +34 -0
  271. package/dist/dictionary/artifact-read.d.ts.map +1 -0
  272. package/dist/dictionary/artifact-read.js +114 -0
  273. package/dist/dictionary/artifact-read.js.map +1 -0
  274. package/dist/dictionary/artifact.d.ts +4 -63
  275. package/dist/dictionary/artifact.d.ts.map +1 -1
  276. package/dist/dictionary/artifact.js +12 -229
  277. package/dist/dictionary/artifact.js.map +1 -1
  278. package/dist/dictionary/assertions.d.ts +5 -57
  279. package/dist/dictionary/assertions.d.ts.map +1 -1
  280. package/dist/dictionary/assertions.js +4 -317
  281. package/dist/dictionary/assertions.js.map +1 -1
  282. package/dist/dictionary/build-assertions.d.ts +12 -0
  283. package/dist/dictionary/build-assertions.d.ts.map +1 -0
  284. package/dist/dictionary/build-assertions.js +13 -0
  285. package/dist/dictionary/build-assertions.js.map +1 -0
  286. package/dist/dictionary/built-dictionary.d.ts +46 -0
  287. package/dist/dictionary/built-dictionary.d.ts.map +1 -0
  288. package/dist/dictionary/built-dictionary.js +97 -0
  289. package/dist/dictionary/built-dictionary.js.map +1 -0
  290. package/dist/dictionary/cedict-senses.d.ts +80 -0
  291. package/dist/dictionary/cedict-senses.d.ts.map +1 -0
  292. package/dist/dictionary/cedict-senses.js +114 -0
  293. package/dist/dictionary/cedict-senses.js.map +1 -0
  294. package/dist/dictionary/character-defaults.d.ts +26 -0
  295. package/dist/dictionary/character-defaults.d.ts.map +1 -0
  296. package/dist/dictionary/character-defaults.js +67 -0
  297. package/dist/dictionary/character-defaults.js.map +1 -0
  298. package/dist/dictionary/character-readings.d.ts +10 -0
  299. package/dist/dictionary/character-readings.d.ts.map +1 -0
  300. package/dist/dictionary/character-readings.js +25 -0
  301. package/dist/dictionary/character-readings.js.map +1 -0
  302. package/dist/dictionary/dictionary-entry.d.ts +37 -0
  303. package/dist/dictionary/dictionary-entry.d.ts.map +1 -0
  304. package/dist/dictionary/dictionary-entry.js +41 -0
  305. package/dist/dictionary/dictionary-entry.js.map +1 -0
  306. package/dist/dictionary/dictionary-readings.d.ts +56 -0
  307. package/dist/dictionary/dictionary-readings.d.ts.map +1 -0
  308. package/dist/dictionary/dictionary-readings.js +93 -0
  309. package/dist/dictionary/dictionary-readings.js.map +1 -0
  310. package/dist/dictionary/dictionary.d.ts +6 -60
  311. package/dist/dictionary/dictionary.d.ts.map +1 -1
  312. package/dist/dictionary/dictionary.js +9 -169
  313. package/dist/dictionary/dictionary.js.map +1 -1
  314. package/dist/dictionary/entry-invariants.d.ts +3 -0
  315. package/dist/dictionary/entry-invariants.d.ts.map +1 -0
  316. package/dist/dictionary/entry-invariants.js +67 -0
  317. package/dist/dictionary/entry-invariants.js.map +1 -0
  318. package/dist/dictionary/entry-lines.d.ts +35 -0
  319. package/dist/dictionary/entry-lines.d.ts.map +1 -0
  320. package/dist/dictionary/entry-lines.js +70 -0
  321. package/dist/dictionary/entry-lines.js.map +1 -0
  322. package/dist/dictionary/erhua-repair.d.ts +26 -0
  323. package/dist/dictionary/erhua-repair.d.ts.map +1 -0
  324. package/dist/dictionary/erhua-repair.js +49 -0
  325. package/dist/dictionary/erhua-repair.js.map +1 -0
  326. package/dist/dictionary/frequency-tones.d.ts +74 -0
  327. package/dist/dictionary/frequency-tones.d.ts.map +1 -0
  328. package/dist/dictionary/frequency-tones.js +128 -0
  329. package/dist/dictionary/frequency-tones.js.map +1 -0
  330. package/dist/dictionary/inventory-invariants.d.ts +3 -0
  331. package/dist/dictionary/inventory-invariants.d.ts.map +1 -0
  332. package/dist/dictionary/inventory-invariants.js +54 -0
  333. package/dist/dictionary/inventory-invariants.js.map +1 -0
  334. package/dist/dictionary/locale-candidates.d.ts +40 -0
  335. package/dist/dictionary/locale-candidates.d.ts.map +1 -0
  336. package/dist/dictionary/locale-candidates.js +77 -0
  337. package/dist/dictionary/locale-candidates.js.map +1 -0
  338. package/dist/dictionary/locale-segments.d.ts +47 -0
  339. package/dist/dictionary/locale-segments.d.ts.map +1 -0
  340. package/dist/dictionary/locale-segments.js +141 -0
  341. package/dist/dictionary/locale-segments.js.map +1 -0
  342. package/dist/dictionary/locale.d.ts +1 -21
  343. package/dist/dictionary/locale.d.ts.map +1 -1
  344. package/dist/dictionary/locale.js +9 -198
  345. package/dist/dictionary/locale.js.map +1 -1
  346. package/dist/dictionary/merge-types.d.ts +121 -0
  347. package/dist/dictionary/merge-types.d.ts.map +1 -0
  348. package/dist/dictionary/merge-types.js +35 -0
  349. package/dist/dictionary/merge-types.js.map +1 -0
  350. package/dist/dictionary/merge-word.d.ts +7 -0
  351. package/dist/dictionary/merge-word.d.ts.map +1 -0
  352. package/dist/dictionary/merge-word.js +91 -0
  353. package/dist/dictionary/merge-word.js.map +1 -0
  354. package/dist/dictionary/merge.d.ts +5 -62
  355. package/dist/dictionary/merge.d.ts.map +1 -1
  356. package/dist/dictionary/merge.js +30 -713
  357. package/dist/dictionary/merge.js.map +1 -1
  358. package/dist/dictionary/proper-noun.d.ts +28 -0
  359. package/dist/dictionary/proper-noun.d.ts.map +1 -0
  360. package/dist/dictionary/proper-noun.js +43 -0
  361. package/dist/dictionary/proper-noun.js.map +1 -0
  362. package/dist/dictionary/reading-agreement.d.ts +71 -0
  363. package/dist/dictionary/reading-agreement.d.ts.map +1 -0
  364. package/dist/dictionary/reading-agreement.js +156 -0
  365. package/dist/dictionary/reading-agreement.js.map +1 -0
  366. package/dist/dictionary/script-conversion.d.ts +28 -0
  367. package/dist/dictionary/script-conversion.d.ts.map +1 -0
  368. package/dist/dictionary/script-conversion.js +58 -0
  369. package/dist/dictionary/script-conversion.js.map +1 -0
  370. package/dist/dictionary/script-pairings.d.ts +74 -0
  371. package/dist/dictionary/script-pairings.d.ts.map +1 -0
  372. package/dist/dictionary/script-pairings.js +120 -0
  373. package/dist/dictionary/script-pairings.js.map +1 -0
  374. package/dist/dictionary/script-tables.d.ts.map +1 -1
  375. package/dist/dictionary/script-tables.js +2 -165
  376. package/dist/dictionary/script-tables.js.map +1 -1
  377. package/dist/dictionary/taiwan-reading.d.ts +8 -0
  378. package/dist/dictionary/taiwan-reading.d.ts.map +1 -0
  379. package/dist/dictionary/taiwan-reading.js +38 -0
  380. package/dist/dictionary/taiwan-reading.js.map +1 -0
  381. package/dist/dictionary/tone-invariants.d.ts +3 -0
  382. package/dist/dictionary/tone-invariants.d.ts.map +1 -0
  383. package/dist/dictionary/tone-invariants.js +64 -0
  384. package/dist/dictionary/tone-invariants.js.map +1 -0
  385. package/dist/dictionary/traditional-form.d.ts +21 -0
  386. package/dist/dictionary/traditional-form.d.ts.map +1 -0
  387. package/dist/dictionary/traditional-form.js +59 -0
  388. package/dist/dictionary/traditional-form.js.map +1 -0
  389. package/dist/dictionary/traditional-ranking.d.ts +22 -0
  390. package/dist/dictionary/traditional-ranking.d.ts.map +1 -0
  391. package/dist/dictionary/traditional-ranking.js +74 -0
  392. package/dist/dictionary/traditional-ranking.js.map +1 -0
  393. package/dist/dictionary/traditional-table.d.ts +51 -0
  394. package/dist/dictionary/traditional-table.d.ts.map +1 -0
  395. package/dist/dictionary/traditional-table.js +98 -0
  396. package/dist/dictionary/traditional-table.js.map +1 -0
  397. package/dist/dictionary/traditional.d.ts +3 -56
  398. package/dist/dictionary/traditional.d.ts.map +1 -1
  399. package/dist/dictionary/traditional.js +3 -186
  400. package/dist/dictionary/traditional.js.map +1 -1
  401. package/dist/dictionary/variant-counts.d.ts +39 -0
  402. package/dist/dictionary/variant-counts.d.ts.map +1 -0
  403. package/dist/dictionary/variant-counts.js +38 -0
  404. package/dist/dictionary/variant-counts.js.map +1 -0
  405. package/dist/dictionary/word-reading.d.ts +26 -0
  406. package/dist/dictionary/word-reading.d.ts.map +1 -0
  407. package/dist/dictionary/word-reading.js +76 -0
  408. package/dist/dictionary/word-reading.js.map +1 -0
  409. package/dist/dictionary/word-readings.d.ts +15 -0
  410. package/dist/dictionary/word-readings.d.ts.map +1 -0
  411. package/dist/dictionary/word-readings.js +38 -0
  412. package/dist/dictionary/word-readings.js.map +1 -0
  413. package/dist/format/annotate.d.ts +90 -0
  414. package/dist/format/annotate.d.ts.map +1 -0
  415. package/dist/format/annotate.js +168 -0
  416. package/dist/format/annotate.js.map +1 -0
  417. package/dist/format/html.d.ts +15 -46
  418. package/dist/format/html.d.ts.map +1 -1
  419. package/dist/format/html.js +3 -162
  420. package/dist/format/html.js.map +1 -1
  421. package/dist/format/slug-hash.d.ts +51 -0
  422. package/dist/format/slug-hash.d.ts.map +1 -0
  423. package/dist/format/slug-hash.js +74 -0
  424. package/dist/format/slug-hash.js.map +1 -0
  425. package/dist/format/slug-options.d.ts +98 -0
  426. package/dist/format/slug-options.d.ts.map +1 -0
  427. package/dist/format/slug-options.js +2 -0
  428. package/dist/format/slug-options.js.map +1 -0
  429. package/dist/format/slug-words.d.ts +27 -0
  430. package/dist/format/slug-words.d.ts.map +1 -0
  431. package/dist/format/slug-words.js +0 -0
  432. package/dist/format/slug-words.js.map +1 -0
  433. package/dist/format/slug.d.ts +3 -128
  434. package/dist/format/slug.d.ts.map +1 -1
  435. package/dist/format/slug.js +0 -0
  436. package/dist/format/slug.js.map +1 -1
  437. package/dist/grade/check-readings.d.ts +41 -0
  438. package/dist/grade/check-readings.d.ts.map +1 -0
  439. package/dist/grade/check-readings.js +36 -0
  440. package/dist/grade/check-readings.js.map +1 -0
  441. package/dist/grade/check.d.ts +4 -4
  442. package/dist/grade/check.d.ts.map +1 -1
  443. package/dist/grade/check.js +5 -270
  444. package/dist/grade/check.js.map +1 -1
  445. package/dist/grade/pair-syllables.d.ts +48 -0
  446. package/dist/grade/pair-syllables.d.ts.map +1 -0
  447. package/dist/grade/pair-syllables.js +71 -0
  448. package/dist/grade/pair-syllables.js.map +1 -0
  449. package/dist/grade/reading-syllables.d.ts +62 -0
  450. package/dist/grade/reading-syllables.d.ts.map +1 -0
  451. package/dist/grade/reading-syllables.js +58 -0
  452. package/dist/grade/reading-syllables.js.map +1 -0
  453. package/dist/grade/reading-tolerance.d.ts +72 -0
  454. package/dist/grade/reading-tolerance.d.ts.map +1 -0
  455. package/dist/grade/reading-tolerance.js +107 -0
  456. package/dist/grade/reading-tolerance.js.map +1 -0
  457. package/dist/grade/typed-reading.d.ts +28 -0
  458. package/dist/grade/typed-reading.d.ts.map +1 -0
  459. package/dist/grade/typed-reading.js +36 -0
  460. package/dist/grade/typed-reading.js.map +1 -0
  461. package/dist/numerals/numeral-parse.d.ts +32 -0
  462. package/dist/numerals/numeral-parse.d.ts.map +1 -0
  463. package/dist/numerals/numeral-parse.js +44 -0
  464. package/dist/numerals/numeral-parse.js.map +1 -0
  465. package/dist/numerals/numeral-shapes.d.ts +89 -0
  466. package/dist/numerals/numeral-shapes.d.ts.map +1 -0
  467. package/dist/numerals/numeral-shapes.js +99 -0
  468. package/dist/numerals/numeral-shapes.js.map +1 -0
  469. package/dist/numerals/numerals.d.ts.map +1 -1
  470. package/dist/numerals/numerals.js +2 -36
  471. package/dist/numerals/numerals.js.map +1 -1
  472. package/dist/numerals/read-numeral.d.ts +76 -0
  473. package/dist/numerals/read-numeral.d.ts.map +1 -0
  474. package/dist/numerals/read-numeral.js +88 -0
  475. package/dist/numerals/read-numeral.js.map +1 -0
  476. package/dist/numerals/text.d.ts +3 -37
  477. package/dist/numerals/text.d.ts.map +1 -1
  478. package/dist/numerals/text.js +3 -254
  479. package/dist/numerals/text.js.map +1 -1
  480. package/dist/numerals/time.d.ts +34 -0
  481. package/dist/numerals/time.d.ts.map +1 -0
  482. package/dist/numerals/time.js +93 -0
  483. package/dist/numerals/time.js.map +1 -0
  484. package/dist/orthography/address-grouping.d.ts +34 -0
  485. package/dist/orthography/address-grouping.d.ts.map +1 -0
  486. package/dist/orthography/address-grouping.js +52 -0
  487. package/dist/orthography/address-grouping.js.map +1 -0
  488. package/dist/orthography/grouping.d.ts +3 -87
  489. package/dist/orthography/grouping.d.ts.map +1 -1
  490. package/dist/orthography/grouping.js +4 -270
  491. package/dist/orthography/grouping.js.map +1 -1
  492. package/dist/orthography/place-grouping.d.ts +39 -0
  493. package/dist/orthography/place-grouping.d.ts.map +1 -0
  494. package/dist/orthography/place-grouping.js +83 -0
  495. package/dist/orthography/place-grouping.js.map +1 -0
  496. package/dist/orthography/word-grouping.d.ts +48 -0
  497. package/dist/orthography/word-grouping.d.ts.map +1 -0
  498. package/dist/orthography/word-grouping.js +147 -0
  499. package/dist/orthography/word-grouping.js.map +1 -0
  500. package/dist/script/conversion-format.d.ts +22 -0
  501. package/dist/script/conversion-format.d.ts.map +1 -0
  502. package/dist/script/conversion-format.js +22 -0
  503. package/dist/script/conversion-format.js.map +1 -0
  504. package/dist/script/conversion-read.d.ts +9 -0
  505. package/dist/script/conversion-read.d.ts.map +1 -0
  506. package/dist/script/conversion-read.js +69 -0
  507. package/dist/script/conversion-read.js.map +1 -0
  508. package/dist/script/conversion-write.d.ts +14 -0
  509. package/dist/script/conversion-write.d.ts.map +1 -0
  510. package/dist/script/conversion-write.js +34 -0
  511. package/dist/script/conversion-write.js.map +1 -0
  512. package/dist/script/conversion.d.ts +10 -16
  513. package/dist/script/conversion.d.ts.map +1 -1
  514. package/dist/script/conversion.js +2 -115
  515. package/dist/script/conversion.js.map +1 -1
  516. package/dist/search/candidate-narrowing.d.ts +56 -0
  517. package/dist/search/candidate-narrowing.d.ts.map +1 -0
  518. package/dist/search/candidate-narrowing.js +55 -0
  519. package/dist/search/candidate-narrowing.js.map +1 -0
  520. package/dist/search/candidate-query.d.ts +25 -0
  521. package/dist/search/candidate-query.d.ts.map +1 -0
  522. package/dist/search/candidate-query.js +28 -0
  523. package/dist/search/candidate-query.js.map +1 -0
  524. package/dist/search/candidate-writings.d.ts +24 -0
  525. package/dist/search/candidate-writings.d.ts.map +1 -0
  526. package/dist/search/candidate-writings.js +114 -0
  527. package/dist/search/candidate-writings.js.map +1 -0
  528. package/dist/search/candidates.d.ts +7 -41
  529. package/dist/search/candidates.d.ts.map +1 -1
  530. package/dist/search/candidates.js +10 -164
  531. package/dist/search/candidates.js.map +1 -1
  532. package/dist/search/match-chunks.d.ts +19 -0
  533. package/dist/search/match-chunks.d.ts.map +1 -0
  534. package/dist/search/match-chunks.js +30 -0
  535. package/dist/search/match-chunks.js.map +1 -0
  536. package/dist/search/match-ranking.d.ts +39 -0
  537. package/dist/search/match-ranking.d.ts.map +1 -0
  538. package/dist/search/match-ranking.js +51 -0
  539. package/dist/search/match-ranking.js.map +1 -0
  540. package/dist/search/match-readings.d.ts +43 -0
  541. package/dist/search/match-readings.d.ts.map +1 -0
  542. package/dist/search/match-readings.js +83 -0
  543. package/dist/search/match-readings.js.map +1 -0
  544. package/dist/search/match-scoring.d.ts +146 -0
  545. package/dist/search/match-scoring.d.ts.map +1 -0
  546. package/dist/search/match-scoring.js +114 -0
  547. package/dist/search/match-scoring.js.map +1 -0
  548. package/dist/search/match-search.d.ts +28 -0
  549. package/dist/search/match-search.d.ts.map +1 -0
  550. package/dist/search/match-search.js +128 -0
  551. package/dist/search/match-search.js.map +1 -0
  552. package/dist/search/match.d.ts +5 -36
  553. package/dist/search/match.d.ts.map +1 -1
  554. package/dist/search/match.js +2 -379
  555. package/dist/search/match.js.map +1 -1
  556. package/dist/search/reverse-index-build.d.ts +30 -0
  557. package/dist/search/reverse-index-build.d.ts.map +1 -0
  558. package/dist/search/reverse-index-build.js +72 -0
  559. package/dist/search/reverse-index-build.js.map +1 -0
  560. package/dist/search/reverse-index-format.d.ts +60 -0
  561. package/dist/search/reverse-index-format.d.ts.map +1 -0
  562. package/dist/search/reverse-index-format.js +54 -0
  563. package/dist/search/reverse-index-format.js.map +1 -0
  564. package/dist/search/reverse-index-groups.d.ts +37 -0
  565. package/dist/search/reverse-index-groups.d.ts.map +1 -0
  566. package/dist/search/reverse-index-groups.js +71 -0
  567. package/dist/search/reverse-index-groups.js.map +1 -0
  568. package/dist/search/reverse-index-passes.d.ts +78 -0
  569. package/dist/search/reverse-index-passes.d.ts.map +1 -0
  570. package/dist/search/reverse-index-passes.js +59 -0
  571. package/dist/search/reverse-index-passes.js.map +1 -0
  572. package/dist/search/reverse-index-state.d.ts +36 -0
  573. package/dist/search/reverse-index-state.d.ts.map +1 -0
  574. package/dist/search/reverse-index-state.js +95 -0
  575. package/dist/search/reverse-index-state.js.map +1 -0
  576. package/dist/search/reverse-index.d.ts +8 -67
  577. package/dist/search/reverse-index.d.ts.map +1 -1
  578. package/dist/search/reverse-index.js +4 -255
  579. package/dist/search/reverse-index.js.map +1 -1
  580. package/dist/sources/unihan-readings.d.ts +58 -0
  581. package/dist/sources/unihan-readings.d.ts.map +1 -0
  582. package/dist/sources/unihan-readings.js +95 -0
  583. package/dist/sources/unihan-readings.js.map +1 -0
  584. package/dist/sources/unihan.d.ts +6 -9
  585. package/dist/sources/unihan.d.ts.map +1 -1
  586. package/dist/sources/unihan.js +2 -85
  587. package/dist/sources/unihan.js.map +1 -1
  588. package/dist/syllable/final-tables.d.ts +23 -0
  589. package/dist/syllable/final-tables.d.ts.map +1 -0
  590. package/dist/syllable/final-tables.js +50 -0
  591. package/dist/syllable/final-tables.js.map +1 -0
  592. package/dist/syllable/inventory.d.ts +8 -42
  593. package/dist/syllable/inventory.d.ts.map +1 -1
  594. package/dist/syllable/inventory.js +9 -918
  595. package/dist/syllable/inventory.js.map +1 -1
  596. package/dist/syllable/spellings.d.ts +40 -0
  597. package/dist/syllable/spellings.d.ts.map +1 -0
  598. package/dist/syllable/spellings.js +469 -0
  599. package/dist/syllable/spellings.js.map +1 -0
  600. package/dist/syllable/syllable-parts.d.ts +31 -0
  601. package/dist/syllable/syllable-parts.d.ts.map +1 -0
  602. package/dist/syllable/syllable-parts.js +105 -0
  603. package/dist/syllable/syllable-parts.js.map +1 -0
  604. package/dist/syllable/syllable.d.ts +1 -14
  605. package/dist/syllable/syllable.d.ts.map +1 -1
  606. package/dist/syllable/syllable.js +3 -144
  607. package/dist/syllable/syllable.js.map +1 -1
  608. package/dist/syllable/written-tones.d.ts +6 -0
  609. package/dist/syllable/written-tones.d.ts.map +1 -0
  610. package/dist/syllable/written-tones.js +453 -0
  611. package/dist/syllable/written-tones.js.map +1 -0
  612. package/dist/transcription/bopomofo-parse.d.ts +42 -0
  613. package/dist/transcription/bopomofo-parse.d.ts.map +1 -0
  614. package/dist/transcription/bopomofo-parse.js +92 -0
  615. package/dist/transcription/bopomofo-parse.js.map +1 -0
  616. package/dist/transcription/bopomofo-reverse.d.ts +31 -0
  617. package/dist/transcription/bopomofo-reverse.d.ts.map +1 -0
  618. package/dist/transcription/bopomofo-reverse.js +48 -0
  619. package/dist/transcription/bopomofo-reverse.js.map +1 -0
  620. package/dist/transcription/bopomofo-symbols.d.ts +36 -0
  621. package/dist/transcription/bopomofo-symbols.d.ts.map +1 -0
  622. package/dist/transcription/bopomofo-symbols.js +41 -0
  623. package/dist/transcription/bopomofo-symbols.js.map +1 -0
  624. package/dist/transcription/bopomofo-tables.d.ts +87 -0
  625. package/dist/transcription/bopomofo-tables.d.ts.map +1 -0
  626. package/dist/transcription/bopomofo-tables.js +180 -0
  627. package/dist/transcription/bopomofo-tables.js.map +1 -0
  628. package/dist/transcription/bopomofo.d.ts +14 -32
  629. package/dist/transcription/bopomofo.d.ts.map +1 -1
  630. package/dist/transcription/bopomofo.js +5 -343
  631. package/dist/transcription/bopomofo.js.map +1 -1
  632. package/dist/transcription/gwoyeu-first-second.d.ts +36 -0
  633. package/dist/transcription/gwoyeu-first-second.d.ts.map +1 -0
  634. package/dist/transcription/gwoyeu-first-second.js +75 -0
  635. package/dist/transcription/gwoyeu-first-second.js.map +1 -0
  636. package/dist/transcription/gwoyeu-spelling.d.ts +38 -0
  637. package/dist/transcription/gwoyeu-spelling.d.ts.map +1 -0
  638. package/dist/transcription/gwoyeu-spelling.js +124 -0
  639. package/dist/transcription/gwoyeu-spelling.js.map +1 -0
  640. package/dist/transcription/gwoyeu-tables.d.ts +93 -0
  641. package/dist/transcription/gwoyeu-tables.d.ts.map +1 -0
  642. package/dist/transcription/gwoyeu-tables.js +205 -0
  643. package/dist/transcription/gwoyeu-tables.js.map +1 -0
  644. package/dist/transcription/gwoyeu-tonal-forms.d.ts +49 -0
  645. package/dist/transcription/gwoyeu-tonal-forms.d.ts.map +1 -0
  646. package/dist/transcription/gwoyeu-tonal-forms.js +89 -0
  647. package/dist/transcription/gwoyeu-tonal-forms.js.map +1 -0
  648. package/dist/transcription/gwoyeu-vowels.d.ts +51 -0
  649. package/dist/transcription/gwoyeu-vowels.d.ts.map +1 -0
  650. package/dist/transcription/gwoyeu-vowels.js +58 -0
  651. package/dist/transcription/gwoyeu-vowels.js.map +1 -0
  652. package/dist/transcription/gwoyeu.d.ts +1 -26
  653. package/dist/transcription/gwoyeu.d.ts.map +1 -1
  654. package/dist/transcription/gwoyeu.js +2 -540
  655. package/dist/transcription/gwoyeu.js.map +1 -1
  656. package/dist/transcription/ipa-symbols.d.ts +67 -0
  657. package/dist/transcription/ipa-symbols.d.ts.map +1 -0
  658. package/dist/transcription/ipa-symbols.js +135 -0
  659. package/dist/transcription/ipa-symbols.js.map +1 -0
  660. package/dist/transcription/ipa.d.ts +2 -10
  661. package/dist/transcription/ipa.d.ts.map +1 -1
  662. package/dist/transcription/ipa.js +2 -134
  663. package/dist/transcription/ipa.js.map +1 -1
  664. package/dist/transcription/wade-giles-index.d.ts +35 -0
  665. package/dist/transcription/wade-giles-index.d.ts.map +1 -0
  666. package/dist/transcription/wade-giles-index.js +110 -0
  667. package/dist/transcription/wade-giles-index.js.map +1 -0
  668. package/dist/transcription/wade-giles-parse.d.ts +36 -0
  669. package/dist/transcription/wade-giles-parse.d.ts.map +1 -0
  670. package/dist/transcription/wade-giles-parse.js +84 -0
  671. package/dist/transcription/wade-giles-parse.js.map +1 -0
  672. package/dist/transcription/wade-giles-spelling.d.ts +61 -0
  673. package/dist/transcription/wade-giles-spelling.d.ts.map +1 -0
  674. package/dist/transcription/wade-giles-spelling.js +107 -0
  675. package/dist/transcription/wade-giles-spelling.js.map +1 -0
  676. package/dist/transcription/wade-giles-syllable.d.ts +29 -0
  677. package/dist/transcription/wade-giles-syllable.d.ts.map +1 -0
  678. package/dist/transcription/wade-giles-syllable.js +90 -0
  679. package/dist/transcription/wade-giles-syllable.js.map +1 -0
  680. package/dist/transcription/wade-giles-tables.d.ts +80 -0
  681. package/dist/transcription/wade-giles-tables.d.ts.map +1 -0
  682. package/dist/transcription/wade-giles-tables.js +178 -0
  683. package/dist/transcription/wade-giles-tables.js.map +1 -0
  684. package/dist/transcription/wade-giles.d.ts +9 -60
  685. package/dist/transcription/wade-giles.d.ts.map +1 -1
  686. package/dist/transcription/wade-giles.js +6 -543
  687. package/dist/transcription/wade-giles.js.map +1 -1
  688. package/dist/transcription/yale-tables.d.ts +54 -0
  689. package/dist/transcription/yale-tables.d.ts.map +1 -0
  690. package/dist/transcription/yale-tables.js +125 -0
  691. package/dist/transcription/yale-tables.js.map +1 -0
  692. package/dist/transcription/yale.d.ts.map +1 -1
  693. package/dist/transcription/yale.js +1 -124
  694. package/dist/transcription/yale.js.map +1 -1
  695. package/package.json +2 -2
@@ -0,0 +1,128 @@
1
+ import { FREQUENCY_FIELD } from "../sources/unihan.js";
2
+ import { NEUTRAL_TONE } from "../tone/tone.js";
3
+ import { readDictionaryReading } from "./reading.js";
4
+ /**
5
+ * Strip the tone marks from a reading, for comparing two spellings.
6
+ */
7
+ function tonelessReading(reading) {
8
+ return reading
9
+ .normalize("NFD")
10
+ .replaceAll(/[̀́̄̌]/gu, "")
11
+ .normalize("NFC");
12
+ }
13
+ /**
14
+ * Whether a reading carries a tone mark.
15
+ */
16
+ function isToneMarked(reading) {
17
+ return tonelessReading(reading) !== reading;
18
+ }
19
+ /**
20
+ * Put back a tone that `kHanyuPinlu` left off.
21
+ *
22
+ * The frequency field writes some readings without their tone mark: 李 is
23
+ * `li(36)` there where every dictionary field writes `lǐ`. Read as 轻声 — which
24
+ * is what an unmarked reading means in source data — that makes 李华 come out
25
+ * `Li Huá`, and it is the only Unihan field this happens in.
26
+ *
27
+ * The other fields settle which it is. If they also write the spelling bare,
28
+ * the neutral tone is real and 么, 们, 吧, 裳 keep it. If every one of them
29
+ * writes it with a tone, the frequency field simply omitted the mark, and the
30
+ * tone is taken back. Measured over the real file, 3,799 characters have a
31
+ * `kHanyuPinlu` entry, 60 of those have only unmarked readings, and the split
32
+ * is 45 that should carry a tone against 15 genuine 轻声.
33
+ */
34
+ export function resolveFrequencyTones(unihan) {
35
+ const frequencyReadings = unihan.fields.get(FREQUENCY_FIELD) ?? [];
36
+ // A character whose frequency field marks any tone is already trustworthy:
37
+ // there the unmarked readings sit alongside marked ones and mean 轻声.
38
+ if (frequencyReadings.length === 0 ||
39
+ frequencyReadings.some((reading) => isToneMarked(reading))) {
40
+ return unihan.readings;
41
+ }
42
+ const elsewhere = [...unihan.fields]
43
+ .filter(([field]) => field !== FREQUENCY_FIELD)
44
+ .flatMap(([, readings]) => readings);
45
+ return unihan.readings.map((reading) => {
46
+ if (isToneMarked(reading)) {
47
+ return reading;
48
+ }
49
+ const sameSpelling = elsewhere.filter((other) => tonelessReading(other) === reading);
50
+ if (sameSpelling.length === 0 || sameSpelling.includes(reading)) {
51
+ return reading;
52
+ }
53
+ return sameSpelling.find((other) => isToneMarked(other)) ?? reading;
54
+ });
55
+ }
56
+ /**
57
+ * A CC-CEDICT sense that describes a suffix rather than a word.
58
+ *
59
+ * Matches its own wording: 子 is `/noun suffix, as in 椅子[yi3 zi5] "chair"/`,
60
+ * and the other suffix senses are written the same way.
61
+ */
62
+ const SUFFIX_SENSE = /\bsuffix\b/iu;
63
+ /**
64
+ * Whether CC-CEDICT reads the bare character 轻声 in its own right.
65
+ *
66
+ * The exception to {@link demoteReducedNeutrals}, and the thing that separates
67
+ * a 语气词 from a syllable that is only ever unstressed inside a word. A
68
+ * single-character CC-CEDICT headword with a neutral reading is a claim about
69
+ * the character standing alone, which is exactly what the frequency field's
70
+ * counting cannot distinguish: 吗 is `(question particle for "yes-no"
71
+ * questions)`, 啊 is `modal particle ending sentence`, 得 is `structural
72
+ * particle: used after a verb`. Nine characters carry one — 得, 啊, 吗, 呀, 啦,
73
+ * 哇, 嘛, 罢 and 子 — and their 繁體 spellings with them.
74
+ *
75
+ * **A suffix sense is not such a claim.** 子's neutral headword is `noun
76
+ * suffix, as in 椅子`, which says the character is unstressed *in words*, and
77
+ * words are what the corpus can already see. 子 is `zǐ` on its own — 子曰, 母子
78
+ * — and CPP's human labelling has it `zi3` in 30 of its 38 cases.
79
+ *
80
+ * 罢 is the known loss. CC-CEDICT calls its `ba5` a final particle, so it is
81
+ * held here, and CPP labels the character `ba4` in all 40 of its cases: the
82
+ * particle is the literary 也罢 and 罢了, while a modern bare 罢 is 罢工. Left
83
+ * protected because the rule is about what a source claims of the character,
84
+ * and singling one out because a dataset disagrees is fitting to the dataset.
85
+ */
86
+ export function isNeutralAlone(character, entries) {
87
+ return entries.some((entry) => {
88
+ const reading = readDictionaryReading(character, entry.readings);
89
+ return (reading?.length === 1 &&
90
+ reading[0]?.tone === NEUTRAL_TONE &&
91
+ !entry.definitions.some((definition) => SUFFIX_SENSE.test(definition)));
92
+ });
93
+ }
94
+ /**
95
+ * Demote a 轻声 the frequency field counted only inside words.
96
+ *
97
+ * `kHanyuPinlu` counts occurrences in running text, and a character's neutral
98
+ * count there mixes two unrelated things: a character that stands alone
99
+ * unstressed, and one reduced *inside a word*. Where the field writes the same
100
+ * spelling both bare and toned it is reporting that split with no way to say
101
+ * which is which — 西 is `xi(902) xī(738)`, and the 902 are 东西 — and since the
102
+ * field leads {@link import("../sources/unihan.js").READING_FIELDS}, the
103
+ * reduction became the character's reading. 西 read `xi`, so 往西 was `wǎng xi`;
104
+ * 夫 read `fu`, 识 `shi`, 拾 `shi`, 候 `hou`, 姐 `jie`, 友 `you`.
105
+ *
106
+ * So a bare spelling the field also writes with a tone ranks below that twin —
107
+ * demoted rather than dropped, keeping it as a candidate without letting it set
108
+ * the default, exactly as a lone `kHanyuPinlu` reading is. It reaches 50
109
+ * characters, and {@link isNeutralAlone} holds back the ones a source says are
110
+ * neutral on their own.
111
+ *
112
+ * The other half of the same blind spot is already handled: where the field
113
+ * marks *no* tone at all it omitted the mark rather than meaning 轻声, which is
114
+ * {@link resolveFrequencyTones}.
115
+ */
116
+ export function demoteReducedNeutrals(unihan, readings) {
117
+ const frequency = unihan.fields.get(FREQUENCY_FIELD) ?? [];
118
+ const reduced = new Set(frequency.filter((reading) => !isToneMarked(reading) &&
119
+ frequency.some((other) => isToneMarked(other) && tonelessReading(other) === reading)));
120
+ if (reduced.size === 0) {
121
+ return readings;
122
+ }
123
+ return [
124
+ ...readings.filter((reading) => !reduced.has(reading)),
125
+ ...readings.filter((reading) => reduced.has(reading)),
126
+ ];
127
+ }
128
+ //# sourceMappingURL=frequency-tones.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"frequency-tones.js","sourceRoot":"","sources":["../../src/dictionary/frequency-tones.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,3 @@
1
+ import type { BuildAssertion } from "./built-dictionary.js";
2
+ export declare const INVENTORY_INVARIANTS: readonly BuildAssertion[];
3
+ //# sourceMappingURL=inventory-invariants.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"inventory-invariants.d.ts","sourceRoot":"","sources":["../../src/dictionary/inventory-invariants.ts"],"names":[],"mappings":"AAQA,OAAO,KAAK,EAAE,cAAc,EAAmB,MAAM,uBAAuB,CAAC;AAE7E,eAAO,MAAM,oBAAoB,EAAE,SAAS,cAAc,EAgDzD,CAAC"}
@@ -0,0 +1,54 @@
1
+ /**
2
+ * What must hold of every reading at once.
3
+ *
4
+ * Three sweeps: every syllable used is one the inventory knows, in a tone the
5
+ * inventory knows, and a reading is as long as the characters it reads.
6
+ */
7
+ import { characterCount } from "../script/characters.js";
8
+ import { DICTIONARY_SYLLABLES } from "../syllable/inventory.js";
9
+ export const INVENTORY_INVARIANTS = [
10
+ {
11
+ // Membership rather than a count. MERGE.md asked for "exactly 408 after the
12
+ // merge", which is the phrase corpus's own inventory — but the merged
13
+ // dictionary also carries Unihan's and CC-CEDICT's rare characters, whose
14
+ // readings are legitimately outside it (鞥 ēng, 覅 fiào, 挼 ruá). Fixing the
15
+ // count would either exclude those or bless whatever a refresh adds; naming
16
+ // the permitted set does neither.
17
+ description: "every syllable used is one the inventory knows",
18
+ check: (dictionary) => {
19
+ const unknown = [...dictionary.syllableInventory()].filter((syllable) => !DICTIONARY_SYLLABLES.has(syllable));
20
+ return unknown.length === 0
21
+ ? undefined
22
+ : `readings use ${String(unknown.length)} syllable(s) outside the inventory: ${unknown.join(", ")}`;
23
+ },
24
+ },
25
+ {
26
+ // The romanisation readers narrow an ambiguous spelling on the tone that
27
+ // was written — `lo²` is 羅 luó and not a 咯 that is only ever neutral —
28
+ // so a tone the table has never heard of is a syllable those readers will
29
+ // refuse to hand back. Regenerate `SYLLABLE_TONES` when this fails.
30
+ description: "every syllable is used in a tone the inventory knows",
31
+ check: (dictionary) => {
32
+ const unattested = [...dictionary.unattestedTones()];
33
+ return unattested.length === 0
34
+ ? undefined
35
+ : `readings use ${String(unattested.length)} syllable(s) in a tone the inventory does not list: ${unattested.join(", ")}`;
36
+ },
37
+ },
38
+ {
39
+ description: "every entry's syllable count matches its character count",
40
+ check: (dictionary) => {
41
+ for (const entry of dictionary.entries) {
42
+ const characters = characterCount(entry.hans);
43
+ const erhua = entry.readings.cn.filter((syllable) => syllable.erhua === true).length;
44
+ // Punctuation is written but unread, so it is allowed to have no
45
+ // syllable; a reading may therefore be shorter but never longer.
46
+ if (entry.readings.cn.length + erhua > characters) {
47
+ return `${entry.hans} has ${String(entry.readings.cn.length)} syllables for ${String(characters)} characters`;
48
+ }
49
+ }
50
+ return;
51
+ },
52
+ },
53
+ ];
54
+ //# sourceMappingURL=inventory-invariants.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"inventory-invariants.js","sourceRoot":"","sources":["../../src/dictionary/inventory-invariants.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,OAAO,EAAE,cAAc,EAAE,MAAM,yBAAyB,CAAC;AACzD,OAAO,EAAE,oBAAoB,EAAE,MAAM,0BAA0B,CAAC;AAGhE,MAAM,CAAC,MAAM,oBAAoB,GAA8B;IAC7D;QACE,4EAA4E;QAC5E,sEAAsE;QACtE,0EAA0E;QAC1E,0EAA0E;QAC1E,4EAA4E;QAC5E,kCAAkC;QAClC,WAAW,EAAE,gDAAgD;QAC7D,KAAK,EAAE,CAAC,UAA2B,EAAsB,EAAE;YACzD,MAAM,OAAO,GAAG,CAAC,GAAG,UAAU,CAAC,iBAAiB,EAAE,CAAC,CAAC,MAAM,CACxD,CAAC,QAAQ,EAAE,EAAE,CAAC,CAAC,oBAAoB,CAAC,GAAG,CAAC,QAAQ,CAAC,CAClD,CAAC;YACF,OAAO,OAAO,CAAC,MAAM,KAAK,CAAC;gBACzB,CAAC,CAAC,SAAS;gBACX,CAAC,CAAC,gBAAgB,MAAM,CAAC,OAAO,CAAC,MAAM,CAAC,uCAAuC,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC;QACxG,CAAC;KACF;IACD;QACE,yEAAyE;QACzE,uEAAuE;QACvE,0EAA0E;QAC1E,oEAAoE;QACpE,WAAW,EAAE,sDAAsD;QACnE,KAAK,EAAE,CAAC,UAA2B,EAAsB,EAAE;YACzD,MAAM,UAAU,GAAG,CAAC,GAAG,UAAU,CAAC,eAAe,EAAE,CAAC,CAAC;YACrD,OAAO,UAAU,CAAC,MAAM,KAAK,CAAC;gBAC5B,CAAC,CAAC,SAAS;gBACX,CAAC,CAAC,gBAAgB,MAAM,CAAC,UAAU,CAAC,MAAM,CAAC,uDAAuD,UAAU,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC;QAC9H,CAAC;KACF;IACD;QACE,WAAW,EAAE,0DAA0D;QACvE,KAAK,EAAE,CAAC,UAA2B,EAAsB,EAAE;YACzD,KAAK,MAAM,KAAK,IAAI,UAAU,CAAC,OAAO,EAAE,CAAC;gBACvC,MAAM,UAAU,GAAG,cAAc,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;gBAC9C,MAAM,KAAK,GAAG,KAAK,CAAC,QAAQ,CAAC,EAAE,CAAC,MAAM,CACpC,CAAC,QAAQ,EAAE,EAAE,CAAC,QAAQ,CAAC,KAAK,KAAK,IAAI,CACtC,CAAC,MAAM,CAAC;gBACT,iEAAiE;gBACjE,iEAAiE;gBACjE,IAAI,KAAK,CAAC,QAAQ,CAAC,EAAE,CAAC,MAAM,GAAG,KAAK,GAAG,UAAU,EAAE,CAAC;oBAClD,OAAO,GAAG,KAAK,CAAC,IAAI,QAAQ,MAAM,CAAC,KAAK,CAAC,QAAQ,CAAC,EAAE,CAAC,MAAM,CAAC,kBAAkB,MAAM,CAAC,UAAU,CAAC,aAAa,CAAC;gBAChH,CAAC;YACH,CAAC;YACD,OAAO;QACT,CAAC;KACF;CACF,CAAC"}
@@ -0,0 +1,40 @@
1
+ import type { DictionaryEntry } from "./entry.js";
2
+ /**
3
+ * Compounds whose constituent's 國語 reading must not be carried over.
4
+ *
5
+ * The composition below only fires where the compound reads its constituent
6
+ * exactly as that constituent's own entry does, which rules out most of the ways
7
+ * it could be wrong. What it cannot rule out is a homograph: two words spelled
8
+ * and read identically in 普通话, of which only one shifts in 國語. 相亲 is
9
+ * `xiāngqīn` either way when it means "mutually close" and `xiàngqīn` in Taiwan
10
+ * when it means a matchmaking meeting, and nothing in the data distinguishes the
11
+ * two senses.
12
+ *
13
+ * **Keep this small**, for the same reason
14
+ * {@link import("./overrides.js").READING_OVERRIDES} is kept small. Three
15
+ * exclusions against the 100 compounds the composition settles is the measured
16
+ * ratio; a list growing much past that would mean the alignment check has
17
+ * stopped carrying its weight and the rule itself needs revisiting.
18
+ */
19
+ export declare const LOCALE_COMPOSITION_EXCLUSIONS: readonly {
20
+ readonly word: string;
21
+ readonly reason: string;
22
+ }[];
23
+ /**
24
+ * Whether a compound can be asked what it is made of at all.
25
+ *
26
+ * A reading of one syllable per character is what lets a character span be cut
27
+ * out of the compound's reading and replaced. 儿化 folds two characters into one
28
+ * syllable and punctuation reads as none, so neither lines up and both are left
29
+ * alone.
30
+ */
31
+ export declare function isComposable(entry: DictionaryEntry): boolean;
32
+ /**
33
+ * Whether any delta-carrying word appears inside this one.
34
+ *
35
+ * A cheap filter ahead of the segmentation: only a few hundred words carry a
36
+ * delta, against 461,555 entries, and enumerating one word's substrings costs
37
+ * far less than segmenting it.
38
+ */
39
+ export declare function hasMarkedConstituent(word: string, marked: ReadonlySet<string>): boolean;
40
+ //# sourceMappingURL=locale-candidates.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"locale-candidates.d.ts","sourceRoot":"","sources":["../../src/dictionary/locale-candidates.ts"],"names":[],"mappings":"AASA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,YAAY,CAAC;AAElD;;;;;;;;;;;;;;;;GAgBG;AACH,eAAO,MAAM,6BAA6B,EAAE,SAAS;IACnD,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;CACzB,EAeA,CAAC;AASF;;;;;;;GAOG;AACH,wBAAgB,YAAY,CAAC,KAAK,EAAE,eAAe,GAAG,OAAO,CAQ5D;AAED;;;;;;GAMG;AACH,wBAAgB,oBAAoB,CAClC,IAAI,EAAE,MAAM,EACZ,MAAM,EAAE,WAAW,CAAC,MAAM,CAAC,GAC1B,OAAO,CAST"}
@@ -0,0 +1,77 @@
1
+ /**
2
+ * Which compounds the locale composition may be asked about at all.
3
+ *
4
+ * Three filters that between them cut 461,555 entries to a few hundred: the
5
+ * compound has to line up one syllable per character, it has to contain a word
6
+ * that carries a delta, and it must not be one of the homographs the data
7
+ * cannot tell apart.
8
+ */
9
+ import { toCharacters } from "../script/characters.js";
10
+ /**
11
+ * Compounds whose constituent's 國語 reading must not be carried over.
12
+ *
13
+ * The composition below only fires where the compound reads its constituent
14
+ * exactly as that constituent's own entry does, which rules out most of the ways
15
+ * it could be wrong. What it cannot rule out is a homograph: two words spelled
16
+ * and read identically in 普通话, of which only one shifts in 國語. 相亲 is
17
+ * `xiāngqīn` either way when it means "mutually close" and `xiàngqīn` in Taiwan
18
+ * when it means a matchmaking meeting, and nothing in the data distinguishes the
19
+ * two senses.
20
+ *
21
+ * **Keep this small**, for the same reason
22
+ * {@link import("./overrides.js").READING_OVERRIDES} is kept small. Three
23
+ * exclusions against the 100 compounds the composition settles is the measured
24
+ * ratio; a list growing much past that would mean the alignment check has
25
+ * stopped carrying its weight and the rule itself needs revisiting.
26
+ */
27
+ export const LOCALE_COMPOSITION_EXCLUSIONS = [
28
+ {
29
+ word: "相亲相爱",
30
+ reason: "相亲 here is 相 + 亲 in the reciprocal sense, `xiāngqīn`, not the matchmaking word that reads `xiàngqīn` in 國語.",
31
+ },
32
+ {
33
+ word: "腹背相亲",
34
+ reason: "The same reciprocal 相亲, so the same reading in both locales.",
35
+ },
36
+ {
37
+ word: "洋为中用",
38
+ reason: "中 is 中国 and 用 is its own verb: 洋为中用 is not built on the word 中用, which is what reads `zhòngyòng` in 國語.",
39
+ },
40
+ ];
41
+ /**
42
+ * The exclusions as a set, for the composition to consult.
43
+ */
44
+ const EXCLUDED = new Set(LOCALE_COMPOSITION_EXCLUSIONS.map((exclusion) => exclusion.word));
45
+ /**
46
+ * Whether a compound can be asked what it is made of at all.
47
+ *
48
+ * A reading of one syllable per character is what lets a character span be cut
49
+ * out of the compound's reading and replaced. 儿化 folds two characters into one
50
+ * syllable and punctuation reads as none, so neither lines up and both are left
51
+ * alone.
52
+ */
53
+ export function isComposable(entry) {
54
+ const characters = toCharacters(entry.hans);
55
+ return (characters.length > 2 &&
56
+ entry.readings.cn.length === characters.length &&
57
+ !EXCLUDED.has(entry.hans) &&
58
+ !EXCLUDED.has(entry.hant));
59
+ }
60
+ /**
61
+ * Whether any delta-carrying word appears inside this one.
62
+ *
63
+ * A cheap filter ahead of the segmentation: only a few hundred words carry a
64
+ * delta, against 461,555 entries, and enumerating one word's substrings costs
65
+ * far less than segmenting it.
66
+ */
67
+ export function hasMarkedConstituent(word, marked) {
68
+ const characters = toCharacters(word);
69
+ return characters.some((_, from) => {
70
+ let candidate = "";
71
+ return characters.slice(from).some((character) => {
72
+ candidate += character;
73
+ return candidate !== word && marked.has(candidate);
74
+ });
75
+ });
76
+ }
77
+ //# sourceMappingURL=locale-candidates.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"locale-candidates.js","sourceRoot":"","sources":["../../src/dictionary/locale-candidates.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AACH,OAAO,EAAE,YAAY,EAAE,MAAM,yBAAyB,CAAC;AAGvD;;;;;;;;;;;;;;;;GAgBG;AACH,MAAM,CAAC,MAAM,6BAA6B,GAGpC;IACJ;QACE,IAAI,EAAE,MAAM;QACZ,MAAM,EACJ,6GAA6G;KAChH;IACD;QACE,IAAI,EAAE,MAAM;QACZ,MAAM,EAAE,8DAA8D;KACvE;IACD;QACE,IAAI,EAAE,MAAM;QACZ,MAAM,EACJ,yGAAyG;KAC5G;CACF,CAAC;AAEF;;GAEG;AACH,MAAM,QAAQ,GAAwB,IAAI,GAAG,CAC3C,6BAA6B,CAAC,GAAG,CAAC,CAAC,SAAS,EAAE,EAAE,CAAC,SAAS,CAAC,IAAI,CAAC,CACjE,CAAC;AAEF;;;;;;;GAOG;AACH,MAAM,UAAU,YAAY,CAAC,KAAsB;IACjD,MAAM,UAAU,GAAG,YAAY,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;IAC5C,OAAO,CACL,UAAU,CAAC,MAAM,GAAG,CAAC;QACrB,KAAK,CAAC,QAAQ,CAAC,EAAE,CAAC,MAAM,KAAK,UAAU,CAAC,MAAM;QAC9C,CAAC,QAAQ,CAAC,GAAG,CAAC,KAAK,CAAC,IAAI,CAAC;QACzB,CAAC,QAAQ,CAAC,GAAG,CAAC,KAAK,CAAC,IAAI,CAAC,CAC1B,CAAC;AACJ,CAAC;AAED;;;;;;GAMG;AACH,MAAM,UAAU,oBAAoB,CAClC,IAAY,EACZ,MAA2B;IAE3B,MAAM,UAAU,GAAG,YAAY,CAAC,IAAI,CAAC,CAAC;IACtC,OAAO,UAAU,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,IAAI,EAAE,EAAE;QACjC,IAAI,SAAS,GAAG,EAAE,CAAC;QACnB,OAAO,UAAU,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,IAAI,CAAC,CAAC,SAAS,EAAE,EAAE;YAC/C,SAAS,IAAI,SAAS,CAAC;YACvB,OAAO,SAAS,KAAK,IAAI,IAAI,MAAM,CAAC,GAAG,CAAC,SAAS,CAAC,CAAC;QACrD,CAAC,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;AACL,CAAC"}
@@ -0,0 +1,47 @@
1
+ import type { DictionaryEntry } from "./entry.js";
2
+ /**
3
+ * One word of a segmentation, and where in the compound it falls.
4
+ */
5
+ export interface Segment {
6
+ readonly entry: DictionaryEntry;
7
+ readonly text: string;
8
+ /** First character covered. */
9
+ readonly from: number;
10
+ /** One past the last character covered. */
11
+ readonly to: number;
12
+ }
13
+ /**
14
+ * Every key an entry answers to, under either script.
15
+ */
16
+ export declare function keysOf(entry: DictionaryEntry): readonly string[];
17
+ /**
18
+ * A compound's constituent words, and the readings they carry.
19
+ *
20
+ * Indexed by every key an entry claims, so that a 繁體 headword segments into
21
+ * 繁體 constituents. Headwords are set first and never displaced, which is the
22
+ * same precedence the artifact and the build assertions use: 发 and 髮 both claim
23
+ * 发, and the entry the key names has to win.
24
+ */
25
+ export declare class ConstituentIndex {
26
+ #private;
27
+ /**
28
+ * Index entries by key, quantising their frequencies the way the decoder will.
29
+ */
30
+ constructor(entries: readonly DictionaryEntry[]);
31
+ /**
32
+ * What a key costs a segmentation that uses it.
33
+ */
34
+ costOf(key: string): number;
35
+ /**
36
+ * The likeliest way to cut a word into *other* dictionary words.
37
+ *
38
+ * The whole word is excluded from its own segmentation, which is the point:
39
+ * 垃圾分类 is a dictionary word, so a decoder handed the text would stop there
40
+ * and never ask what it is made of. This asks anyway.
41
+ *
42
+ * Returns undefined when no path of known words covers the word, which is
43
+ * common — most compounds contain a character no shorter word claims.
44
+ */
45
+ segment(word: string): readonly Segment[] | undefined;
46
+ }
47
+ //# sourceMappingURL=locale-segments.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"locale-segments.d.ts","sourceRoot":"","sources":["../../src/dictionary/locale-segments.ts"],"names":[],"mappings":"AAQA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,YAAY,CAAC;AAmBlD;;GAEG;AACH,MAAM,WAAW,OAAO;IACtB,QAAQ,CAAC,KAAK,EAAE,eAAe,CAAC;IAChC,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,+BAA+B;IAC/B,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,2CAA2C;IAC3C,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAC;CACrB;AAED;;GAEG;AACH,wBAAgB,MAAM,CAAC,KAAK,EAAE,eAAe,GAAG,SAAS,MAAM,EAAE,CAEhE;AAED;;;;;;;GAOG;AACH,qBAAa,gBAAgB;;IAI3B;;OAEG;IACH,YAAY,OAAO,EAAE,SAAS,eAAe,EAAE,EA4B9C;IA+BD;;OAEG;IACH,MAAM,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAG1B;IAED;;;;;;;;;OASG;IACH,OAAO,CAAC,IAAI,EAAE,MAAM,GAAG,SAAS,OAAO,EAAE,GAAG,SAAS,CA+BpD;CACF"}
@@ -0,0 +1,141 @@
1
+ /**
2
+ * Cutting a compound into the constituents a 國語 delta can be composed from.
3
+ *
4
+ * The segmentation the composition runs on: which pieces a word divides into,
5
+ * and what each of them costs, so that the division a reader would make is
6
+ * the one that wins.
7
+ */
8
+ import { toCharacters } from "../script/characters.js";
9
+ import { FrequencyTable } from "./frequency-table.js";
10
+ /**
11
+ * What each word in a segmentation costs on top of its frequency.
12
+ *
13
+ * The same charge, and for the same reason, as `READING_CHARGE` in
14
+ * `src/decode/lattice.ts`: it orders candidate segmentations by fewest words
15
+ * first and frequency second. That ordering is what decides 皮夹克 is 皮 + 夹克
16
+ * rather than 皮夹 + 克, which is the difference between leaving `pí jiákè`
17
+ * alone and mistaking it for the wallet 皮夹 that reads `pí jiá` in 國語.
18
+ *
19
+ * Duplicated rather than imported because the decoder sits above the dictionary
20
+ * and must not be depended on from inside it. The two are kept in step by
21
+ * `src/dictionary/locale.test.ts`, which asserts the segmentations this value
22
+ * produces rather than the value itself.
23
+ */
24
+ const WORD_CHARGE = 16;
25
+ /**
26
+ * Every key an entry answers to, under either script.
27
+ */
28
+ export function keysOf(entry) {
29
+ return [entry.hans, entry.hant, ...(entry.hantVariants ?? [])];
30
+ }
31
+ /**
32
+ * A compound's constituent words, and the readings they carry.
33
+ *
34
+ * Indexed by every key an entry claims, so that a 繁體 headword segments into
35
+ * 繁體 constituents. Headwords are set first and never displaced, which is the
36
+ * same precedence the artifact and the build assertions use: 发 and 髮 both claim
37
+ * 发, and the entry the key names has to win.
38
+ */
39
+ export class ConstituentIndex {
40
+ #byKey;
41
+ #cost;
42
+ /**
43
+ * Index entries by key, quantising their frequencies the way the decoder will.
44
+ */
45
+ constructor(entries) {
46
+ const byKey = new Map();
47
+ for (const entry of entries) {
48
+ byKey.set(entry.hans, entry);
49
+ }
50
+ for (const entry of entries) {
51
+ for (const form of keysOf(entry)) {
52
+ if (!byKey.has(form)) {
53
+ byKey.set(form, entry);
54
+ }
55
+ }
56
+ }
57
+ // Costs come from the same quantised table the artifact ships, so that a
58
+ // segmentation decided here is the one the decoder would have reached.
59
+ const table = FrequencyTable.build(entries.map((entry) => entry.frequency));
60
+ const byEntry = new Map();
61
+ for (const [at, entry] of entries.entries()) {
62
+ byEntry.set(entry, table.costOf(at));
63
+ }
64
+ const cost = new Map();
65
+ for (const [key, entry] of byKey) {
66
+ /* c8 ignore next -- every key was indexed from one of these entries */
67
+ cost.set(key, (byEntry.get(entry) ?? 0) + WORD_CHARGE);
68
+ }
69
+ this.#byKey = byKey;
70
+ this.#cost = cost;
71
+ }
72
+ /**
73
+ * Relax every word starting at one position, improving the costs it reaches.
74
+ *
75
+ * One step of the shortest-path scan, lifted out of its enclosing loop.
76
+ */
77
+ #relaxFrom(word, characters, from, best, previous) {
78
+ /* c8 ignore next -- the caller only relaxes from a position in range */
79
+ const reached = best[from] ?? Infinity;
80
+ let candidate = "";
81
+ for (let to = from; to < characters.length; to++) {
82
+ /* c8 ignore next -- the loop condition keeps the index in range */
83
+ candidate += characters[to] ?? "";
84
+ // The whole word is not a segmentation of itself.
85
+ const entry = candidate === word ? undefined : this.#byKey.get(candidate);
86
+ const total = reached + this.costOf(candidate);
87
+ /* c8 ignore next -- `to + 1` is at most `length`, which `best` holds */
88
+ if (entry !== undefined && total < (best[to + 1] ?? Infinity)) {
89
+ best[to + 1] = total;
90
+ previous[to + 1] = { entry, text: candidate, from, to: to + 1 };
91
+ }
92
+ }
93
+ }
94
+ /**
95
+ * What a key costs a segmentation that uses it.
96
+ */
97
+ costOf(key) {
98
+ /* c8 ignore next -- only asked about keys the index just returned */
99
+ return this.#cost.get(key) ?? WORD_CHARGE;
100
+ }
101
+ /**
102
+ * The likeliest way to cut a word into *other* dictionary words.
103
+ *
104
+ * The whole word is excluded from its own segmentation, which is the point:
105
+ * 垃圾分类 is a dictionary word, so a decoder handed the text would stop there
106
+ * and never ask what it is made of. This asks anyway.
107
+ *
108
+ * Returns undefined when no path of known words covers the word, which is
109
+ * common — most compounds contain a character no shorter word claims.
110
+ */
111
+ segment(word) {
112
+ const characters = toCharacters(word);
113
+ const length = characters.length;
114
+ const best = Array.from({ length: length + 1 }, () => Infinity);
115
+ const previous = Array.from({ length: length + 1 });
116
+ best[0] = 0;
117
+ for (let from = 0; from < length; from++) {
118
+ /* c8 ignore next -- the loop condition keeps the index in range */
119
+ if ((best[from] ?? Infinity) !== Infinity) {
120
+ this.#relaxFrom(word, characters, from, best, previous);
121
+ }
122
+ }
123
+ /* c8 ignore next -- `best` is built one longer than the word */
124
+ if ((best[length] ?? Infinity) === Infinity) {
125
+ return undefined;
126
+ }
127
+ const path = [];
128
+ let at = length;
129
+ while (at > 0) {
130
+ const step = previous[at];
131
+ /* c8 ignore next 3 -- a finite cost at `at` means a step reached it */
132
+ if (step === undefined) {
133
+ return undefined;
134
+ }
135
+ path.unshift(step);
136
+ at = step.from;
137
+ }
138
+ return path;
139
+ }
140
+ }
141
+ //# sourceMappingURL=locale-segments.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"locale-segments.js","sourceRoot":"","sources":["../../src/dictionary/locale-segments.ts"],"names":[],"mappings":"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"}
@@ -1,25 +1,5 @@
1
1
  import { type DictionaryEntry } from "./entry.js";
2
- /**
3
- * Compounds whose constituent's 國語 reading must not be carried over.
4
- *
5
- * The composition below only fires where the compound reads its constituent
6
- * exactly as that constituent's own entry does, which rules out most of the ways
7
- * it could be wrong. What it cannot rule out is a homograph: two words spelled
8
- * and read identically in 普通话, of which only one shifts in 國語. 相亲 is
9
- * `xiāngqīn` either way when it means "mutually close" and `xiàngqīn` in Taiwan
10
- * when it means a matchmaking meeting, and nothing in the data distinguishes the
11
- * two senses.
12
- *
13
- * **Keep this small**, for the same reason
14
- * {@link import("./overrides.js").READING_OVERRIDES} is kept small. Three
15
- * exclusions against the 100 compounds the composition settles is the measured
16
- * ratio; a list growing much past that would mean the alignment check has
17
- * stopped carrying its weight and the rule itself needs revisiting.
18
- */
19
- export declare const LOCALE_COMPOSITION_EXCLUSIONS: readonly {
20
- readonly word: string;
21
- readonly reason: string;
22
- }[];
2
+ export { LOCALE_COMPOSITION_EXCLUSIONS } from "./locale-candidates.js";
23
3
  /**
24
4
  * What the composition pass changed.
25
5
  */
@@ -1 +1 @@
1
- {"version":3,"file":"locale.d.ts","sourceRoot":"","sources":["../../src/dictionary/locale.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,KAAK,eAAe,EAAiB,MAAM,YAAY,CAAC;AAGjE;;;;;;;;;;;;;;;;GAgBG;AACH,eAAO,MAAM,6BAA6B,EAAE,SAAS;IACnD,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;CACzB,EAeA,CAAC;AA6PF;;GAEG;AACH,MAAM,WAAW,iBAAiB;IAChC,QAAQ,CAAC,OAAO,EAAE,SAAS,eAAe,EAAE,CAAC;IAC7C,4DAA4D;IAC5D,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;CAC3B;AAYD;;;;;;;;;;;;;;;;;;;;;;GAsBG;AACH,wBAAgB,mBAAmB,CACjC,OAAO,EAAE,SAAS,eAAe,EAAE,GAClC,iBAAiB,CA8DnB"}
1
+ {"version":3,"file":"locale.d.ts","sourceRoot":"","sources":["../../src/dictionary/locale.ts"],"names":[],"mappings":"AASA,OAAO,EAAE,KAAK,eAAe,EAAiB,MAAM,YAAY,CAAC;AAIjE,OAAO,EAAE,6BAA6B,EAAE,MAAM,wBAAwB,CAAC;AA6CvE;;GAEG;AACH,MAAM,WAAW,iBAAiB;IAChC,QAAQ,CAAC,OAAO,EAAE,SAAS,eAAe,EAAE,CAAC;IAC7C,4DAA4D;IAC5D,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;CAC3B;AAYD;;;;;;;;;;;;;;;;;;;;;;GAsBG;AACH,wBAAgB,mBAAmB,CACjC,OAAO,EAAE,SAAS,eAAe,EAAE,GAClC,iBAAiB,CA8DnB"}