Loading [MathJax]/jax/output/CommonHTML/config.js
前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >专栏 >中文分词代码(此代码为作者多年经验总结,以前发表过VB,PB版本)

中文分词代码(此代码为作者多年经验总结,以前发表过VB,PB版本)

作者头像
jack.yang
发布于 2025-04-05 03:11:42
发布于 2025-04-05 03:11:42
390
举报

/*  * created by yzh 2004.5.12  * 请大家引用时保留这段作者声明,此代码为开源代码;使用不受限制。  * 中文分词代码  *此代码为作者多年经验总结,以前发表过VB,PB版本 */

import java.io.BufferedReader; import java.io.IOException; import java.io.InputStream; import java.io.InputStreamReader; import java.util.Locale; import java.util.TreeMap; import java.util.TreeSet;

public class ChineseSegmenter {

   private static ChineseSegmenter segmenter = null;

   // private Hashtable zhwords;    private TreeMap zhwords;

   private TreeSet cforeign, cnumbers;

   // Char form    public final static int TRAD = 0;

   public final static int SIMP = 1;

   public final static int BOTH = 2;

   // Charform is TRAD, SIMP or BOTH    private ChineseSegmenter(int charform, boolean loadwordfile) {       cforeign = new TreeSet();       cnumbers = new TreeSet();

      if (charform == SIMP) {          loadset(cnumbers, "data/snumbers_u8.txt");          loadset(cforeign, "data/sforeign_u8.txt");       } else if (charform == TRAD) {          loadset(cnumbers, "data/tnumbers_u8.txt");          loadset(cforeign, "data/tforeign_u8.txt");       } else { // BOTH          loadset(cnumbers, "data/snumbers_u8.txt");          loadset(cforeign, "data/sforeign_u8.txt");          loadset(cnumbers, "data/tnumbers_u8.txt");          loadset(cforeign, "data/tforeign_u8.txt");       }

      // zhwords = new Hashtable(120000);       zhwords = new TreeMap();

      if (!loadwordfile) {          return;       }

      String newword = null;       try {          InputStream worddata = null;          if (charform == SIMP) {             worddata = getClass().getResourceAsStream("simplexu8.txt");          } else if (charform == TRAD) {             worddata = getClass().getResourceAsStream("tradlexu8.txt");          } else if (charform == BOTH) {             worddata = getClass().getResourceAsStream("bothlexu8.txt");          }          BufferedReader in = new BufferedReader(new InputStreamReader(                worddata, "UTF8"));          while ((newword = in.readLine()) != null) {             if ((newword.indexOf("#") == -1) && (newword.length() < 5)) {

               zhwords.put(newword.intern(), "1");

               if (newword.length() == 3) {                   if (zhwords.containsKey(newword.substring(0, 2)                         .intern()) == false) {                      zhwords.put(newword.substring(0, 2).intern(), "2");                   }                }

               if (newword.length() == 4) {                   if (zhwords.containsKey(newword.substring(0, 2)                         .intern()) == false) {                      zhwords.put(newword.substring(0, 2).intern(), "2");                   }                   if (zhwords.containsKey(newword.substring(0, 3)                         .intern()) == false) {                      zhwords.put(newword.substring(0, 3).intern(), "2");                   }                }             }          }          in.close();       } catch (IOException e) {          e.printStackTrace();       }

   }    public synchronized static void reset() {       ChineseSegmenter.segmenter = null;    }

   public synchronized static ChineseSegmenter getGBSegmenter() {       Locale.setDefault(Locale.SIMPLIFIED_CHINESE);       if (ChineseSegmenter.segmenter == null) {          ChineseSegmenter.segmenter = new ChineseSegmenter(ChineseSegmenter.SIMP, true);       }       return ChineseSegmenter.segmenter;    }

   public synchronized static ChineseSegmenter getBig5Segmenter() {       Locale.setDefault(Locale.TRADITIONAL_CHINESE);       if (ChineseSegmenter.segmenter == null) {          ChineseSegmenter.segmenter = new ChineseSegmenter(ChineseSegmenter.TRAD, true);       }       return ChineseSegmenter.segmenter;    }

