:::

線上中文斷詞工具:Jieba-JS / Online Chinese Analyzer: Jieba-JS

image

現在最流行的中文斷詞工具結巴(jieba)原本是以Python開發,必須要有Python的環境才能運作。不過它也有很多不同程式語言的版本,其中最好用的就是不需要安裝、只要瀏覽器就能夠執行的JavaScript版本:Jieba-JS。我把Jeiba-JS專案fork了一份:jieba-js,並加入了可以讓其他程式碼直接引用的方法。這樣在任何網頁上都可以輕易實作斷詞功能了。


Jieba-JS原始碼 / Repository

image

我把原始碼都放在GitHub上:

有需要的人可以直接下載:

或著用下面的方法,直接引用函式庫來斷詞。

使用方法 / Usage

布丁的Jeiba-JS使用的時候需要引用require-jieba-js.js檔案:

然後使用以下函式來呼叫:

call_jieba_cut(_text, _callback);

範例程式碼來說:

<script src="https://pulipulichen.github.io/jieba-js/require-jieba-js.js"></script>

<script>
_text = "這個布丁是在無聊的世界中找尋樂趣的一種不能吃的食物,喜愛動漫畫、遊戲、程式,以及跟世間脫節的生活步調。";
call_jieba_cut(_text, function (_result) {
  console.log(_result);
});
</script>

最後會在瀏覽器的console呈現斷詞結果:

image

斷詞的結果是:

["這個", "布丁", "是", "在", "無聊", "的", "世界", "中", "找尋", "樂趣", "的", "一種", "不能", "吃", "的", "食物", ",", "喜愛", "動漫畫", "、", "遊戲", "、", "程式", ",", "以及", "跟", "世間", "脫節", "的", "生活", "步調", "。"]

自訂詞庫設定 / Cutom Dictionary

Jieba允許大家自訂詞庫,我也在Jieba-JS中擴充了這個功能。

dict_custom.js是自訂詞庫的範例檔案,內容如下:

_custom_dict = [
  ["漫畫", 99999999, "n"],
];


// 引用設定檔案,以下不用變更
if (typeof(define) === "function") {
    define(function (require) {
        return _custom_dict;
    });
}
else {
    module.exports = _custom_dict;
}

詞庫是由多個詞彙組成,每個詞彙設定有三個欄位:

  • 詞:例如「漫畫」
  • 斷詞權重:要設很大才能蓋過原本的斷詞權重,如「99999999」。
  • 詞性標記:例如名詞「n」。Jieba的詞性列表請看「词的分类」這篇的內容。

在Jieba-JS中要使用自訂詞庫的話,用法如下:

call_jieba_cut(_text, _custom_dict, _callback);

示範用法如下:

var _text = "這個布丁是在無聊的世界中找尋樂趣的一種不能吃的食物,喜愛動漫畫、遊戲、程式,以及跟世間脫節的生活步調。";
var _custom_dict = "https://github.com/pulipulichen/jieba-js/blob/master/scripts/data/dict_custom.js";
call_jieba_cut(_text, _custom_dict, function (_result) {
  console.log(_result);
});

載入自訂詞庫之後,斷詞結果會有些變化:

image

原本「動漫畫」被視為一個詞,現在被斷開成為「動」跟「漫畫」了。

Node.js版本 / Use Jieba-JS in Node.js

image

我們也可以在Node.js上執行Jieba-JS。做法請參考node.js這個檔案,內容如下,運作結果如上圖:

require('../scripts/main.js');

_text = "這個布丁是在無聊的世界中找尋樂趣的一種不能吃的食物,喜愛動漫畫、遊戲、程式,以及跟世間脫節的生活步調。";

dict1 = require('../scripts/data/dictionary.js');
dict2 = require('../scripts/data/dict_custom.js');

node_jieba_parsing([dict1, dict2], _text, function (_result) {
    console.log(_result.join(" "));
});

線上展示 / Online Demo

你可以直接使用上面的網頁直接斷詞,不用再安裝其他工具了。


結語 / In closing

我開始研究Jieba-JS的理由很簡單,因為我只是想找一個免安裝的斷詞工具而已。雖然CKIP有提供線上展示服務,但是那並不是一個JavaScript工具,不好客製化。而且CKIP的詞庫是以Big5為主,一些特殊的文字是沒辦法辨識的。

