浅谈Python 敏感词过滤的实现


Posted in Python onAugust 15, 2019

一个简单的实现

class NaiveFilter():

  '''Filter Messages from keywords

  very simple filter implementation

  >>> f = NaiveFilter()
  >>> f.add("sexy")
  >>> f.filter("hello sexy baby")
  hello **** baby
  '''

  def __init__(self):
    self.keywords = set([])

  def parse(self, path):
    for keyword in open(path):
      self.keywords.add(keyword.strip().decode('utf-8').lower())

  def filter(self, message, repl="*"):
    message = str(message).lower()
    for kw in self.keywords:
      message = message.replace(kw, repl)
    return message

其中strip() 函数 删除附近的一些空格,解码采用utf-8的形式,然后将其转为小写。

parse()函数就是打开文件,然后从中取各个关键词,然后将其存在关键词集合中。

filter()函数是一个过滤器函数,其中将消息转化为小写,然后将关键词替换成*。、

class BSFilter:

  '''Filter Messages from keywords

  Use Back Sorted Mapping to reduce replacement times

  >>> f = BSFilter()
  >>> f.add("sexy")
  >>> f.filter("hello sexy baby")
  hello **** baby
  '''

  def __init__(self):
    self.keywords = []
    self.kwsets = set([])
    self.bsdict = defaultdict(set)
    self.pat_en = re.compile(r'^[0-9a-zA-Z]+$') # english phrase or not

  def add(self, keyword):
    if not isinstance(keyword, str):
      keyword = keyword.decode('utf-8')
    keyword = keyword.lower()
    if keyword not in self.kwsets:
      self.keywords.append(keyword)
      self.kwsets.add(keyword)
      index = len(self.keywords) - 1
      for word in keyword.split():
        if self.pat_en.search(word):
          self.bsdict[word].add(index)
        else:
          for char in word:
            self.bsdict[char].add(index)

  def parse(self, path):
    with open(path, "r") as f:
      for keyword in f:
        self.add(keyword.strip())

  def filter(self, message, repl="*"):
    if not isinstance(message, str):
      message = message.decode('utf-8')
    message = message.lower()
    for word in message.split():
      if self.pat_en.search(word):
        for index in self.bsdict[word]:
          message = message.replace(self.keywords[index], repl)
      else:
        for char in word:
          for index in self.bsdict[char]:
            message = message.replace(self.keywords[index], repl)
    return message

在上面的实现例子中,对于搜索查找进行了优化,对于英语单词,直接进行了按词索引字典查找。对于其他语言模式,我们采用逐字符查找匹配的一种模式。

BFS:宽度优先搜索方式。

class DFAFilter():

  '''Filter Messages from keywords

  Use DFA to keep algorithm perform constantly

  >>> f = DFAFilter()
  >>> f.add("sexy")
  >>> f.filter("hello sexy baby")
  hello **** baby
  '''

  def __init__(self):
    self.keyword_chains = {}
    self.delimit = '\x00'

  def add(self, keyword):
    if not isinstance(keyword, str):
      keyword = keyword.decode('utf-8')
    keyword = keyword.lower()
    chars = keyword.strip()
    if not chars:
      return
    level = self.keyword_chains
    for i in range(len(chars)):
      if chars[i] in level:
        level = level[chars[i]]
      else:
        if not isinstance(level, dict):
          break
        for j in range(i, len(chars)):
          level[chars[j]] = {}
          last_level, last_char = level, chars[j]
          level = level[chars[j]]
        last_level[last_char] = {self.delimit: 0}
        break
    if i == len(chars) - 1:
      level[self.delimit] = 0

  def parse(self, path):
    with open(path,encoding='UTF-8') as f:
      for keyword in f:
        self.add(keyword.strip())

  def filter(self, message, repl="*"):
    if not isinstance(message, str):
      message = message.decode('utf-8')
    message = message.lower()
    ret = []
    start = 0
    while start < len(message):
      level = self.keyword_chains
      step_ins = 0
      for char in message[start:]:
        if char in level:
          step_ins += 1
          if self.delimit not in level[char]:
            level = level[char]
          else:
            ret.append(repl * step_ins)
            start += step_ins - 1
            break
        else:
          ret.append(message[start])
          break
      else:
        ret.append(message[start])
      start += 1

    return ''.join(ret)

