Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: 英文词汇自动大写转换 #305

Merged
merged 3 commits into from
May 30, 2023
Merged

feat: 英文词汇自动大写转换 #305

merged 3 commits into from
May 30, 2023

Conversation

mirtlecn
Copy link
Collaborator

@mirtlecn mirtlecn commented May 28, 2023

利用候选词长度构造匹配规则,适配以所有大写英文开头的单词(解决 #303 所示代码潜在问题)。同时让代码整洁一点。

功能

单字符, 输入码小写,词组,大写词,非纯英文词 -> 候选项保持原样
SQL Server,APIs,VMware ==

输入码大写 + 小写 -> 候选项首字母大写
Ha -> Have, HAv -> Have

输入码全词大写 -> 候选项全词大写
HA -> HAVE, HAV -> HAVE

对于多大写字母开头的词,需要将它第一个小写字母大写
IMD -> IMDb, IMDB -> IMDB

问题:

暂时不能解决词汇中缩写形式的大写词汇,即在如下词库中:

Photoshop PS
Instagram IG
Instagram ins

本功能会导致 IG -> INSTAGRAM,INS -> INSTAGRAM

@iDvel
Copy link
Owner

iDvel commented May 28, 2023

我们可不可以弄一个简单暴力的规则:

说明 code text
输入小写,得到词库中的原样 latex LaTeX
输入首字母大写,得到首字母大写 Hello Hello
输入前2~n个字母大写,得到全大写 HEllo HELLO
同上,输入全大写,得到全大写 HELLO HELLO

这份规则对应的代码:(参考 #302 的简单修改)

local function autocap_filter(input, env)
    local code = env.engine.context.input -- 输入码
    for cand in input:iter() do
        local text = cand.text -- 候选词
        -- 输入码前 2~n 位大写,候选词转换为全大写
        if code:find("^%u%u+.*") then
            text = text:upper()
            yield(Candidate(cand.type, 0, #code, text, cand.comment))
        -- 输入码首位大写,候选词转换为首位大写
        elseif code:find("^%u.*") then
            text = text:sub(1, 1):upper() .. text:sub(2)
            yield(Candidate(cand.type, 0, #code, text, cand.comment))
        -- 输入码全小写,原样输出
        else
            yield(cand)
        end
    end
end

return autocap_filter

@mirtlecn
Copy link
Collaborator Author

我们可不可以弄一个简单暴力的规则:

说明 code text
输入小写,得到词库中的原样 latex LaTeX
输入首字母大写,得到首字母大写 Hello Hello
输入前2~n个字母大写,得到全大写 HEllo HELLO
同上,输入全大写,得到全大写 HELLO HELLO
这份规则对应的代码:(参考 #302 的简单修改)

local function autocap_filter(input, env)
    local code = env.engine.context.input -- 输入码
    for cand in input:iter() do
        local text = cand.text -- 候选词
        -- 输入码前 2~n 位大写,候选词转换为全大写
        if code:find("^%u%u+.*") then
            text = text:upper()
            yield(Candidate(cand.type, 0, #code, text, cand.comment))
        -- 输入码首位大写,候选词转换为首位大写
        elseif code:find("^%u.*") then
            text = text:sub(1, 1):upper() .. text:sub(2)
            yield(Candidate(cand.type, 0, #code, text, cand.comment))
        -- 输入码全小写,原样输出
        else
            yield(cand)
        end
    end
end

return autocap_filter

简单是简单,但似乎过于暴力了,还是在要在脚本判断不少其他情况:

  • 本身就以大写字母开头的词汇:用户输入 VM 应该对应 VMware,不能输入 VM -> VMWARE
  • 词组:词组不应该大写:输入 SSH,不应该出现 SECURE SHELL
  • 其它语言和英文混合词,:比如 ENdict词典,不应该出现 ENDICT 词典;
  • 特殊符号:EB 应该出现 E-Business,而不是 E-BUSINESS

@iDvel
Copy link
Owner

iDvel commented May 28, 2023

你说得对,有些缩写其实不适合转换。
image
image
image
image

目前这样应该是可以了,用一天看看。

This was referenced May 28, 2023
@mirtlecn
Copy link
Collaborator Author

mirtlecn commented May 29, 2023

一个潜在的性能问题:在 melt eng 定义的派生算法有些繁杂。在词库大的时候,部署时间非常长,生成 build 文件非常大。

我用了一个去重的 5mb 较全的英文词库,派生前 10 个大写,生成文件达到 80 mb,比几万个词的中文词库 bin 还要大。

我还是觉得输入全大写 -> 候选全大写,输入首字母大写 -> 候选首字母大写这样的逻辑通顺一点,还可以不修改派生算法,只要将 codeAllUCase 的判断改下就行:

-- ...
    elseif code == code:upper() then
         codeAllUCase = true
--...
        elseif codeAllUCase then
            text = text:upper()
            yield(Candidate(cand.type, 0, codeLen, text, cand.comment))
        -- 输入码首位大写,候选词转换为首位大写
        elseif codeUCase then
            text = text:sub(1, 1):upper() .. text:sub(2)
            yield(Candidate(cand.type, 0, codeLen, text, cand.comment))
        else
            yield(cand)

@mirtlecn
Copy link
Collaborator Author

还有一个问题。因为 candidate 构造候选词不写入用户词典,所以选择大写词不能动态调整词频。

简单研究了下要写入用户词典要用 Phrase,这样下来脚本就很繁琐了。

@iDvel
Copy link
Owner

iDvel commented May 30, 2023

目前英文词库很小,超大词库可以再只派生前俩大写或 lua 改成纯大写。
雾凇的配置就没启用英文方案调频,大写不能调频也没啥问题。
问题不大,先合并了。

@iDvel iDvel merged commit b6d3917 into iDvel:main May 30, 2023
@mirtlecn mirtlecn deleted the capfilter.lua branch May 30, 2023 14:19
@mirtlecn mirtlecn mentioned this pull request Jun 4, 2023
luckmoon pushed a commit to luckmoon/rime-ice that referenced this pull request Jun 8, 2023
示例:
输入小写,得到词库中的原样:latex → LaTeX
输入首字母大写,得到首字母大写:Hello → Hello
输入前2~n个字母大写,得到全大写:HEllo → HELLO
同上,输入全大写,得到全大写:HELLO → HELLO
ann61c pushed a commit to ann61c/rime-ice that referenced this pull request Jul 11, 2023
示例:
输入小写,得到词库中的原样:latex → LaTeX
输入首字母大写,得到首字母大写:Hello → Hello
输入前2~n个字母大写,得到全大写:HEllo → HELLO
同上,输入全大写,得到全大写:HELLO → HELLO
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants