Java實現敏感詞過濾代碼

jopen 9年前發布 | 4K 次閱讀 Java

import java.io.BufferedReader;
import java.io.File;
import java.io.FileInputStream;
import java.io.InputStreamReader;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Iterator;
import java.util.Map;
import java.util.Set;

/**

  • @Description: 初始化敏感詞庫,將敏感詞加入到HashMap中,構建DFA算法模型
  • @Project:test
  • @Author : chenming
  • @Date : 2014年4月20日 下午2:27:06
  • @version 1.0 */ public class SensitiveWordInit { private String ENCODING = "GBK"; //字符編碼 @SuppressWarnings("rawtypes") public HashMap sensitiveWordMap;

    public SensitiveWordInit(){

     super();
    

    }

    /**

    • @author chenming
    • @date 2014年4月20日 下午2:28:32
    • @version 1.0 */ @SuppressWarnings("rawtypes") public Map initKeyWord(){ try {

       //讀取敏感詞庫
       Set<String> keyWordSet = readSensitiveWordFile();
       //將敏感詞庫加入到HashMap中
       addSensitiveWordToHashMap(keyWordSet);
       //spring獲取application,然后application.setAttribute("sensitiveWordMap",sensitiveWordMap);
      

      } catch (Exception e) {

       e.printStackTrace();
      

      } return sensitiveWordMap; }

      /**

    • 讀取敏感詞庫,將敏感詞放入HashSet中,構建一個DFA算法模型:<br>
    • 中 = {
    • isEnd = 0
    • 國 = {<br>
    • isEnd = 1
    • 人 = {isEnd = 0
    • 民 = {isEnd = 1}
    • }
    • 男 = {
    • isEnd = 0
    • 人 = {
    • isEnd = 1
    • }
    • }
    • }
    • }
    • 五 = {
    • isEnd = 0
    • 星 = {
    • isEnd = 0
    • 紅 = {
    • isEnd = 0
    • 旗 = {
    • isEnd = 1
    • }
    • }
    • }
    • }
    • @author chenming
    • @date 2014年4月20日 下午3:04:20
    • @param keyWordSet 敏感詞庫
    • @version 1.0 */ @SuppressWarnings({ "rawtypes", "unchecked" }) private void addSensitiveWordToHashMap(Set<String> keyWordSet) { sensitiveWordMap = new HashMap(keyWordSet.size()); //初始化敏感詞容器,減少擴容操作 String key = null;
      Map nowMap = null; Map<String, String> newWorMap = null; //迭代keyWordSet Iterator<String> iterator = keyWordSet.iterator(); while(iterator.hasNext()){

       key = iterator.next();    //關鍵字
       nowMap = sensitiveWordMap;
       for(int i = 0 ; i < key.length() ; i++){
           char keyChar = key.charAt(i);       //轉換成char型
           Object wordMap = nowMap.get(keyChar);       //獲取
      
           if(wordMap != null){        //如果存在該key,直接賦值
               nowMap = (Map) wordMap;
           }
           else{     //不存在則,則構建一個map,同時將isEnd設置為0,因為他不是最后一個
               newWorMap = new HashMap<String,String>();
               newWorMap.put("isEnd", "0");     //不是最后一個
               nowMap.put(keyChar, newWorMap);
               nowMap = newWorMap;
           }
      
           if(i == key.length() - 1){
               nowMap.put("isEnd", "1");    //最后一個
           }
       }
      

      } }

      public static void main(String[] args) { Set set = new HashSet(); set.add("中國"); set.add("中國人民"); set.add("中國人"); new SensitiveWordInit().addSensitiveWordToHashMap(set); }

      /**

    • 讀取敏感詞庫中的內容,將內容添加到set集合中
    • @author chenming
    • @date 2014年4月20日 下午2:31:18
    • @return
    • @version 1.0
    • @throws Exception */ @SuppressWarnings("resource") private Set<String> readSensitiveWordFile() throws Exception{ Set<String> set = null;

      File file = new File("D:\SensitiveWord.txt"); //讀取文件 InputStreamReader read = new InputStreamReader(new FileInputStream(file),ENCODING); try {

       if(file.isFile() && file.exists()){      //文件流是否存在
           set = new HashSet<String>();
           BufferedReader bufferedReader = new BufferedReader(read);
           String txt = null;
           while((txt = bufferedReader.readLine()) != null){    //讀取文件,將文件內容放入到set中
               set.add(txt);
           }
       }
       else{         //不存在拋出異常信息
           throw new Exception("敏感詞庫文件不存在");
       }
      

      } catch (Exception e) {

       throw e;
      

      }finally{

       read.close();     //關閉文件流
      

      } return set; } }</pre>


       

      import java.util.HashSet;
      import java.util.Iterator;
      import java.util.Map;
      import java.util.Set;

