前言

敏感词过滤应该是不用给大家过多的解释吧?讲白了就是你在项目中输入某些字(比如输入xxoo相关的文字时)时要能检

测出来,很多项目中都会有一个敏感词管理模块,在敏感词管理模块中你可以加入敏感词,然后根据加入的敏感词去过滤输

入内容中的敏感词并进行相应的处理,要么提示,要么高亮显示,要么直接替换成其它的文字或者符号代替。

敏感词过滤的做法有很多,我简单描述我现在理解的几种:

①查询数据库当中的敏感词,循环每一个敏感词,然后去输入的文本中从头到尾搜索一遍,看是否存在此敏感词,有则做相

应的处理,这种方式讲白了就是找到一个处理一个。

优点:so easy。用java代码实现基本没什么难度。

缺点:这效率让我心中奔过十万匹草泥马,而且匹配的是不是有些蛋疼,如果是英文时你会发现一个很无语的事情,比如英文

a是敏感词,那我如果是一篇英文文档,那程序它妹的得处理多少次敏感词?谁能告诉我?

②传说中的DFA算法(有穷自动机),也正是我要给大家分享的,毕竟感觉比较通用,算法的原理希望大家能够自己去网上查查

资料,这里就不详细说明了。

优点:至少比上面那sb效率高点。

缺点:对于学过算法的应该不难,对于没学过算法的用起来也不难,就是理解起来有点gg疼,匹配效率也不高,比较耗费内存,

敏感词越多,内存占用的就越大。

③第三种在这里要特别说明一下,那就是你自己去写一个算法吧,或者在现有的算法的基础上去优化,这也是追求的至高境界之一。

那么,传说中的DFA算法是怎么实现的呢?

第一步:敏感词库初始化(将敏感词用DFA算法的原理封装到敏感词库中,敏感词库采用HashMap保存),代码如下:

package com.cfwx.rox.web.sysmgr.util;

import java.util.HashMap;

import java.util.HashSet;

import java.util.Iterator;

import java.util.List;

import java.util.Map;

import java.util.Set;

import com.cfwx.rox.web.common.model.entity.SensitiveWord;

/**

* 敏感词库初始化

*

* @author AlanLee

*

*/

public class SensitiveWordInit

{

/**

* 敏感词库

*/

public HashMap sensitiveWordMap;

/**

* 初始化敏感词

*

* @return

*/

public Map initKeyWord(List sensitiveWords)

{

try

{

// 从敏感词集合对象中取出敏感词并封装到Set集合中

Set keyWordSet = new HashSet();

for (SensitiveWord s : sensitiveWords)

{

keyWordSet.add(s.getContent().trim());

}

// 将敏感词库加入到HashMap中

addSensitiveWordToHashMap(keyWordSet);

}

catch (Exception e)

{

e.printStackTrace();

}

return sensitiveWordMap;

}

/**

* 封装敏感词库

*

* @param keyWordSet

*/

@SuppressWarnings("rawtypes")

private void addSensitiveWordToHashMap(Set keyWordSet)

{

// 初始化HashMap对象并控制容器的大小

sensitiveWordMap = new HashMap(keyWordSet.size());

// 敏感词

String key = null;

// 用来按照相应的格式保存敏感词库数据

Map nowMap = null;

// 用来辅助构建敏感词库

Map newWorMap = null;

// 使用一个迭代器来循环敏感词集合

Iterator iterator = keyWordSet.iterator();

while (iterator.hasNext())

{

key = iterator.next();

// 等于敏感词库,HashMap对象在内存中占用的是同一个地址,所以此nowMap对象的变化,sensitiveWordMap对象也会跟着改变

nowMap = sensitiveWordMap;

for (int i = 0; i < key.length(); i++)

{

// 截取敏感词当中的字,在敏感词库中字为HashMap对象的Key键值

char keyChar = key.charAt(i);

// 判断这个字是否存在于敏感词库中

Object wordMap = nowMap.get(keyChar);

if (wordMap != null)

{

nowMap = (Map) wordMap;

}

else

{

newWorMap = new HashMap();

newWorMap.put("isEnd", "0");

nowMap.put(keyChar, newWorMap);

nowMap = newWorMap;

}

// 如果该字是当前敏感词的最后一个字,则标识为结尾字

if (i == key.length() - 1)

{

nowMap.put("isEnd", "1");

}

System.out.println("封装敏感词库过程:"+sensitiveWordMap);

}

System.out.println("查看敏感词库数据:" + sensitiveWordMap);

}

}

}

第二步:写一个敏感词过滤工具类,里面可以写上自己需要的方法,代码如下:

package com.cfwx.rox.web.sysmgr.util;

import java.util.HashSet;

import java.util.Iterator;

import java.util.Map;

import java.util.Set;

/**

* 敏感词过滤工具类

*

* @author AlanLee

*

*/

public class SensitivewordEngine

{

/**

* 敏感词库

*/

public static Map sensitiveWordMap = null;

/**

* 只过滤最小敏感词

*/

public static int minMatchTYpe = 1;

/**

* 过滤所有敏感词

*/

public static int maxMatchType = 2;

/**

* 敏感词库敏感词数量

*

* @return

*/

public static int getWordSize()

{

if (SensitivewordEngine.sensitiveWordMap == null)

{

return 0;

}

return SensitivewordEngine.sensitiveWordMap.size();

}

/**

* 是否包含敏感词

*

* @param txt

* @param matchType

* @return

*/

public static boolean isContaintSensitiveWord(String txt, int matchType)

{

boolean flag = false;

for (int i = 0; i < txt.length(); i++)

{

int matchFlag = checkSensitiveWord(txt, i, matchType);

if (matchFlag > 0)

{

flag = true;

}

}

return flag;

}

/**

* 获取敏感词内容

*

* @param txt

* @param matchType

* @return 敏感词内容

*/

public static Set getSensitiveWord(String txt, int matchType)

{

Set sensitiveWordList = new HashSet();

for (int i = 0; i < txt.length(); i++)

{

int length = checkSensitiveWord(txt, i, matchType);

if (length > 0)

{

// 将检测出的敏感词保存到集合中

sensitiveWordList.add(txt.substring(i, i + length));

i = i + length - 1;

}

}

return sensitiveWordList;

}

/**

* 替换敏感词

*

* @param txt

* @param matchType

* @param replaceChar

* @return

*/

public static String replaceSensitiveWord(String txt, int matchType, String replaceChar)

{

String resultTxt = txt;

Set set = getSensitiveWord(txt, matchType);

Iterator iterator = set.iterator();

String word = null;

String replaceString = null;

while (iterator.hasNext())

{

word = iterator.next();

replaceString = getReplaceChars(replaceChar, word.length());

resultTxt = resultTxt.replaceAll(word, replaceString);

}

return resultTxt;

}

/**

* 替换敏感词内容

*

* @param replaceChar

* @param length

* @return

*/

private static String getReplaceChars(String replaceChar, int length)

{

String resultReplace = replaceChar;

for (int i = 1; i < length; i++)

{

resultReplace += replaceChar;

}

return resultReplace;

}

/**

* 检查敏感词数量

*

* @param txt

* @param beginIndex

* @param matchType

* @return

*/

public static int checkSensitiveWord(String txt, int beginIndex, int matchType)

{

boolean flag = false;

// 记录敏感词数量

int matchFlag = 0;

char word = 0;

Map nowMap = SensitivewordEngine.sensitiveWordMap;

for (int i = beginIndex; i < txt.length(); i++)

{

word = txt.charAt(i);

// 判断该字是否存在于敏感词库中

nowMap = (Map) nowMap.get(word);

if (nowMap != null)

{

matchFlag++;

// 判断是否是敏感词的结尾字,如果是结尾字则判断是否继续检测

if ("1".equals(nowMap.get("isEnd")))

{

flag = true;

// 判断过滤类型,如果是小过滤则跳出循环,否则继续循环

if (SensitivewordEngine.minMatchTYpe == matchType)

{

break;

}

}

}

else

{

break;

}

}

if (!flag)

{

matchFlag = 0;

}

return matchFlag;

}

}

第三步:一切都准备就绪,当然是查询好数据库当中的敏感词,并且开始过滤咯,代码如下:

@SuppressWarnings("rawtypes")

@Override

public Set sensitiveWordFiltering(String text)

{

// 初始化敏感词库对象

SensitiveWordInit sensitiveWordInit = new SensitiveWordInit();

// 从数据库中获取敏感词对象集合(调用的方法来自Dao层,此方法是service层的实现类)

List sensitiveWords = sensitiveWordDao.getSensitiveWordListAll();

// 构建敏感词库

Map sensitiveWordMap = sensitiveWordInit.initKeyWord(sensitiveWords);

// 传入SensitivewordEngine类中的敏感词库

SensitivewordEngine.sensitiveWordMap = sensitiveWordMap;

// 得到敏感词有哪些,传入2表示获取所有敏感词

Set set = SensitivewordEngine.getSensitiveWord(text, 2);

return set;

}

最后一步:在Controller层写一个方法给前端请求,前端获取到需要的数据并进行相应的处理,代码如下:

/**

* 敏感词过滤

*

* @param text

* @return

*/

@RequestMapping(value = "/word/filter")

@ResponseBody

public RespVo sensitiveWordFiltering(String text)

{

RespVo respVo = new RespVo();

try

{

Set set = sensitiveWordService.sensitiveWordFiltering(text);

respVo.setResult(set);

}

catch (Exception e)

{

throw new RoxException("过滤敏感词出错,请联系维护人员");

}

return respVo;

}

总结

以上就是这篇文章的全部内容了,代码中写了不少的注释,大家可以动动自己的脑筋好好的理解一下。希望本文的内容对大家的学习或者工作能带来一定的帮助,如果有疑问大家可以留言交流,谢谢大家对聚米学院的支持。

java dfa 敏感词_java利用DFA算法实现敏感词过滤功能相关推荐

  1. 用Java输出高频词_java进行一篇文章的高频词统计

    一.需求分析: 给定一篇文档,请对其高频词进行统计,并输出高频词top10. 二.解决思路: 对高频词进行统计,主要是对字符串进行分割,并对其出现的频率进行存储和统计.存储字符串频率可用HashMap ...

  2. java 大整数编程_Java编程--RSA算法中的大整数运算

    Java编程–RSA算法中的大整数运算 RSA原理浅析 RSA是利用陷门单向函数实现的,其安全基础依赖于大整数的分解问题的难解性 算法过程 为了加深对RSA算法的了解,接下来通过简单的一个例子来分析一 ...

  3. java 二维链表_Java数据结构与算法----数组与链表

    数据类型 1 数据类型介绍 数据类型的分类(按照结构划分):线性结构和非线性结构 线性结构:线性结构作为最常用的数据结构,其特点是数据元素之间存在一对一的线性关系 线性结构有两种不同的存储结构,即顺序 ...

  4. java string逆序_java经典入门算法题,java初学者必备

    java经典入门算法题 开头求关注警告 喜欢这样文章的可以关注我,我会持续更新,你们的关注是我更新的动力!需要更多java学习资 料的也可以私信我! 祝关注我的人都:身体健康,财源广进,福如东海,寿比 ...

  5. java socket 聊天室_java利用Socket实现聊天室功能实例

    导读热词 最近研究了下Java socket通信基础,利用代码实现了一个简单的多人聊天室功能,现把代码共享下,希望能帮到有兴趣了解的人. 目录结构: ChatClient: package com.p ...

  6. java游戏输赢统计_java利用多线程和Socket实现猜拳游戏

    本文实例为大家分享了利用多线程和Socket实现猜拳游戏的具体代码,供大家参考,具体内容如下 实例:猜拳游戏 猜拳游戏是指小时候玩的石头.剪刀.布的游戏.客户端与服务器的"较量", ...

  7. java 特殊符号正则_java利用正则表达式处理特殊字符的方法实例

    前言 一串字符串中有特殊符号,可能会影响到相关接口业务,所以需要把字符串中的特殊字符都过滤掉 百度上面搜索大部分处理方法是通过正则表达式, 他需要处理的特殊符号都写进正则表达式中去校验, 这种方式一眼 ...

  8. java多核的利用率_java利用FutureTask、ExecutorService 在多核时代充分利用CPU运算

    java利用FutureTask.ExecutorService 在多核时代充分利用CPU运算 FutureTask.ExecutorService 相关知识,请看java,API 一个使用Futur ...

  9. java快排原理_Java数据结构与算法——快速排序

    声明:码字不易,转载请注明出处,欢迎文章下方讨论交流. 前言:Java数据结构与算法专题会不定时更新,欢迎各位读者监督.本篇文章介绍排序算法中最常用也是面试中最容易考到的排序算法--快排,包括快排的思 ...

最新文章

  1. Cell重磅发布15万人体微生物基因组!超大规模宏基因组研究揭示数千计人体微生物新物种...
  2. R语言stringr包str_count函数计算字符串匹配个数实战
  3. 数据科学和机器学习中使用的最多的20个R语言包
  4. 人工智能的发展趋势和行业岗位
  5. diskgenius扩容c盘重启电脑卡住_电脑使用DiskGenius工具增加C盘空间的方法
  6. 运营商何时推出无限流量?
  7. 第一百二十一期:当新闻报道用上AR 技术,能为读者带来什么?
  8. 第二周:神经网络的编程基础之Python与向量化
  9. kotlin list转map
  10. 百度AI C#客户端车辆检测找不到VehicleDetect解决
  11. ★RFC标准库_目录链接
  12. 搜索引擎整体结构图以及描述
  13. 光线追踪渲染技术能听懂的介绍
  14. Linux文件打包与压缩
  15. 9行代码制作一个简单的油猴插件
  16. 儿童三轮自行车外观及结构设计(lunwen+任务书+开题+文综+翻译及原文+三维模型)
  17. 多元统计分析——聚类分析——K-均值聚类(K-中值、K-众数)
  18. HDTV 之-HDMI HPD
  19. 谁能引爆大数据?答案是“位置大数据”
  20. 学生动漫网页设计模板下载 海贼王大学生HTML网页制作作品 简单漫画网页设计成品 dreamweaver学生网站模板

热门文章

  1. 2k2实用球员_NBA2KOL2王朝模式角色球员推荐 角色球员哪些好
  2. 爆破445端口和22端口拿shell
  3. MVC5+EF6 入门完整教程六
  4. window应用在linux运行,如何在Linux上运行Windows应用程序?
  5. 软件开发实训(720)
  6. GCC - GIMPLE IR 学习一
  7. 查看debian 版本和KDE还是Gnome
  8. 【uni-app】列表左滑实现商品删除
  9. 热血三国:白领人士超级攻略
  10. Node-Red 实践:企业微信消息推送