DFA即Deterministic Finite Automaton,也就是确定有穷自动机。

使用了嵌套的字典来实现。

参考

Github:敏感词过滤系统

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Python 相关文章推荐
使用Python的Flask框架实现视频的流媒体传输
Mar 31 Python
Python基于Pymssql模块实现连接SQL Server数据库的方法详解
Jul 20 Python
微信跳一跳小游戏python脚本
Jan 05 Python
Python OpenCV处理图像之图像直方图和反向投影
Jul 10 Python
Python 从subprocess运行的子进程中实时获取输出的例子
Aug 14 Python
python实现滑雪游戏
Feb 22 Python
Python无头爬虫下载文件的实现
Apr 02 Python
Python turtle库的画笔控制说明
Jun 28 Python
Python直接赋值及深浅拷贝原理详解
Sep 05 Python
Python基于内置函数type创建新类型
Oct 22 Python
python 制作网站小说下载器
Feb 20 Python
Python if else条件语句形式详解
Mar 24 Python
pycharm创建scrapy项目教程及遇到的坑解析
Aug 15 #Python
通过selenium抓取某东的TT购买记录并分析趋势过程解析
Aug 15 #Python
Python依赖包整体迁移方法详解
Aug 15 #Python
使用python批量修改文件名的方法(视频合并时)
Mar 24 #Python
python 修改本地网络配置的方法
Aug 14 #Python
python django 原生sql 获取数据的例子
Aug 14 #Python
django 连接数据库 sqlite的例子
Aug 14 #Python
You might like
require(),include(),require_once()和include_once()区别
2008/03/27 PHP
php中的注释、变量、数组、常量、函数应用介绍
2012/11/16 PHP
PHP中SESSION的注销与清除
2015/04/16 PHP
php中二分法查找算法实例分析
2016/09/22 PHP
phpstudy2020搭建站点的实现示例
2020/10/30 PHP
多个iframe自动调整大小的问题
2006/09/18 Javascript
用js模拟struts2的多action调用示例
2014/05/19 Javascript
Jquery实现由下向上展开效果的例子
2014/12/08 Javascript
jquery实现的伪分页效果代码
2015/10/29 Javascript
AngularJS入门教程之XHR和依赖注入详解
2016/08/18 Javascript
jQuery插件FusionCharts实现的2D面积图效果示例【附demo源码下载】
2017/03/06 Javascript
js a标签点击事件
2017/03/30 Javascript
VueJs 将接口用webpack代理到本地的方法
2017/11/27 Javascript
微信小程序实现image组件图片自适应宽度比例显示的方法
2018/01/16 Javascript
vue中使用cookies和crypto-js实现记住密码和加密的方法
2018/10/18 Javascript
详解在vue-test-utils中mock全局对象
2018/11/07 Javascript
详解如何给React-Router添加路由页面切换时的过渡动画
2019/04/25 Javascript
微信小程序用户盒子、宫格列表的实现
2020/07/01 Javascript
jquery实现简单每周轮换的日历
2020/09/10 jQuery
在vue中配置不同的代理同时访问不同的后台操作
2020/09/11 Javascript
浅谈python多线程和队列管理shell程序
2015/08/04 Python
设计模式中的原型模式在Python程序中的应用示例
2016/03/02 Python
Python用于学习重要算法的模块pygorithm实例浅析
2018/08/16 Python
python 输出所有大小写字母的方法
2019/01/02 Python
Python设计模式之状态模式原理与用法详解
2019/01/15 Python
Python爬虫学习之翻译小程序
2019/07/30 Python
一文了解python 3 字符串格式化 F-string 用法
2020/03/04 Python
捷克汽车配件和工具销售网站:TorriaCars
2018/02/26 全球购物
同事打架检讨书
2014/02/04 职场文书
医院工作检讨书范文
2014/02/10 职场文书
小学生安全责任书
2014/07/25 职场文书
2015年高中生国庆节演讲稿
2015/07/30 职场文书
golang interface判断为空nil的实现代码
2021/04/24 Golang
Spring整合Mybatis的全过程
2021/06/28 Java/Android
postgresql使用filter进行多维度聚合的解决方法
2021/07/16 PostgreSQL
关于的python五子棋的算法
2022/05/02 Python