/**

  • @Description: 敏感詞過濾
  • @Project:test
  • @Author : chenming
  • @Date : 2014年4月20日 下午4:17:15
  • @version 1.0 */ public class SensitivewordFilter { @SuppressWarnings("rawtypes") private Map sensitiveWordMap = null; public static int minMatchTYpe = 1; //最小匹配規則 public static int maxMatchType = 2; //最大匹配規則

    /**

    • 構造函數,初始化敏感詞庫 */ public SensitivewordFilter(){ sensitiveWordMap = new SensitiveWordInit().initKeyWord(); }

      /**

    • 判斷文字是否包含敏感字符
    • @author chenming
    • @date 2014年4月20日 下午4:28:30
    • @param txt 文字
    • @param matchType 匹配規則&nbsp;1:最小匹配規則,2:最大匹配規則
    • @return 若包含返回true,否則返回false
    • @version 1.0 */ public boolean isContaintSensitiveWord(String txt,int matchType){ boolean flag = false; for(int i = 0 ; i < txt.length() ; i++){

       int matchFlag = this.CheckSensitiveWord(txt, i, matchType); //判斷是否包含敏感字符
       if(matchFlag > 0){    //大于0存在,返回true
           flag = true;
       }
      

      } return flag; }

      /**

    • 獲取文字中的敏感詞
    • @author chenming
    • @date 2014年4月20日 下午5:10:52
    • @param txt 文字
    • @param matchType 匹配規則&nbsp;1:最小匹配規則,2:最大匹配規則
    • @return
    • @version 1.0 */ public Set<String> getSensitiveWord(String txt , int matchType){ Set<String> sensitiveWordList = new HashSet<String>();

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

       int length = CheckSensitiveWord(txt, i, matchType);    //判斷是否包含敏感字符
       if(length > 0){    //存在,加入list中
           sensitiveWordList.add(txt.substring(i, i+length));
           i = i + length - 1;    //減1的原因,是因為for會自增
       }
      

      }

      return sensitiveWordList; }

      /**

    • 替換敏感字字符
    • @author chenming
    • @date 2014年4月20日 下午5:12:07
    • @param txt
    • @param matchType
    • @param replaceChar 替換字符,默認*
    • @version 1.0 */ public String replaceSensitiveWord(String txt,int matchType,String replaceChar){ String resultTxt = txt; Set<String> set = getSensitiveWord(txt, matchType); //獲取所有的敏感詞 Iterator<String> 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; }

      /**

    • 獲取替換字符串
    • @author chenming
    • @date 2014年4月20日 下午5:21:19
    • @param replaceChar
    • @param length
    • @return
    • @version 1.0 */ private String getReplaceChars(String replaceChar,int length){ String resultReplace = replaceChar; for(int i = 1 ; i < length ; i++){

       resultReplace += replaceChar;
      

      }

      return resultReplace; }

      /**

    • 檢查文字中是否包含敏感字符,檢查規則如下:<br>
    • @author chenming
    • @date 2014年4月20日 下午4:31:03
    • @param txt
    • @param beginIndex
    • @param matchType
    • @return,如果存在,則返回敏感詞字符的長度,不存在返回0
    • @version 1.0 */ @SuppressWarnings({ "rawtypes"}) public int CheckSensitiveWord(String txt,int beginIndex,int matchType){ boolean flag = false; //敏感詞結束標識位:用于敏感詞只有1位的情況 int matchFlag = 0; //匹配標識數默認為0 char word = 0; Map nowMap = sensitiveWordMap; for(int i = beginIndex; i < txt.length() ; i++){

       word = txt.charAt(i);
       nowMap = (Map) nowMap.get(word);     //獲取指定key
       if(nowMap != null){     //存在,則判斷是否為最后一個
           matchFlag++;     //找到相應key,匹配標識+1 
           if("1".equals(nowMap.get("isEnd"))){       //如果為最后一個匹配規則,結束循環,返回匹配標識數
               flag = true;       //結束標志位為true   
               if(SensitivewordFilter.minMatchTYpe == matchType){    //最小規則,直接返回,最大規則還需繼續查找
                   break;
               }
           }
       }
       else{     //不存在,直接返回
           break;
       }
      

      } if(matchFlag < 2 || !flag){ //長度必須大于等于1,為詞

       matchFlag = 0;
      

      } return matchFlag; }

      public static void main(String[] args) { SensitivewordFilter filter = new SensitivewordFilter(); System.out.println("敏感詞的數量:" + filter.sensitiveWordMap.size()); String string = "太多的傷感情懷也許只局限于飼養基地 熒幕中的情節,主人公嘗試著去用某種方式漸漸的很瀟灑地釋自殺指南懷那些自己經歷的傷感。"

                   + "然后法輪功 我們的扮演的角色就是跟隨著主人公的喜紅客聯盟 怒哀樂而過于牽強的把自己的情感也附加于銀幕情節中,然后感動就流淚,"
                   + "難過就躺在某一個人的懷里盡情的闡述心扉或者手機卡復制器一個人一杯紅酒一部電影在夜三級片 深人靜的晚上,關上電話靜靜的發呆著。";
      

      System.out.println("待檢測語句字數:" + string.length()); long beginTime = System.currentTimeMillis(); Set<String> set = filter.getSensitiveWord(string, 1); long endTime = System.currentTimeMillis(); System.out.println("語句中包含敏感詞的個數為:" + set.size() + "。包含:" + set); System.out.println("總共消耗時間為:" + (endTime - beginTime)); } }</pre>


      原文地址:http://blog.csdn.net/chenssy/article/details/26961957

       

 本文由用戶 jopen 自行上傳分享,僅供網友學習交流。所有權歸原作者,若您的權利被侵害,請聯系管理員。
 轉載本站原創文章,請注明出處,并保留原始鏈接、圖片水印。
 本站是一個以用戶分享為主的開源技術平臺,歡迎各類分享!