另一方面,現在中文斷詞最主流的Jieba雖然也很多程式語言,也大多提供線上展示的連結,像是原始Python版的 http://jiebademo.ap01.aws.af.cm/ 或 PHP版的 http://jieba-php.fukuball.com/ ,但是也因為是伺服器端的語言,使用上並沒有這麼便利。

找著找著,沒想到Jieba真的有不用安裝的JavaScript版本,我就這樣子做了一個真正免安裝的「線上展示斷詞工具」了。這個工具並不是在伺服器端運作,而是完全在使用者端的瀏覽器運作。雖然運作速度比較慢一點,但是這樣我就幾乎不需要擔心伺服器當機的問題,非常好用。

除了解決了線上展示的問題之外,Jieba-JS也解決了另一個問題:Node.js難以安裝結巴斷詞器的問題。Node.js在Windows中要使用Jieba的話,必須要先安裝Python,然後在作業系統上編譯Jieba所需要的檔案,最後才能使用Jieba斷詞。但是這個安裝過程非常地困難,時常遭遇問題,可以看NodeJieba Readme.me中的「NodeJieba 在 Windows 上面的一系列安装问题和斗争成功过程参考」。

不過現在有Jieba-JS這樣的JavaScript函式庫之後,就不需要再去煩惱NodeJieba編譯的問題,可以在Node.js中直接使用Jieba-JS來斷詞。

希望這個程式幫得上大家的忙,一起來做中文文本分析吧。