   private void loadset(TreeSet targetset, String sourcefile) {       String dataline;       try {          InputStream setdata = getClass().getResourceAsStream(sourcefile);          BufferedReader in = new BufferedReader(new InputStreamReader(                setdata, "UTF-8"));          while ((dataline = in.readLine()) != null) {             if ((dataline.indexOf("#") > -1) || (dataline.length() == 0)) {                continue;             }             targetset.add(dataline.intern());          }          in.close();       } catch (Exception e) {          System.err.println("Exception loading data file" + sourcefile + " "                + e);          e.printStackTrace();       }

   }

   public boolean isNumber(String testword) {       boolean result = true;       for (int i = 0; i < testword.length(); i++) {          if (cnumbers.contains(testword.substring(i, i + 1).intern()) == false) {             result = false;             break;          }       }       return result;    }

   public boolean isAllForeign(String testword) {       boolean result = true;       for (int i = 0; i < testword.length(); i++) {          if (cforeign.contains(testword.substring(i, i + 1).intern()) == false) {             result = false;             break;          }       }

      return result;    }

   public boolean isNotCJK(String testword) {       boolean result = true;       for (int i = 0; i < testword.length(); i++) {          if (Character.UnicodeBlock.of(testword.charAt(i)) == Character.UnicodeBlock.CJK_UNIFIED_IDEOGRAPHS) {             result = false;             break;          }       }

      return result;    }

