@kensio/pinyinjs 1.7.5 → 1.7.6
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +128 -123
- package/data/full.entries +2595 -2595
- package/data/manifest.json +5 -5
- package/data/script.map +66 -3
- package/dist/decode/chang-context.d.ts +27 -0
- package/dist/decode/chang-context.d.ts.map +1 -0
- package/dist/decode/chang-context.js +66 -0
- package/dist/decode/chang-context.js.map +1 -0
- package/dist/decode/chang-rule.d.ts +37 -0
- package/dist/decode/chang-rule.d.ts.map +1 -0
- package/dist/decode/chang-rule.js +169 -0
- package/dist/decode/chang-rule.js.map +1 -0
- package/dist/decode/confidence.d.ts +11 -3
- package/dist/decode/confidence.d.ts.map +1 -1
- package/dist/decode/confidence.js +11 -3
- package/dist/decode/confidence.js.map +1 -1
- package/dist/decode/convert-pipeline.d.ts.map +1 -1
- package/dist/decode/convert-pipeline.js +2 -1
- package/dist/decode/convert-pipeline.js.map +1 -1
- package/dist/decode/de-rule.d.ts +54 -0
- package/dist/decode/de-rule.d.ts.map +1 -0
- package/dist/decode/de-rule.js +113 -0
- package/dist/decode/de-rule.js.map +1 -0
- package/dist/decode/hint-lattice.d.ts.map +1 -1
- package/dist/decode/hint-lattice.js +17 -3
- package/dist/decode/hint-lattice.js.map +1 -1
- package/dist/decode/jiao-rule.d.ts +9 -3
- package/dist/decode/jiao-rule.d.ts.map +1 -1
- package/dist/decode/jiao-rule.js +44 -5
- package/dist/decode/jiao-rule.js.map +1 -1
- package/dist/decode/lattice-types.d.ts +27 -8
- package/dist/decode/lattice-types.d.ts.map +1 -1
- package/dist/decode/lattice-types.js +27 -8
- package/dist/decode/lattice-types.js.map +1 -1
- package/dist/decode/polyphone-rules.d.ts +7 -27
- package/dist/decode/polyphone-rules.d.ts.map +1 -1
- package/dist/decode/polyphone-rules.js +7 -155
- package/dist/decode/polyphone-rules.js.map +1 -1
- package/dist/decode/reading-rules.d.ts +1 -29
- package/dist/decode/reading-rules.d.ts.map +1 -1
- package/dist/decode/reading-rules.js +4 -69
- package/dist/decode/reading-rules.js.map +1 -1
- package/dist/decode/run-words.d.ts +17 -0
- package/dist/decode/run-words.d.ts.map +1 -0
- package/dist/decode/run-words.js +29 -0
- package/dist/decode/run-words.js.map +1 -0
- package/dist/decode/sandhi-input.d.ts +30 -0
- package/dist/decode/sandhi-input.d.ts.map +1 -0
- package/dist/decode/sandhi-input.js +35 -0
- package/dist/decode/sandhi-input.js.map +1 -0
- package/dist/decode/sandhi-tones.d.ts +33 -5
- package/dist/decode/sandhi-tones.d.ts.map +1 -1
- package/dist/decode/sandhi-tones.js +59 -8
- package/dist/decode/sandhi-tones.js.map +1 -1
- package/dist/decode/sandhi.d.ts +9 -6
- package/dist/decode/sandhi.d.ts.map +1 -1
- package/dist/decode/sandhi.js +10 -7
- package/dist/decode/sandhi.js.map +1 -1
- package/dist/decode/write-run.d.ts +0 -7
- package/dist/decode/write-run.d.ts.map +1 -1
- package/dist/decode/write-run.js +4 -39
- package/dist/decode/write-run.js.map +1 -1
- package/dist/dictionary/cedict-senses.d.ts +7 -0
- package/dist/dictionary/cedict-senses.d.ts.map +1 -1
- package/dist/dictionary/cedict-senses.js +12 -0
- package/dist/dictionary/cedict-senses.js.map +1 -1
- package/dist/dictionary/constituent-repair.d.ts +36 -0
- package/dist/dictionary/constituent-repair.d.ts.map +1 -0
- package/dist/dictionary/constituent-repair.js +117 -0
- package/dist/dictionary/constituent-repair.js.map +1 -0
- package/dist/dictionary/merge-types.d.ts +8 -2
- package/dist/dictionary/merge-types.d.ts.map +1 -1
- package/dist/dictionary/merge-types.js.map +1 -1
- package/dist/dictionary/merge-walk.d.ts +27 -0
- package/dist/dictionary/merge-walk.d.ts.map +1 -0
- package/dist/dictionary/merge-walk.js +49 -0
- package/dist/dictionary/merge-walk.js.map +1 -0
- package/dist/dictionary/merge.d.ts +3 -3
- package/dist/dictionary/merge.d.ts.map +1 -1
- package/dist/dictionary/merge.js +18 -28
- package/dist/dictionary/merge.js.map +1 -1
- package/dist/dictionary/word-readings.d.ts.map +1 -1
- package/dist/dictionary/word-readings.js +3 -0
- package/dist/dictionary/word-readings.js.map +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +1 -1
- package/dist/index.js.map +1 -1
- package/package.json +2 -2
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"polyphone-rules.d.ts","sourceRoot":"","sources":["../../src/decode/polyphone-rules.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"polyphone-rules.d.ts","sourceRoot":"","sources":["../../src/decode/polyphone-rules.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AACH,OAAO,EAAE,gBAAgB,EAAE,MAAM,iBAAiB,CAAC;AACnD,OAAO,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC"}
|
|
@@ -1,159 +1,11 @@
|
|
|
1
|
-
export { PLAYING_TAN } from "./tan-rule.js";
|
|
2
|
-
import { wordEndingAt } from "./rules.js";
|
|
3
|
-
/**
|
|
4
|
-
* Whether a syllable is `cháng`, the stative reading of 长.
|
|
5
|
-
*/
|
|
6
|
-
function isChang(syllable) {
|
|
7
|
-
return (syllable?.initial === "ch" &&
|
|
8
|
-
syllable.final === "ang" &&
|
|
9
|
-
syllable.tone === 2);
|
|
10
|
-
}
|
|
11
|
-
/**
|
|
12
|
-
* Adverbs that measure a quality rather than modify an action.
|
|
13
|
-
*
|
|
14
|
-
* The discriminating side of the 长 context, and the reason the set is written
|
|
15
|
-
* out rather than taken from a tag: jieba calls 很 `zg` and 多 `m`, so the two
|
|
16
|
-
* commonest members are not adverbs as far as the dictionary is concerned,
|
|
17
|
-
* while 已经, 也, 却 and 就 — which sit in front of the *verb* 长 — are `d`
|
|
18
|
-
* along with the ones wanted here. The tag names the wrong set in both
|
|
19
|
-
* directions, so the set is named directly.
|
|
20
|
-
*
|
|
21
|
-
* Everything here is degree or comparison. 还 and 不 are deliberately absent
|
|
22
|
-
* even though 距离还长 and 那座桥不长 are both `cháng`: they modify verbs as
|
|
23
|
-
* readily as qualities, and 还长有毛 and 胡子不长在前额上 are the same two
|
|
24
|
-
* characters around the verb.
|
|
25
|
-
*/
|
|
26
|
-
const DEGREE = new Set([
|
|
27
|
-
"一样",
|
|
28
|
-
"十分",
|
|
29
|
-
"多",
|
|
30
|
-
"多么",
|
|
31
|
-
"好",
|
|
32
|
-
"如此",
|
|
33
|
-
"尽量",
|
|
34
|
-
"很",
|
|
35
|
-
"格外",
|
|
36
|
-
"极",
|
|
37
|
-
"极其",
|
|
38
|
-
"比较",
|
|
39
|
-
"略",
|
|
40
|
-
"相当",
|
|
41
|
-
"真",
|
|
42
|
-
"稍",
|
|
43
|
-
"稍微",
|
|
44
|
-
"越",
|
|
45
|
-
"越来越",
|
|
46
|
-
"这么",
|
|
47
|
-
"这样",
|
|
48
|
-
"那么",
|
|
49
|
-
"那样",
|
|
50
|
-
"更",
|
|
51
|
-
"最",
|
|
52
|
-
"有多",
|
|
53
|
-
"特别",
|
|
54
|
-
"老",
|
|
55
|
-
"够",
|
|
56
|
-
"挺",
|
|
57
|
-
"太",
|
|
58
|
-
"非常",
|
|
59
|
-
]);
|
|
60
|
-
/**
|
|
61
|
-
* What shows a 长 to be growing even with a degree word in front of it.
|
|
62
|
-
*
|
|
63
|
-
* {@link DEGREE} already excludes nearly everything that precedes the verb, so
|
|
64
|
-
* this only has to settle the three shapes reachable from both sets: 真长得很快
|
|
65
|
-
* and 越长得快, where 得 marks the complement; 长着, where the aspect does; and
|
|
66
|
-
* 越长越高, where the correlative makes the 长 the thing that increases.
|
|
67
|
-
*
|
|
68
|
-
* 了 and 的 are pointedly *not* here, and that is the whole use of conditioning
|
|
69
|
-
* on the adverb first. Following a bare 长 either would suggest the verb — 长了
|
|
70
|
-
* 一个大包, 长的很像 — but following an adverb and a 长 they are the sentence
|
|
71
|
-
* particle and the attributive: 时间太长了 and 很长的道路 are both `cháng`, and
|
|
72
|
-
* an earlier draft of this rule that guarded on them read both as `zhǎng`.
|
|
73
|
-
*/
|
|
74
|
-
const GROWING = new Set(["得", "着", "越"]);
|
|
75
1
|
/**
|
|
76
|
-
*
|
|
2
|
+
* The rules that settle a polyphone from the words around it.
|
|
77
3
|
*
|
|
78
|
-
*
|
|
79
|
-
*
|
|
80
|
-
*
|
|
81
|
-
*
|
|
4
|
+
* 弹 is `tán` or `dàn`, and which one a text means is a question about the
|
|
5
|
+
* neighbours rather than about the character. 长 is the same question and has
|
|
6
|
+
* a file of its own. The other rules in `reading-rules.ts` are about particles
|
|
7
|
+
* and 儿化, which is a different kind of evidence.
|
|
82
8
|
*/
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
* Whether an edge is the 越长 of a 越长越X saying something grew.
|
|
86
|
-
*
|
|
87
|
-
* This exists because of a defect in the sources rather than a gap in them.
|
|
88
|
-
* 越长 is a key, read `yuè cháng`, and it is the *only* one of its shape: 越大,
|
|
89
|
-
* 越高, 越好, 越快 and 越多 are all absent, so 越高越好 decodes as two words and
|
|
90
|
-
* 越长越高 reaches for a word nothing else in the paradigm has. It carries no
|
|
91
|
-
* part of speech, which is how the dictionary holds a reading somebody asserted
|
|
92
|
-
* rather than a word anybody counted — the same category {@link TEACHING_JIAO}
|
|
93
|
-
* declines to trust — and it comes from one source, `large_pinyin.txt`, with
|
|
94
|
-
* CC-CEDICT holding no such entry.
|
|
95
|
-
*
|
|
96
|
-
* Taking the edge away leaves the character's own default, which is `zhǎng`,
|
|
97
|
-
* and leaves `cháng` standing as a rival about one bucket dearer. That last
|
|
98
|
-
* part is the point of forbidding rather than forcing: 越长越X is genuinely
|
|
99
|
-
* ambiguous — 孩子越长越漂亮 grows and 头发越长越漂亮 lengthens, and only the
|
|
100
|
-
* subject says which — so the decode should answer with the likelier reading
|
|
101
|
-
* and still report itself as guessing. A forced edge could not.
|
|
102
|
-
*
|
|
103
|
-
* Unlike the rest of this file the shape has no corpus behind it: 越长 occurs
|
|
104
|
-
* three times in the 88,866 lines, and all three are 越来越长 or 说的越长. The
|
|
105
|
-
* word list is therefore small on purpose, and everything outside it is left as
|
|
106
|
-
* the sources have it.
|
|
107
|
-
*/
|
|
108
|
-
function isGrowthCorrelative(context) {
|
|
109
|
-
const { characters, edge } = context;
|
|
110
|
-
return (edge.text === "越长" &&
|
|
111
|
-
edge.partOfSpeech === "" &&
|
|
112
|
-
characters[edge.to] === "越" &&
|
|
113
|
-
GROWN_INTO.has(characters[edge.to + 1] ?? ""));
|
|
114
|
-
}
|
|
115
|
-
/**
|
|
116
|
-
* 长 read as `cháng` where an adverb of degree measures it.
|
|
117
|
-
*
|
|
118
|
-
* The character is stored `zhǎng` with `cháng` as an alternate, and the data
|
|
119
|
-
* says so about the character in isolation: Unihan ranks the readings
|
|
120
|
-
* `zhǎng(1879) cháng(1179)` by corpus count and names `zhǎng` in `kMandarin`.
|
|
121
|
-
* That ranking is doing real work — 署长, 团长, 公安局长, 总会长, 审理长 and
|
|
122
|
-
* the rest reach a bare 长 at the end of a title and read it correctly — so the
|
|
123
|
-
* default is not the thing to change. What is left over is the 长 that is an
|
|
124
|
-
* adjective, and nothing in the cost model can prefer an alternate at a
|
|
125
|
-
* position no word covers: 这篇文章不太长 came out `bú tài zhǎng`.
|
|
126
|
-
*
|
|
127
|
-
* The context that separates them is one-sided, as it was for the modal 得. A
|
|
128
|
-
* 长 that is *growing* is a verb, and a degree adverb cannot modify one — there
|
|
129
|
-
* is no 很长 meaning it grew a lot — so 很, 太, 最, 多 and their kin in front of
|
|
130
|
-
* a bare 长 make it the adjective. The other side carries almost nothing: what
|
|
131
|
-
* follows an adjectival 长 is a noun (很长时间), a particle (最长的大桥), or the
|
|
132
|
-
* end of the sentence (他的腿很长), which is also what follows half the verbs.
|
|
133
|
-
*
|
|
134
|
-
* Measured over the same 88,866 lines of Tatoeba and zh.wikipedia the other
|
|
135
|
-
* rules were sized against, 260 长 decode as a word of their own and this moves
|
|
136
|
-
* 75 of them to `cháng`, all 75 correctly. On CPP's 40 hand-labelled 长 it takes
|
|
137
|
-
* the character from 85.00% to 87.50%, fixing 时间最长 and breaking nothing.
|
|
138
|
-
*
|
|
139
|
-
* The other half of the rule is {@link GROWN_INTO}, which pushes the opposite
|
|
140
|
-
* way on the one shape the sources get wrong.
|
|
141
|
-
*/
|
|
142
|
-
export const ADJECTIVAL_CHANG = {
|
|
143
|
-
name: "adjectival-chang",
|
|
144
|
-
verdictFor: (context) => {
|
|
145
|
-
const { characters, edge } = context;
|
|
146
|
-
if (isGrowthCorrelative(context)) {
|
|
147
|
-
return "forbid";
|
|
148
|
-
}
|
|
149
|
-
if (edge.text !== "长" || !isChang(edge.reading[0])) {
|
|
150
|
-
return "keep";
|
|
151
|
-
}
|
|
152
|
-
if (GROWING.has(characters[edge.to] ?? "")) {
|
|
153
|
-
return "keep";
|
|
154
|
-
}
|
|
155
|
-
const before = wordEndingAt(context, edge.from);
|
|
156
|
-
return before !== undefined && DEGREE.has(before) ? "force" : "keep";
|
|
157
|
-
},
|
|
158
|
-
};
|
|
9
|
+
export { ADJECTIVAL_CHANG } from "./chang-rule.js";
|
|
10
|
+
export { PLAYING_TAN } from "./tan-rule.js";
|
|
159
11
|
//# sourceMappingURL=polyphone-rules.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"polyphone-rules.js","sourceRoot":"","sources":["../../src/decode/polyphone-rules.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"polyphone-rules.js","sourceRoot":"","sources":["../../src/decode/polyphone-rules.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AACH,OAAO,EAAE,gBAAgB,EAAE,MAAM,iBAAiB,CAAC;AACnD,OAAO,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC"}
|
|
@@ -1,34 +1,6 @@
|
|
|
1
|
+
export { MODAL_DE, PARTICLE_DE } from "./de-rule.js";
|
|
1
2
|
export { TEACHING_JIAO } from "./jiao-rule.js";
|
|
2
3
|
import { type EdgeRule } from "./rules.js";
|
|
3
|
-
/**
|
|
4
|
-
* 得 read as `děi` where it is a modal rather than a particle.
|
|
5
|
-
*
|
|
6
|
-
* One character, three readings, and the dictionary can only carry a default:
|
|
7
|
-
* 得 is stored `de` — the structural particle, which is far the commonest — with
|
|
8
|
-
* `dé` and `děi` as alternates. Nothing in the cost model can prefer an
|
|
9
|
-
* alternate at a position no word covers, so 我得走了 came out `wǒ de zǒule`
|
|
10
|
-
* and every other modal 得 with it. This is the case ROADMAP.md was waiting for
|
|
11
|
-
* before building stage 4: neither harness could see it, since the gold corpus
|
|
12
|
-
* had only 觉得 and CPP's 40 得 cases are labelled `dé` or `de` and never `děi`.
|
|
13
|
-
*
|
|
14
|
-
* The context is what separates the three, and only one side of it carries
|
|
15
|
-
* information. The particle 得 always follows the verb or adjective it attaches
|
|
16
|
-
* to (说得好, 跑得快, 累得要命), so a 得 with a *pronoun, adverb or time word*
|
|
17
|
-
* in front of it is not that particle. Requiring a verb phrase after it as well
|
|
18
|
-
* keeps 得了感冒 and 得了奖 — `dé`, and a real reading of the same character —
|
|
19
|
-
* out of it.
|
|
20
|
-
*
|
|
21
|
-
* Conditioning on what precedes rather than on what follows was measured, not
|
|
22
|
-
* assumed: "the word before is not a verb" fires 309 times over 88,866 lines of
|
|
23
|
-
* Tatoeba and zh.wikipedia and is wrong about four times in five, because
|
|
24
|
-
* jieba tags 下 as `f`, 学 as `n` and 飞 as nothing at all, and 雨下得很大 is a
|
|
25
|
-
* particle whatever the tag says. Naming the small closed set of things that
|
|
26
|
-
* can precede a modal is the same rule from the other side, and over the same
|
|
27
|
-
* text it fires 126 times and is right 122: the four misses are literary 得
|
|
28
|
-
* read `dé` after an adverb — 未必得喜悦, 暂得于己, 仅得约, 未得迁还家乡 —
|
|
29
|
-
* which nothing short of semantics separates from 必须得承认.
|
|
30
|
-
*/
|
|
31
|
-
export declare const MODAL_DE: EdgeRule;
|
|
32
4
|
/**
|
|
33
5
|
* 儿 does not stand on its own where the dictionary attests the 儿化.
|
|
34
6
|
*
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"reading-rules.d.ts","sourceRoot":"","sources":["../../src/decode/reading-rules.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"reading-rules.d.ts","sourceRoot":"","sources":["../../src/decode/reading-rules.ts"],"names":[],"mappings":"AAIA,OAAO,EAAE,QAAQ,EAAE,WAAW,EAAE,MAAM,cAAc,CAAC;AACrD,OAAO,EAAE,aAAa,EAAE,MAAM,gBAAgB,CAAC;AAE/C,OAAO,EAEL,KAAK,QAAQ,EAGd,MAAM,YAAY,CAAC;AAEpB;;;;;;;;;;;;;;;;;;;GAmBG;AACH,eAAO,MAAM,cAAc,EAAE,QAY5B,CAAC;AAsCF;;;;;;;;;;;;;;;;;;;;;;;;;;;GA2BG;AACH,eAAO,MAAM,eAAe,EAAE,QAuB7B,CAAC;AAIF,OAAO,EAAE,gBAAgB,EAAE,WAAW,EAAE,MAAM,sBAAsB,CAAC;AAErE;;GAEG;AACH,eAAO,MAAM,aAAa,EAAE,SAAS,QAAQ,EAQ5C,CAAC"}
|
|
@@ -1,76 +1,10 @@
|
|
|
1
1
|
import { QUANTITY_CHARACTERS } from "../numerals/characters.js";
|
|
2
|
+
import { MODAL_DE, PARTICLE_DE } from "./de-rule.js";
|
|
2
3
|
import { TEACHING_JIAO } from "./jiao-rule.js";
|
|
4
|
+
export { MODAL_DE, PARTICLE_DE } from "./de-rule.js";
|
|
3
5
|
export { TEACHING_JIAO } from "./jiao-rule.js";
|
|
4
6
|
import { toCharacters } from "../script/characters.js";
|
|
5
|
-
import { tagOf, wordEndingAt,
|
|
6
|
-
/**
|
|
7
|
-
* Whether a syllable is `děi`, the modal reading of 得.
|
|
8
|
-
*
|
|
9
|
-
* Compared structurally rather than by spelling it out, since a syllable is
|
|
10
|
-
* stored as its parts and writing one back is the formatting stage's job.
|
|
11
|
-
*/
|
|
12
|
-
function isDei(syllable) {
|
|
13
|
-
return (syllable?.initial === "d" && syllable.final === "ei" && syllable.tone === 3);
|
|
14
|
-
}
|
|
15
|
-
/**
|
|
16
|
-
* What stands in front of a modal 得: a subject, an adverb, or a time word.
|
|
17
|
-
*
|
|
18
|
-
* 我得走, 你就得去, 我今天得走. The particle 得 cannot follow any of these,
|
|
19
|
-
* because it attaches to the predicate it modifies — which is exactly what
|
|
20
|
-
* makes this the discriminating side of the context.
|
|
21
|
-
*/
|
|
22
|
-
const SUBJECT_TAGS = new Set(["r", "d", "t"]);
|
|
23
|
-
/**
|
|
24
|
-
* What follows a modal 得: the verb phrase it governs.
|
|
25
|
-
*
|
|
26
|
-
* Prepositions and adverbs are in because 我得在八月, 我得先走 and 我得快点 are
|
|
27
|
-
* all modal, and what follows the 得 in each is the front of a verb phrase
|
|
28
|
-
* rather than a verb.
|
|
29
|
-
*/
|
|
30
|
-
const GOVERNED_TAGS = /^(?:v|p|d|a)/u;
|
|
31
|
-
/**
|
|
32
|
-
* 得 read as `děi` where it is a modal rather than a particle.
|
|
33
|
-
*
|
|
34
|
-
* One character, three readings, and the dictionary can only carry a default:
|
|
35
|
-
* 得 is stored `de` — the structural particle, which is far the commonest — with
|
|
36
|
-
* `dé` and `děi` as alternates. Nothing in the cost model can prefer an
|
|
37
|
-
* alternate at a position no word covers, so 我得走了 came out `wǒ de zǒule`
|
|
38
|
-
* and every other modal 得 with it. This is the case ROADMAP.md was waiting for
|
|
39
|
-
* before building stage 4: neither harness could see it, since the gold corpus
|
|
40
|
-
* had only 觉得 and CPP's 40 得 cases are labelled `dé` or `de` and never `děi`.
|
|
41
|
-
*
|
|
42
|
-
* The context is what separates the three, and only one side of it carries
|
|
43
|
-
* information. The particle 得 always follows the verb or adjective it attaches
|
|
44
|
-
* to (说得好, 跑得快, 累得要命), so a 得 with a *pronoun, adverb or time word*
|
|
45
|
-
* in front of it is not that particle. Requiring a verb phrase after it as well
|
|
46
|
-
* keeps 得了感冒 and 得了奖 — `dé`, and a real reading of the same character —
|
|
47
|
-
* out of it.
|
|
48
|
-
*
|
|
49
|
-
* Conditioning on what precedes rather than on what follows was measured, not
|
|
50
|
-
* assumed: "the word before is not a verb" fires 309 times over 88,866 lines of
|
|
51
|
-
* Tatoeba and zh.wikipedia and is wrong about four times in five, because
|
|
52
|
-
* jieba tags 下 as `f`, 学 as `n` and 飞 as nothing at all, and 雨下得很大 is a
|
|
53
|
-
* particle whatever the tag says. Naming the small closed set of things that
|
|
54
|
-
* can precede a modal is the same rule from the other side, and over the same
|
|
55
|
-
* text it fires 126 times and is right 122: the four misses are literary 得
|
|
56
|
-
* read `dé` after an adverb — 未必得喜悦, 暂得于己, 仅得约, 未得迁还家乡 —
|
|
57
|
-
* which nothing short of semantics separates from 必须得承认.
|
|
58
|
-
*/
|
|
59
|
-
export const MODAL_DE = {
|
|
60
|
-
name: "modal-de",
|
|
61
|
-
verdictFor: (context) => {
|
|
62
|
-
const { edge } = context;
|
|
63
|
-
if (edge.text !== "得" || !isDei(edge.reading[0])) {
|
|
64
|
-
return "keep";
|
|
65
|
-
}
|
|
66
|
-
const before = wordEndingAt(context, edge.from);
|
|
67
|
-
const after = wordStartingAt(context, edge.to);
|
|
68
|
-
return SUBJECT_TAGS.has(tagOf(context, before)) &&
|
|
69
|
-
GOVERNED_TAGS.test(tagOf(context, after))
|
|
70
|
-
? "force"
|
|
71
|
-
: "keep";
|
|
72
|
-
},
|
|
73
|
-
};
|
|
7
|
+
import { tagOf, wordEndingAt, } from "./rules.js";
|
|
74
8
|
/**
|
|
75
9
|
* 儿 does not stand on its own where the dictionary attests the 儿化.
|
|
76
10
|
*
|
|
@@ -194,6 +128,7 @@ export { ADJECTIVAL_CHANG, PLAYING_TAN } from "./polyphone-rules.js";
|
|
|
194
128
|
*/
|
|
195
129
|
export const READING_RULES = [
|
|
196
130
|
MODAL_DE,
|
|
131
|
+
PARTICLE_DE,
|
|
197
132
|
TEACHING_JIAO,
|
|
198
133
|
ATTESTED_ERHUA,
|
|
199
134
|
COUNTED_MEASURE,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"reading-rules.js","sourceRoot":"","sources":["../../src/decode/reading-rules.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,mBAAmB,EAAE,MAAM,2BAA2B,CAAC;AAChE,OAAO,EAAE,
|
|
1
|
+
{"version":3,"file":"reading-rules.js","sourceRoot":"","sources":["../../src/decode/reading-rules.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Recutting a run's words for 分词连写.
|
|
3
|
+
*
|
|
4
|
+
* Grouping rewrites word boundaries and never the readings behind them, so the
|
|
5
|
+
* syllables — and the confidence beside them — survive it in order, and are
|
|
6
|
+
* simply cut in different places.
|
|
7
|
+
*/
|
|
8
|
+
import type { Dictionary } from "../dictionary/dictionary.js";
|
|
9
|
+
import type { ScoredWord } from "./word.js";
|
|
10
|
+
/**
|
|
11
|
+
* The words a Han run decodes to, with 分词连写 applied.
|
|
12
|
+
*
|
|
13
|
+
* Grouping rewrites word boundaries and never the readings behind them, so the
|
|
14
|
+
* syllables — and the confidence beside them — survive it in order.
|
|
15
|
+
*/
|
|
16
|
+
export declare function wordsOf(decoded: readonly ScoredWord[], dictionary: Dictionary, isGrouped: boolean): readonly ScoredWord[];
|
|
17
|
+
//# sourceMappingURL=run-words.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"run-words.d.ts","sourceRoot":"","sources":["../../src/decode/run-words.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AACH,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,6BAA6B,CAAC;AAE9D,OAAO,KAAK,EAAe,UAAU,EAAE,MAAM,WAAW,CAAC;AAEzD;;;;;GAKG;AACH,wBAAgB,OAAO,CACrB,OAAO,EAAE,SAAS,UAAU,EAAE,EAC9B,UAAU,EAAE,UAAU,EACtB,SAAS,EAAE,OAAO,GACjB,SAAS,UAAU,EAAE,CAUvB"}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import { applyGrouping } from "../orthography/grouping.js";
|
|
2
|
+
/**
|
|
3
|
+
* The words a Han run decodes to, with 分词连写 applied.
|
|
4
|
+
*
|
|
5
|
+
* Grouping rewrites word boundaries and never the readings behind them, so the
|
|
6
|
+
* syllables — and the confidence beside them — survive it in order.
|
|
7
|
+
*/
|
|
8
|
+
export function wordsOf(decoded, dictionary, isGrouped) {
|
|
9
|
+
return isGrouped
|
|
10
|
+
? regroup(decoded, applyGrouping(decoded.map((scored) => scored.word), dictionary))
|
|
11
|
+
: decoded;
|
|
12
|
+
}
|
|
13
|
+
/**
|
|
14
|
+
* Redistribute the decode's per-syllable confidence over regrouped words.
|
|
15
|
+
*
|
|
16
|
+
* 分词连写 moves word boundaries — 看 and 了 become 看了 — without touching a
|
|
17
|
+
* reading, so the run's syllables are the same syllables in the same order and
|
|
18
|
+
* are simply cut in different places.
|
|
19
|
+
*/
|
|
20
|
+
function regroup(decoded, grouped) {
|
|
21
|
+
const confidence = decoded.flatMap((scored) => [...scored.confidence]);
|
|
22
|
+
let at = 0;
|
|
23
|
+
return grouped.map((word) => {
|
|
24
|
+
const held = confidence.slice(at, at + word.reading.length);
|
|
25
|
+
at += word.reading.length;
|
|
26
|
+
return { word, confidence: held };
|
|
27
|
+
});
|
|
28
|
+
}
|
|
29
|
+
//# sourceMappingURL=run-words.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"run-words.js","sourceRoot":"","sources":["../../src/decode/run-words.ts"],"names":[],"mappings":"AAQA,OAAO,EAAE,aAAa,EAAE,MAAM,4BAA4B,CAAC;AAG3D;;;;;GAKG;AACH,MAAM,UAAU,OAAO,CACrB,OAA8B,EAC9B,UAAsB,EACtB,SAAkB;IAElB,OAAO,SAAS;QACd,CAAC,CAAC,OAAO,CACL,OAAO,EACP,aAAa,CACX,OAAO,CAAC,GAAG,CAAC,CAAC,MAAM,EAAE,EAAE,CAAC,MAAM,CAAC,IAAI,CAAC,EACpC,UAAU,CACX,CACF;QACH,CAAC,CAAC,OAAO,CAAC;AACd,CAAC;AAED;;;;;;GAMG;AACH,SAAS,OAAO,CACd,OAA8B,EAC9B,OAA+B;IAE/B,MAAM,UAAU,GAAG,OAAO,CAAC,OAAO,CAAC,CAAC,MAAM,EAAE,EAAE,CAAC,CAAC,GAAG,MAAM,CAAC,UAAU,CAAC,CAAC,CAAC;IACvE,IAAI,EAAE,GAAG,CAAC,CAAC;IACX,OAAO,OAAO,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE;QAC1B,MAAM,IAAI,GAAG,UAAU,CAAC,KAAK,CAAC,EAAE,EAAE,EAAE,GAAG,IAAI,CAAC,OAAO,CAAC,MAAM,CAAC,CAAC;QAC5D,EAAE,IAAI,IAAI,CAAC,OAAO,CAAC,MAAM,CAAC;QAC1B,OAAO,EAAE,IAAI,EAAE,UAAU,EAAE,IAAI,EAAE,CAAC;IACpC,CAAC,CAAC,CAAC;AACL,CAAC"}
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* What the sandhi pass needs from a decoded run, beyond the syllables.
|
|
3
|
+
*
|
|
4
|
+
* Two questions sandhi cannot answer from a reading alone. Third-tone sandhi
|
|
5
|
+
* applies inside a prosodic foot, so it has to be told where the words and
|
|
6
|
+
* their parts are. 一 sandhi asks what stands in front of the 一, and the answer
|
|
7
|
+
* is a character rather than a spelling. Both are things the decode knows and
|
|
8
|
+
* the syllable array does not.
|
|
9
|
+
*/
|
|
10
|
+
import type { Dictionary } from "../dictionary/dictionary.js";
|
|
11
|
+
import type { Syllable } from "../syllable/syllable.js";
|
|
12
|
+
import type { SandhiGrouping } from "./sandhi.js";
|
|
13
|
+
import type { ScoredWord } from "./word.js";
|
|
14
|
+
/**
|
|
15
|
+
* Where the words and their constituents fall, for third-tone sandhi.
|
|
16
|
+
*
|
|
17
|
+
* Undefined unless third-tone sandhi was asked for, since dividing a word costs
|
|
18
|
+
* dictionary lookups and nothing else reads the answer.
|
|
19
|
+
*/
|
|
20
|
+
export declare function groupingOf(dictionary: Dictionary, words: readonly ScoredWord[], readings: readonly (readonly Syllable[])[], isThirdTone: boolean): SandhiGrouping | undefined;
|
|
21
|
+
/**
|
|
22
|
+
* One 汉字 per syllable, where a word offers one.
|
|
23
|
+
*
|
|
24
|
+
* A word whose reading is a different length from its text — 玩儿 as `wánr` —
|
|
25
|
+
* has no character to give any one of its syllables, so its syllables get none
|
|
26
|
+
* and the pass falls back to their spellings. See
|
|
27
|
+
* {@link import("./sandhi-tones.js").isCounting}.
|
|
28
|
+
*/
|
|
29
|
+
export declare function charactersPerSyllable(words: readonly ScoredWord[], readings: readonly (readonly Syllable[])[]): readonly (string | undefined)[];
|
|
30
|
+
//# sourceMappingURL=sandhi-input.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"sandhi-input.d.ts","sourceRoot":"","sources":["../../src/decode/sandhi-input.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AACH,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,6BAA6B,CAAC;AAE9D,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,yBAAyB,CAAC;AAExD,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,aAAa,CAAC;AAClD,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,WAAW,CAAC;AAE5C;;;;;GAKG;AACH,wBAAgB,UAAU,CACxB,UAAU,EAAE,UAAU,EACtB,KAAK,EAAE,SAAS,UAAU,EAAE,EAC5B,QAAQ,EAAE,SAAS,CAAC,SAAS,QAAQ,EAAE,CAAC,EAAE,EAC1C,WAAW,EAAE,OAAO,GACnB,cAAc,GAAG,SAAS,CAQ5B;AAED;;;;;;;GAOG;AACH,wBAAgB,qBAAqB,CACnC,KAAK,EAAE,SAAS,UAAU,EAAE,EAC5B,QAAQ,EAAE,SAAS,CAAC,SAAS,QAAQ,EAAE,CAAC,EAAE,GACzC,SAAS,CAAC,MAAM,GAAG,SAAS,CAAC,EAAE,CAQjC"}
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
import { toCharacters } from "../script/characters.js";
|
|
2
|
+
import { divisionOf } from "./constituents.js";
|
|
3
|
+
/**
|
|
4
|
+
* Where the words and their constituents fall, for third-tone sandhi.
|
|
5
|
+
*
|
|
6
|
+
* Undefined unless third-tone sandhi was asked for, since dividing a word costs
|
|
7
|
+
* dictionary lookups and nothing else reads the answer.
|
|
8
|
+
*/
|
|
9
|
+
export function groupingOf(dictionary, words, readings, isThirdTone) {
|
|
10
|
+
if (!isThirdTone) {
|
|
11
|
+
return undefined;
|
|
12
|
+
}
|
|
13
|
+
return words.map((scored, index) => {
|
|
14
|
+
const reading = readings[index] ?? [];
|
|
15
|
+
return divisionOf(dictionary, scored.word.text, reading) ?? reading.length;
|
|
16
|
+
});
|
|
17
|
+
}
|
|
18
|
+
/**
|
|
19
|
+
* One 汉字 per syllable, where a word offers one.
|
|
20
|
+
*
|
|
21
|
+
* A word whose reading is a different length from its text — 玩儿 as `wánr` —
|
|
22
|
+
* has no character to give any one of its syllables, so its syllables get none
|
|
23
|
+
* and the pass falls back to their spellings. See
|
|
24
|
+
* {@link import("./sandhi-tones.js").isCounting}.
|
|
25
|
+
*/
|
|
26
|
+
export function charactersPerSyllable(words, readings) {
|
|
27
|
+
return words.flatMap((scored, index) => {
|
|
28
|
+
const reading = readings[index] ?? [];
|
|
29
|
+
const held = toCharacters(scored.word.text);
|
|
30
|
+
return held.length === reading.length
|
|
31
|
+
? held
|
|
32
|
+
: Array.from({ length: reading.length });
|
|
33
|
+
});
|
|
34
|
+
}
|
|
35
|
+
//# sourceMappingURL=sandhi-input.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"sandhi-input.js","sourceRoot":"","sources":["../../src/decode/sandhi-input.ts"],"names":[],"mappings":"AAUA,OAAO,EAAE,YAAY,EAAE,MAAM,yBAAyB,CAAC;AAEvD,OAAO,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAC;AAI/C;;;;;GAKG;AACH,MAAM,UAAU,UAAU,CACxB,UAAsB,EACtB,KAA4B,EAC5B,QAA0C,EAC1C,WAAoB;IAEpB,IAAI,CAAC,WAAW,EAAE,CAAC;QACjB,OAAO,SAAS,CAAC;IACnB,CAAC;IACD,OAAO,KAAK,CAAC,GAAG,CAAC,CAAC,MAAM,EAAE,KAAK,EAAE,EAAE;QACjC,MAAM,OAAO,GAAG,QAAQ,CAAC,KAAK,CAAC,IAAI,EAAE,CAAC;QACtC,OAAO,UAAU,CAAC,UAAU,EAAE,MAAM,CAAC,IAAI,CAAC,IAAI,EAAE,OAAO,CAAC,IAAI,OAAO,CAAC,MAAM,CAAC;IAC7E,CAAC,CAAC,CAAC;AACL,CAAC;AAED;;;;;;;GAOG;AACH,MAAM,UAAU,qBAAqB,CACnC,KAA4B,EAC5B,QAA0C;IAE1C,OAAO,KAAK,CAAC,OAAO,CAAC,CAAC,MAAM,EAAE,KAAK,EAAmC,EAAE;QACtE,MAAM,OAAO,GAAG,QAAQ,CAAC,KAAK,CAAC,IAAI,EAAE,CAAC;QACtC,MAAM,IAAI,GAAG,YAAY,CAAC,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QAC5C,OAAO,IAAI,CAAC,MAAM,KAAK,OAAO,CAAC,MAAM;YACnC,CAAC,CAAC,IAAI;YACN,CAAC,CAAC,KAAK,CAAC,IAAI,CAAqB,EAAE,MAAM,EAAE,OAAO,CAAC,MAAM,EAAE,CAAC,CAAC;IACjE,CAAC,CAAC,CAAC;AACL,CAAC"}
|
|
@@ -47,6 +47,28 @@ export declare const CONTINUES_NUMBER: Set<string>;
|
|
|
47
47
|
* The ordinal prefix 第.
|
|
48
48
|
*/
|
|
49
49
|
export declare const ORDINAL_PREFIX = "di";
|
|
50
|
+
/**
|
|
51
|
+
* The 汉字 {@link NUMERAL_WORDS} names, for a caller that has them.
|
|
52
|
+
*
|
|
53
|
+
* The spellings are ambiguous and the characters are not, which is the whole
|
|
54
|
+
* point of carrying both. 是 is spelt `shi` and stands in front of a 一 in
|
|
55
|
+
* 那是一条狗, 这是一个好主意 and several hundred sentences like them, and every
|
|
56
|
+
* one of them lost its sandhi to a 十 that was never there. 时, 事, 使 and 试 do
|
|
57
|
+
* the same.
|
|
58
|
+
*
|
|
59
|
+
* The 繁體 forms are here because a 繁體 text reaches this pass with 繁體
|
|
60
|
+
* characters. 拾, 佰 and 仟 are the 大写 banking forms, which appear on cheques
|
|
61
|
+
* and in contracts and count exactly as their everyday spellings do.
|
|
62
|
+
*/
|
|
63
|
+
export declare const NUMERAL_CHARACTERS: Set<string>;
|
|
64
|
+
/**
|
|
65
|
+
* The 汉字 {@link CONTINUES_NUMBER} names.
|
|
66
|
+
*/
|
|
67
|
+
export declare const CONTINUES_NUMBER_CHARACTERS: Set<string>;
|
|
68
|
+
/**
|
|
69
|
+
* The ordinal prefix as it is written.
|
|
70
|
+
*/
|
|
71
|
+
export declare const ORDINAL_CHARACTER = "\u7B2C";
|
|
50
72
|
/**
|
|
51
73
|
* Whether a 一 is counting something, which is the only time it takes sandhi.
|
|
52
74
|
*
|
|
@@ -60,10 +82,16 @@ export declare const ORDINAL_PREFIX = "di";
|
|
|
60
82
|
* is counting the ten.
|
|
61
83
|
* - **An ordinal.** 第一个 is `dìyī gè`.
|
|
62
84
|
*
|
|
63
|
-
* **
|
|
64
|
-
*
|
|
65
|
-
* tell 十 from 时 or 第 from
|
|
66
|
-
*
|
|
85
|
+
* **Answered from the characters wherever the caller has them**, and from the
|
|
86
|
+
* spellings where it does not. `pinyinjs sandhi shíyī gè` is handed nothing but
|
|
87
|
+
* pinyin, so there the pass still cannot tell 十 from 时 or 第 from 地 and
|
|
88
|
+
* `docs/sandhi/` carries what that costs. A conversion knows which 汉字 it read,
|
|
89
|
+
* and passing them along is what stops 那是一条狗 losing its sandhi to the 是 in
|
|
90
|
+
* front of the 一.
|
|
91
|
+
*
|
|
92
|
+
* The two sides are decided separately, because a run can know one and not the
|
|
93
|
+
* other: a word whose reading has a different syllable count from its character
|
|
94
|
+
* count has no character to offer for any one syllable.
|
|
67
95
|
*/
|
|
68
|
-
export declare function isCounting(syllables: readonly Syllable[], at: number): boolean;
|
|
96
|
+
export declare function isCounting(syllables: readonly Syllable[], at: number, characters?: readonly (string | undefined)[]): boolean;
|
|
69
97
|
//# sourceMappingURL=sandhi-tones.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"sandhi-tones.d.ts","sourceRoot":"","sources":["../../src/decode/sandhi-tones.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,OAAO,EAAE,KAAK,QAAQ,EAAyB,MAAM,yBAAyB,CAAC;AAC/E,OAAO,EAAgB,KAAK,IAAI,EAAE,MAAM,iBAAiB,CAAC;AAE1D;;GAEG;AACH,wBAAgB,IAAI,CAAC,QAAQ,EAAE,QAAQ,GAAG,OAAO,CAEhD;AAED;;GAEG;AACH,wBAAgB,IAAI,CAAC,QAAQ,EAAE,QAAQ,GAAG,OAAO,CAEhD;AAED;;;;;;GAMG;AACH,wBAAgB,YAAY,CAAC,SAAS,EAAE,IAAI,GAAG,SAAS,GAAG,IAAI,CAK9D;AAED;;;;;;;;;;;;GAYG;AACH,eAAO,MAAM,aAAa,aAAyC,CAAC;AAEpE;;;;;GAKG;AACH,eAAO,MAAM,gBAAgB,aAAsC,CAAC;AAEpE;;GAEG;AACH,eAAO,MAAM,cAAc,OAAO,CAAC;AAEnC
|
|
1
|
+
{"version":3,"file":"sandhi-tones.d.ts","sourceRoot":"","sources":["../../src/decode/sandhi-tones.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,OAAO,EAAE,KAAK,QAAQ,EAAyB,MAAM,yBAAyB,CAAC;AAC/E,OAAO,EAAgB,KAAK,IAAI,EAAE,MAAM,iBAAiB,CAAC;AAE1D;;GAEG;AACH,wBAAgB,IAAI,CAAC,QAAQ,EAAE,QAAQ,GAAG,OAAO,CAEhD;AAED;;GAEG;AACH,wBAAgB,IAAI,CAAC,QAAQ,EAAE,QAAQ,GAAG,OAAO,CAEhD;AAED;;;;;;GAMG;AACH,wBAAgB,YAAY,CAAC,SAAS,EAAE,IAAI,GAAG,SAAS,GAAG,IAAI,CAK9D;AAED;;;;;;;;;;;;GAYG;AACH,eAAO,MAAM,aAAa,aAAyC,CAAC;AAEpE;;;;;GAKG;AACH,eAAO,MAAM,gBAAgB,aAAsC,CAAC;AAEpE;;GAEG;AACH,eAAO,MAAM,cAAc,OAAO,CAAC;AAEnC;;;;;;;;;;;;GAYG;AACH,eAAO,MAAM,kBAAkB,aAS7B,CAAC;AAEH;;GAEG;AACH,eAAO,MAAM,2BAA2B,aAItC,CAAC;AAEH;;GAEG;AACH,eAAO,MAAM,iBAAiB,WAAM,CAAC;AAErC;;;;;;;;;;;;;;;;;;;;;;;GAuBG;AACH,wBAAgB,UAAU,CACxB,SAAS,EAAE,SAAS,QAAQ,EAAE,EAC9B,EAAE,EAAE,MAAM,EACV,UAAU,GAAE,SAAS,CAAC,MAAM,GAAG,SAAS,CAAC,EAAO,GAC/C,OAAO,CAwBT"}
|
|
@@ -56,6 +56,41 @@ export const CONTINUES_NUMBER = new Set([...NUMERAL_WORDS, "ling"]);
|
|
|
56
56
|
* The ordinal prefix 第.
|
|
57
57
|
*/
|
|
58
58
|
export const ORDINAL_PREFIX = "di";
|
|
59
|
+
/**
|
|
60
|
+
* The 汉字 {@link NUMERAL_WORDS} names, for a caller that has them.
|
|
61
|
+
*
|
|
62
|
+
* The spellings are ambiguous and the characters are not, which is the whole
|
|
63
|
+
* point of carrying both. 是 is spelt `shi` and stands in front of a 一 in
|
|
64
|
+
* 那是一条狗, 这是一个好主意 and several hundred sentences like them, and every
|
|
65
|
+
* one of them lost its sandhi to a 十 that was never there. 时, 事, 使 and 试 do
|
|
66
|
+
* the same.
|
|
67
|
+
*
|
|
68
|
+
* The 繁體 forms are here because a 繁體 text reaches this pass with 繁體
|
|
69
|
+
* characters. 拾, 佰 and 仟 are the 大写 banking forms, which appear on cheques
|
|
70
|
+
* and in contracts and count exactly as their everyday spellings do.
|
|
71
|
+
*/
|
|
72
|
+
export const NUMERAL_CHARACTERS = new Set([
|
|
73
|
+
"十",
|
|
74
|
+
"百",
|
|
75
|
+
"千",
|
|
76
|
+
"万",
|
|
77
|
+
"萬",
|
|
78
|
+
"拾",
|
|
79
|
+
"佰",
|
|
80
|
+
"仟",
|
|
81
|
+
]);
|
|
82
|
+
/**
|
|
83
|
+
* The 汉字 {@link CONTINUES_NUMBER} names.
|
|
84
|
+
*/
|
|
85
|
+
export const CONTINUES_NUMBER_CHARACTERS = new Set([
|
|
86
|
+
...NUMERAL_CHARACTERS,
|
|
87
|
+
"零",
|
|
88
|
+
"〇",
|
|
89
|
+
]);
|
|
90
|
+
/**
|
|
91
|
+
* The ordinal prefix as it is written.
|
|
92
|
+
*/
|
|
93
|
+
export const ORDINAL_CHARACTER = "第";
|
|
59
94
|
/**
|
|
60
95
|
* Whether a 一 is counting something, which is the only time it takes sandhi.
|
|
61
96
|
*
|
|
@@ -69,20 +104,36 @@ export const ORDINAL_PREFIX = "di";
|
|
|
69
104
|
* is counting the ten.
|
|
70
105
|
* - **An ordinal.** 第一个 is `dìyī gè`.
|
|
71
106
|
*
|
|
72
|
-
* **
|
|
73
|
-
*
|
|
74
|
-
* tell 十 from 时 or 第 from
|
|
75
|
-
*
|
|
107
|
+
* **Answered from the characters wherever the caller has them**, and from the
|
|
108
|
+
* spellings where it does not. `pinyinjs sandhi shíyī gè` is handed nothing but
|
|
109
|
+
* pinyin, so there the pass still cannot tell 十 from 时 or 第 from 地 and
|
|
110
|
+
* `docs/sandhi/` carries what that costs. A conversion knows which 汉字 it read,
|
|
111
|
+
* and passing them along is what stops 那是一条狗 losing its sandhi to the 是 in
|
|
112
|
+
* front of the 一.
|
|
113
|
+
*
|
|
114
|
+
* The two sides are decided separately, because a run can know one and not the
|
|
115
|
+
* other: a word whose reading has a different syllable count from its character
|
|
116
|
+
* count has no character to offer for any one syllable.
|
|
76
117
|
*/
|
|
77
|
-
export function isCounting(syllables, at) {
|
|
118
|
+
export function isCounting(syllables, at, characters = []) {
|
|
78
119
|
const spelt = (index) => {
|
|
79
120
|
const syllable = syllables[index];
|
|
80
121
|
return syllable === undefined ? "" : writeSyllableSpelling(syllable);
|
|
81
122
|
};
|
|
82
|
-
const before =
|
|
83
|
-
if (before ===
|
|
123
|
+
const before = characters[at - 1];
|
|
124
|
+
if (before === undefined
|
|
125
|
+
? spelt(at - 1) === ORDINAL_PREFIX
|
|
126
|
+
: before === ORDINAL_CHARACTER) {
|
|
84
127
|
return false;
|
|
85
128
|
}
|
|
86
|
-
|
|
129
|
+
if (before === undefined
|
|
130
|
+
? !NUMERAL_WORDS.has(spelt(at - 1))
|
|
131
|
+
: !NUMERAL_CHARACTERS.has(before)) {
|
|
132
|
+
return true;
|
|
133
|
+
}
|
|
134
|
+
const after = characters[at + 1];
|
|
135
|
+
return after === undefined
|
|
136
|
+
? CONTINUES_NUMBER.has(spelt(at + 1))
|
|
137
|
+
: CONTINUES_NUMBER_CHARACTERS.has(after);
|
|
87
138
|
}
|
|
88
139
|
//# sourceMappingURL=sandhi-tones.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"sandhi-tones.js","sourceRoot":"","sources":["../../src/decode/sandhi-tones.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,OAAO,EAAiB,qBAAqB,EAAE,MAAM,yBAAyB,CAAC;AAC/E,OAAO,EAAE,YAAY,EAAa,MAAM,iBAAiB,CAAC;AAE1D;;GAEG;AACH,MAAM,UAAU,IAAI,CAAC,QAAkB;IACrC,OAAO,QAAQ,CAAC,OAAO,KAAK,EAAE,IAAI,QAAQ,CAAC,KAAK,KAAK,GAAG,CAAC;AAC3D,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,IAAI,CAAC,QAAkB;IACrC,OAAO,QAAQ,CAAC,OAAO,KAAK,GAAG,IAAI,QAAQ,CAAC,KAAK,KAAK,GAAG,CAAC;AAC5D,CAAC;AAED;;;;;;GAMG;AACH,MAAM,UAAU,YAAY,CAAC,SAA2B;IACtD,IAAI,SAAS,KAAK,SAAS,IAAI,SAAS,KAAK,YAAY,EAAE,CAAC;QAC1D,OAAO,CAAC,CAAC;IACX,CAAC;IACD,OAAO,SAAS,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;AACjC,CAAC;AAED;;;;;;;;;;;;GAYG;AACH,MAAM,CAAC,MAAM,aAAa,GAAG,IAAI,GAAG,CAAC,CAAC,KAAK,EAAE,KAAK,EAAE,MAAM,EAAE,KAAK,CAAC,CAAC,CAAC;AAEpE;;;;;GAKG;AACH,MAAM,CAAC,MAAM,gBAAgB,GAAG,IAAI,GAAG,CAAC,CAAC,GAAG,aAAa,EAAE,MAAM,CAAC,CAAC,CAAC;AAEpE;;GAEG;AACH,MAAM,CAAC,MAAM,cAAc,GAAG,IAAI,CAAC;AAEnC
|
|
1
|
+
{"version":3,"file":"sandhi-tones.js","sourceRoot":"","sources":["../../src/decode/sandhi-tones.ts"],"names":[],"mappings":"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"}
|