總共33 則留言 ( 我要發問 , 隱藏留言 顯示留言 )

  1. 範例用ie開好像不行耶 會一直停在處理中

    回覆刪除
  2. 您好,想請問大大一個問題,要如何實現詞性標註

    例如這樣(github上的文件說明)的結果

    var nodejieba = require("nodejieba");
    console.log(nodejieba.tag("红掌拨清波"));
    //[ { word: '红掌', tag: 'n' },
    // { word: '拨', tag: 'v' },
    // { word: '清波', tag: 'n' } ]

    辛苦大大的整理了

    回覆刪除
    回覆
    1. 你好,

      呃,我不是用nodejieba,用的是jieba-js,所以你那個github上的文件說明是不一樣的

      https://github.com/pulipulichen/jieba-js/blob/master/scripts/main.js
      請自行研究程式碼,關鍵可能是這一個?我也不太清楚

      刪除
  3. 因為最近有斷詞的需求,所以我改進了線上斷詞器的使用介面:
    https://lh3.googleusercontent.com/-E-sJdliqHr4/Wuv_F78OXuI/AAAAAAADuKg/8mu_9S6E6HEh6qZYzz2EEd5ecPgBwl1mgCHMYCw/s0/2018-05-04_14-34-53.png
    改良功能如下:
    - 加入使用者詞典、停用字功能
    - 使用者詞典與停用字皆有範例檔。停用字的範例來自於stopwords-iso
    * Chinese stopwords https://github.com/stopwords-iso/stopwords-zh
    * English stopwords https://github.com/stopwords-iso/stopwords-en
    - 各個欄位加入檔案上傳、下載、複製到剪貼簿的功能

    我本來希望加入詞性標註跟斷詞模式中的搜尋引擎模式,這兩種功能對於文本分類、擷取特徵來說非常重要。可惜jieba-js專案並沒有實作這些功能,我也不太可能從頭去做這樣的工具出來,可能還是要用伺服器端的Python或Node.js來實作吧。線上斷詞器應該就只能先做到這裡了。

    回覆刪除
  4. 您好
    是否在IE尚無法正常使用?我在Chrome上可以正常顯示,但是也會出現
    Uncaught Error: No define call for main
    http://requirejs.org/docs/errors.html#nodefine
    at A (require.js:8)
    at Object.completeLoad (require.js:28)
    at HTMLScriptElement.onScriptLoad (require.js:29)
    這個錯誤

    回覆刪除
    回覆
    1. To Unknow:

      1. IE無法執行,請使用Chrome。

      2. require.js有錯誤訊息,但可以忽視,程式仍然可以正常執行。

      刪除
    2. To 布丁大大
      謝謝您給的建議,不過我可能需要IE可以運作,我在想辦法看看
      謝謝

      刪除
  5. 大大您好
    你的範例輸出結果會把前面“這個”砍掉耶?
    那是正常的嗎?
    我是有在下面Stop word看到“這個”有存進去啦
    抱歉我可能不太懂他的運行原理@@

    回覆刪除
    回覆
    1. To Danny Hwang,

      Stop words表示會被過濾掉的停用字
      所以「這個」在Stop words中,表示他不會出現在斷詞結果裡。

      反過來說,如果你把Stop words中拿掉「這個」
      他就會出現在斷詞結果中了

      刪除
  6. To 布丁大大你好
    最近因為要資料分析的關係再用您的這個系統,但我發現網頁上上傳自訂字典,但重新斷字結果不是我要的@@?
    請問這個部分我哪裡要修正嗎?我是下載上面的text檔新增如下
    找尋樂趣,9999999,n
    無聊的世界,9999999,n
    然後再按開始斷詞,但結果不是我要的
    我目前因為分析是要給專門領域使用,所以希望可以動態修改字典,省去複雜的操作(畢竟要給非資訊專業的老師們用)
    想請問這部分我可以怎麼解決呢?
    另外我是HTME和js新手,所以有可能是我程式上面有錯,還謝謝布丁大大把問題看到這邊~

    回覆刪除
    回覆
    1. To 遊戲狼,

      這是因為我程式只有在讀取網頁初始化的時候才讀取自訂詞典。後來改進了,只要有變更自訂詞典,程式就會重新初始化,這樣子就能夠正確使用自訂詞典了。

      刪除
  7. 謝謝您的協助!!!
    目前直接下載您的檔案可以達到我要的效果,真的非常感謝!!
    但因為我喜歡了解程式用法,以利後面在使用時比較能自己修改,所以想問:
    1.請問是要用$(function ()...這個方式先執行過程式,才能成功運行嗎?
    我有試過這樣https://jsbin.com/yofalen/edit.但結果不會是我的字典,希望大大能講解這之中的原因
    2.如果不需要馬上讀取使用的話,我想問我這個問題要怎麼改才好呢?
    我希望網頁一開始不要執行,因為我不知道後續動態自訂字典會有多大,怕會一開始就影響到
    以上問題希望有幸能讓布丁大大抽空指導,謝謝m(_ _)m

    回覆刪除
    回覆
    1. To 遊戲狼,

      問題1:
      建議你fork我的repo再去修改,jsbin上可能會有什麼額外的限制,我不確定。

      fork的用法:https://git-scm.com/book/zh-tw/v2/GitHub-%E5%8F%83%E8%88%87%E4%B8%80%E5%80%8B%E5%B0%88%E6%A1%88

      問題2:
      取消網頁載入後就點選按鈕的指令就好了

      用註解幫你標示出來了
      https://github.com/pulipulichen/jieba-js/blob/master/index.html#L194
      fort我的repo,自行改改看吧。

      有什麼建議可以用pull request傳送合併請求
      加油

      刪除
  8. 網頁版的斷詞工具雖然用起來很簡單,如果要一口氣處理大量文件的話,我比較推薦另一篇的工具 Python-Jieba
    http://blog.pulipuli.info/2019/01/python-jieba-word-segmentation-and-part.html
    請根據需求來決定要用那個工具吧

    回覆刪除
  9. Jieba-JS前端介面更新囉
    現在把輸入輸出、以及設定的介面拆開了

    輸入輸出之後,可以接到繪製文字雲、文本分析、主題分析的工具
    http://4.bp.blogspot.com/-y8swiHm6qjU/XrdzV-ZblFI/AAAAAAAEpF4/vME37JyEXS4sN3tzlS6T6EPxuUJ16AEwgCK4BGAYYCw/s1600/2020-05-10_111957.png

    設定加上了詞幹分析(stemming),也修正了n-gram分析中英文混雜文字時的問題
    http://1.bp.blogspot.com/-SLCUp5nbsVY/XrdzV_dAp-I/AAAAAAAEpF0/LkJd5_p57VUdmvdY37jbEfcVsexHPTr8QCK4BGAYYCw/s1600/2020-05-10_112019.png

    做一下記錄

    回覆刪除
  10. 您好
    我在使用線上斷詞的時候
    突然無法使用並一直在跑進度條
    請問線上斷詞有維修時間嗎
    謝謝

    回覆刪除
    回覆
    1. 您好,

      這是純瀏覽器端的工具,跟伺服器沒有關係。
      如果程式不能運作,請嘗試清除瀏覽器快取後再試試看。

      不然就是您先拿比較短的文字來試著斷詞看看能不能運作。
      如果可以,再試試看比較長的文字。

      如果都不行,您可以把有問題的文字放上來,我有空會再來修

      https://upload.express/
      這是上傳短期暫存檔案的網站,供您參考

      刪除
  11. https://jsfiddle.net/7pd9e0fz/3/

    想請教一下, 這段CODE 可以在PC上運行成功, 但在手機上的Chrome Safari 也會顯示script error
    請問我可以怎解決,
    因為在寫一個網站, 但手機上會卡在這步.

    回覆刪除
    回覆
    1. 您好,

      不,您上面那段網址的程式碼是不能運作的
      JSFiddle把程式碼分的很開

      我改寫了你原本的程式碼,這樣就能順利運作
      https://jsfiddle.net/zqvw723g/3/
      主要是幾個需要引用的網址都移到左邊的「Resources」裡面去設定

      最後可以跑得出結果
      我測試過Windows的Chrome以及Android的Chrome
      兩者都可以

      您再確認一下,好嗎?

      刪除
    2. 你好, 感謝回覆, 我手上只有iphone, 我剛剛和另一個使用iphone使用者也測試過, 的確在iphone上的Chrome和Safari 也用不到
      在console 中會顯示
      "沒有資料"
      "Script error."
      "Script error."
      "Script error."

      刪除
    3. 我手邊沒有iPhone裝置,剩下的請您自行想辦法了

      刪除
  12. 網誌管理員已經移除這則留言。

    回覆刪除
  13. 想請教布丁大,會有機會出,如何寫停用詞方法嗎?謝謝

    回覆刪除
    回覆
    1. 您好,

      1. 開啟Jieba JS
      https://pulipulichen.github.io/jieba-js/

      2. 點選右上角的「Configuration」
      https://blogger.googleusercontent.com/img/a/AVvXsEhuG4815zRPTVAOPa9_rN0uRwfe3qkXgM178uPu1gSQdnOdwCbpF22R59Rc1l3MfnNa53Lzihhn6hJDvr9TygXPbXC5CcfRk5g0LG99hkqe7QZJVVm2P0R-Yf0aMMFXLXw1S_tnaiTv6Mv_fGPGmdYjKK_jeuyHcdAs_5xBEHti0zZ8E0b8Phw

      3. 停用詞功能「Stop Words」在最下面
      https://blogger.googleusercontent.com/img/a/AVvXsEghHh8y1-a2ahSV4_9pnvda_9ojVLEBhPIr4WNlS9vFD5ZbLfbANwreLbof6hiBOzOR96nJICayAu2qpPlpXGWO-FfwBO8-yhc2g3en0JwXH53Prt9WWiPFKxvRf1qOTumhbPvHQOn09aiHop5qeLJ6MG0a6fWa9c5qPtzyTQ52zC836GWbvkw

      刪除
  14. 布丁大您好,想詢問的是停用詞的寫法,小弟公司最近要寫jieba-js斷字,小弟研究過大大您的github還是不了解如何使用,故想詢問大大停用詞寫法。

    回覆刪除
    回覆
    1. 您好,

      嗯...看起來,您是要自己寫程式來處理斷詞的問題。

      如果是Node.js的純程式的話,我的博士論文使用的是novel-segment
      https://www.npmjs.com/package/novel-segment

      加入停用字的寫法是:
      segment.loadStopwordDict('stopword.txt');

      stopword.txt的內容例如:
      之所以
      因為

      這樣就可以了。

      至於要不要用Jieba-JS嘛...
      有其他寫得更好的套件,我就不強求Jieba-JS要做多好了。

      刪除
    2. 感謝布丁大,小弟再研究看看,感謝您

      刪除
    3. 不好意思,想再詢問布丁大,VS2017 該如何安裝novel-segment呢,我使用NuGet 安裝無法安裝,我將github(novel-segment的)載入放進我的專案裡,也無法,想詢問布丁大是如何載入的呢?

      刪除
    4. 您好,

      novel-segment是Node.js的套件,必須要在Node.js的環境下才能使用。

      您可能要先看看您要使用哪一種程式語言來做斷詞,每種程式語言會有對應的套件可供使用。

      加油。

      刪除
    5. 謝謝大大,小弟再研究一下,謝謝您!!!

      刪除
    6. 您好,

      如果您需要簡單操作的斷詞工具的話,不妨看一下我最近整理的Python-Jieba專案。
      https://blog.pulipuli.info/2019/01/python-jieba-word-segmentation-and-part.html?showComment=1645697319572#c7209462930443520658

      用Docker包裝,就讓功能變得很簡單了。
      可以參考看看。

      刪除