   public String segmentLine(String cline, String separator) {       StringBuffer currentword = new StringBuffer();       StringBuffer outline = new StringBuffer();       int i, clength;       char currentchar;       // separator = " ";

      clength = cline.length();       for (i = 0; i < clength; i++) {          currentchar = cline.charAt(i);          if (Character.UnicodeBlock.of(currentchar) == Character.UnicodeBlock.CJK_UNIFIED_IDEOGRAPHS                || isNumber(cline.substring(i, i + 1)) == true) {             // Character in CJK block             if (currentword.length() == 0) { // start looking for next                                        // word                if (i > 0                      && (Character.isWhitespace(cline.charAt(i - 1)) == false)) {                   outline.append(separator);                }                currentword.append(currentchar);

            } else {                if (zhwords.containsKey(new String(currentword.toString()                      + currentchar).intern()) == true                      && ((String) (zhwords.get(new String(currentword                            .toString()                            + currentchar).intern()))).equals("1") == true) {                   // word is in lexicon                   currentword.append(currentchar);                } else if (isAllForeign(currentword.toString())                      && cforeign.contains(new String(                            new char[] { currentchar }).intern())                      && i + 2 < clength                      && (zhwords.containsKey(cline.substring(i, i + 2)                            .intern()) == false)) {                   // Possible a transliteration of a foreign name                   currentword.append(currentchar);                } else if (isNumber(currentword.toString())                      && cnumbers.contains(new String(                            new char[] { currentchar }).intern())                /*                 * && (i + 2 < clength) &&                 * (zhwords.containsKey(cline.substring(i, i+2).intern()) ==                 * false)                 */) {                   // Put all consecutive number characters together                   currentword.append(currentchar);                } else if ((zhwords.containsKey(new String(currentword                      .toString()                      + currentchar).intern()))                      && (((String) (zhwords.get(new String(currentword                            .toString()                            + currentchar).intern()))).equals("2") == true)                      && i + 1 < clength                      && (zhwords.containsKey(new String(currentword                            .toString()                            + currentchar + cline.charAt(i + 1))                            .intern()) == true)) {                   // Starts a word in the lexicon                   currentword.append(currentchar);

               } else { // Start anew                      outline.append(currentword.toString());                   if (Character.isWhitespace(currentchar) == false) {                      outline.append(separator);                   }                   currentword.setLength(0);                   currentword.append(currentchar);                }             }

         } else { // Not chinese character             // System.err.println("not cjk");             if (currentword.length() > 0) {                outline.append(currentword.toString());                if (Character.isWhitespace(currentchar) == false) {                   outline.append(separator);                }                currentword.setLength(0);             }             outline.append(currentchar);          }       }

      outline.append(currentword.toString());

      return outline.toString();       // return offsets;    }

   public static void main(String[] args) throws Exception {

      ChineseSegmenter seg = ChineseSegmenter.getGBSegmenter();       System.out.println(seg.segmentLine("Some string in chinese.", " "));    }

}

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2006-03-24,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
暂无评论
推荐阅读
编辑精选文章
换一批
Java 结合中文分词库 jieba 统计一堆文本中各个词语的出现次数【代码记录】
訾博ZiBo
2025/01/06
970
Java 结合中文分词库 jieba 统计一堆文本中各个词语的出现次数【代码记录】
Java_util_02_Java判断字符串是中文还是英文
做微信开发,使用百度翻译API时,需要指定译文的语种。这就需要我们判断待翻译内容是中文还是英文,若是中文,则翻译成英文,若是英文则翻译成中文。
shirayner
2018/08/10
1.6K0
Java 代码实现——使用 IK 分词器进行词频统计
使用分词器对文章的词频进行统计,主要目的是实现如下图所示的词云功能,可以找到文章内的重点词汇。
铭毅天下
2021/12/15
2.7K0
Java 代码实现——使用 IK 分词器进行词频统计
Java中json字符串中文的处理
中间想过先把中文转成unicode。但是\u会变成\\u,还是有问题,无奈之下,只好自己上场,写了一个JAVA脚本提供给安卓了。
魔王卷子
2019/05/31
3.7K0
Lucene.net(4.8.0) 学习问题记录五: JIEba分词和Lucene的结合,以及对分词器的思考
前言:目前自己在做使用Lucene.net和PanGu分词实现全文检索的工作,不过自己是把别人做好的项目进行迁移。因为项目整体要迁移到ASP.NET Core 2.0版本,而Lucene使用的版本是3.6.0 ,PanGu分词也是对应Lucene3.6.0版本的。不过好在Lucene.net 已经有了Core 2.0版本(4.8.0 bate版),而PanGu分词,目前有人正在做,貌似已经做完,只是还没有测试~,Lucene升级的改变我都会加粗表示。 Lucene.net 4.8.0    https://
ShenduCC
2018/04/27
2.3K0
EditText 集锦 - 开发中常用的用法及遇到的各种坑
EditText ,文本输入框,一个再熟悉不过的的控件,在开发当中,我们需要经常用到。这边文章,主要是记录 EditText 的常用用法,需要的时候可以直接复制张贴,提高效率。同时,本文章会持续更新,建议收藏起来。
程序员徐公
2019/03/04
2.4K0
语法设计——基于LL(1)文法的预测分析表法
通过实验教学,加深学生对所学的关于编译的理论知识的理解,增强学生对所学知识的综合应用能力,并通过实践达到对所学的知识进行验证。通过对基于LL(1)文法的预测分析表法DFA模拟程序实验,使学生掌握确定的自上而下的语法分析的实现技术,及具体实现方法。通过本实验加深对语词法分析程序的功能及实现方法的理解 。
Angel_Kitty
2019/01/30
1.7K0
Java实用工具类四:StringUtils工具类
此文仅对自己工作中用到的类进行总结,方便以后的使用。 package com.cn.hnust.util; import java.io.UnsupportedEncodingException; import java.util.ArrayList; import java.util.List; import java.util.regex.Matcher; import java.util.regex.Pattern; import javax.servlet.http.HttpServletRe
芈亓
2022/06/17
7450
没错,我是高端吃瓜玩家
行了,咱们步入正轨,已经进入2022,在2021这一年,很多人的快乐消遣是在吃瓜快乐中度过的,有的作为主动吃瓜群众第一手掌握消息,有的作为第二手或者被动吃瓜者(比如我就是)。
bigsai
2022/01/05
1.6K1
没错,我是高端吃瓜玩家
1035. Spell checker
POJ 刷题系列:1035. Spell checker 题意: 一组字符串,组成字典。查询某个字符串是否在该字典中。如果不存在,输出字典集中与查询字符串编辑距离为1的字符串。 思路: 因为每个字符串的最大长度为15,查询O(1),采用暴力。 代码如下: import java.io.BufferedReader; import java.io.File; import java.io.FileInputStream; import java.io.IOException; impor
用户1147447
2019/05/26
3790
java版JieBa分词源码走读
JieBa内部存储了一个文件dict.txt,比如记录了 X光线 3 n。在内部的存储trie树结构则为
爬蜥
2019/07/09
1.6K0
Java 对字符串操作的工具类,很全
目录 1 实现 1 实现 import java.io.Serializable; import java.util.ArrayList; import java.util.Collection; import java.util.HashSet; import java.util.List; import java.util.Map; import java.util.Set; import org.springframework.util.AntPathMatcher; import com.ruoy
一写代码就开心
2023/02/01
1.2K0
StringUtils的源码解析
文章目录 1. StringUtils 1.1. 源码解析 StringUtils spring封装的字符串工具类 源码解析 isEmpty(Object str) :判断当前字符串为空,如果为空返回true 如果字符串为空或者是个空字符串,那么返回true public static boolean isEmpty(Object str) { return (str == null || "".equals(str)); } hasLength(CharSequence str) : 如果字符
爱撒谎的男孩
2019/12/31
8110
分词工具Hanlp基于感知机的中文分词框架
结构化感知机标注框架是一套利用感知机做序列标注任务,并且应用到中文分词、词性标注与命名实体识别这三个问题的完整在线学习框架,该框架利用1个算法解决3个问题,时自治同意的系统,同时三个任务顺序渐进,构成流水线式的系统。本文先介绍中文分词框架部分内容。
IT小白龙
2019/04/03
1K0
分词工具Hanlp基于感知机的中文分词框架
LWC 58:726. Number of Atoms
用户1147447
2018/01/02
6450
利用文本挖掘技术来找出《天龙八部》中的“小鲜词”
Star先生
2017/08/02
1.2K0
利用文本挖掘技术来找出《天龙八部》中的“小鲜词”
【学习】深度解析中文分词器算法(最大正向/逆向匹配)
中文分词算法概述: 1:非基于词典的分词(人工智能领域) 相当于人工智能领域计算。一般用于机器学习,特定领域等方法,这种在特定领域的分词可以让计算机在现有的规则模型中,推理如何分词。在某个领域(垂直领域)分词精度较高。但是实现比较复杂。 例:比较流行的语义网:基于本体的语义检索。 大致实现:用protege工具构建一个本体(在哲学中也叫概念,在80年代开始被人工智能),通过jena的推理机制和实现方法。 实现对Ontology的语义检索。 Ontology语义检索这块自己和一朋友也还在琢
小莹莹
2018/04/23
2.3K0
【学习】深度解析中文分词器算法(最大正向/逆向匹配)
POJ 刷题系列:3080. Blue Jeans
版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/u014688145/article/details/79057958
用户1147447
2019/05/26
3740
Fiddler + JSoup 爬取现代汉语语料库数据
爬虫中常用JSoup处理Html,对于类似百度这样的搜索引擎,则需要配合fiddler使用,步骤如下 Fidder获取链接信息 在IE浏览器中打开http://www.cncorpus.org/CnC
Star先生
2017/08/01
1.9K0
Fiddler + JSoup 爬取现代汉语语料库数据
杨校老师课堂之封装操作消息提醒工具类ResultCode【简直太好用】
以下工具类可以帮开发工程师在springmvc中进行快速完成封装消息、map链式的提醒,由对象转为json传递到前台,适用于Vue项目
杨校
2022/09/23
5850
推荐阅读
相关推荐
Java 结合中文分词库 jieba 统计一堆文本中各个词语的出现次数【代码记录】
更多 >
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档