--[[ 使用Aho-Corasick算法多模式匹配,时间控制在1秒内 ]] -- 初始化根 root = {}; root.value = 0; root.failure = root; -- 创建失败指针 function makefailure(node) local p = node.parent.failure; while true do if p[node.value] then node.failure = p[node.value]; break; elseif p == root then node.failure = p; else p = p.parent; end; end; end; -- 插入一个字符串 function insert(pattern) -- 循环插入字节 local pos; local p = root; for pos = 1, pattern:len() do local byte = pattern:byte(pos); if not p[byte] then -- 创建节点 p[byte] = {}; p[byte].value = byte; -- 父节点 p[byte].parent = p; -- 失败指针 makefailure(p[byte]); end; p = p[byte]; end; p.matched = true; end; -- 初始化树 function init(patternfile) -- 按行读模式字符串 local pattern; for pattern in io.lines(patternfile) do -- 插入字符串 insert(pattern:lower()); end; end; -- 判断字符串是否匹配 function match(str) local p = root; local pos; for pos = 1, str:len() do local byte = str:byte(pos); if p[byte] then p = p[byte]; else p = p.failure; while not (p[byte] or p == root) do p = p.parent; end; end; if p.matched then return true; end; end; return false; end; -- 函数:转换文件 function convert(inname, outname) io.write("正在转换:/"", inname, "/" -> /"", outname, "/"/n"); -- 打开输出文件 local fileout = assert(io.open(outname, "w")); -- 按行读取输入文件 local line; for line in io.lines(inname) do -- 如果不包含匹配字符串,则写到输出文件中 if not match(line:lower()) then fileout:write(line, "/n"); end; end; -- 关闭输入和输出文件 fileout:close(); end; starttime = os.time(); print("初始化..."); init("matchstr.txt"); convert("in//DOSNET.INF", "out//DOSNET.INF"); convert("in//DRVINDEX.INF", "out//DRVINDEX.INF"); convert("in//TXTSETUP.SIF", "out//TXTSETUP.SIF"); endtime = os.time(); io.write("用时:", os.difftime(endtime, starttime), "秒/n");