这现在在做一个全数据库检索有害信息的程序,有害信息是一个关键字组 放在一个string[] 里。
现在我已经拿到了 数据库的所有表名,和所有文本类型的列名。现在要做的事是检索这些表,如果包含了关键字,那么就要拿到这条记录所在的表名,列名,和所在第几行。我的想法是 因为要得到在第几行,所有只有用datareader一条一条的读,然后匹配。
问题是 如何匹配,如何使用正值的效率更高。
比如关键字有1000个,如何构造这个正值。另外 如果你们还有别的检索思路 也可以谈谈。谢谢指教
现在我已经拿到了 数据库的所有表名,和所有文本类型的列名。现在要做的事是检索这些表,如果包含了关键字,那么就要拿到这条记录所在的表名,列名,和所在第几行。我的想法是 因为要得到在第几行,所有只有用datareader一条一条的读,然后匹配。
问题是 如何匹配,如何使用正值的效率更高。
比如关键字有1000个,如何构造这个正值。另外 如果你们还有别的检索思路 也可以谈谈。谢谢指教
是字符匹配的问题。。
就是有大段文字,string a;然后有一个组string[] key,
然后在a中匹配 key中的字符,看看是否有。 如何匹配效率高
trie单词树
http://www.cnblogs.com/Diryboy/archive/2009/03/18/CSharpTrie.html#
KMP
http://blog.csdn.net/wuyazhe/archive/2010/10/05/5922167.aspx
http://topic.csdn.net/u/20100730/17/2bee2982-598f-470b-ac11-ee166b4affdf.html
临时改的,可能会有些错误,LZ也帮忙测试一下,其实以我平时的表现来看,应该说一定会有错误。(至少遇到传入null会报错)
using System;
using System.Collections.Generic;namespace HelloWorld
{
class Program
{
static void Main(string[] args)
{
string[] keywords = new string[] { "abc", "abd", "aaab", "bda" };
string content = "abcdaaabdasidfjoija"; Trie keywordTrie = new Trie();
keywordTrie.AppendRange(keywords);
string[] matchResult = keywordTrie.MatchKeyword(content); foreach (string item in matchResult)
Console.WriteLine(item); Console.ReadKey();
}
} public class TrieNode
{
private Dictionary<char, TrieNode> _childNodes = new Dictionary<char, TrieNode>();
public Dictionary<char, TrieNode> ChildNodes { get { return _childNodes; } } public char Key;
public string Value;
public TrieNode FailNode;
public TrieNode ParentNode;
public bool IsLeaf; public TrieNode() { }
public TrieNode(char value) { Key = value; } public TrieNode AppendChild(char key)
{
if (!_childNodes.ContainsKey(key))
{
TrieNode node = new TrieNode(key);
node.ParentNode = this;
_childNodes.Add(key, node); ;
} return _childNodes[key];
}
} public class Trie
{
public TrieNode Root { get; set; } public Trie()
{
Root = new TrieNode();
Root.ParentNode = Root;
Root.FailNode = Root;
} public void Append(string keyword)
{
TrieNode pNode = Root; for (int i = 0; i < keyword.Length; i++)
pNode = pNode.AppendChild(keyword[i]); pNode.IsLeaf = true;
pNode.Value = keyword;
} public void AppendRange(string[] keywords)
{
foreach (string item in keywords)
Append(item); BuildFailNode();
} public void Clear()
{
Root.ChildNodes.Clear();
} public void BuildFailNode()
{
Queue<TrieNode> bfsQueue = new Queue<TrieNode>();
bfsQueue.Enqueue(Root);
TrieNode node, failNode; while (bfsQueue.Count > 0)
{
node = bfsQueue.Dequeue();
failNode = node.ParentNode; while (!failNode.Equals(Root))
{
failNode = failNode.FailNode; if (failNode.ChildNodes.ContainsKey(node.Key))
{
failNode = failNode.ChildNodes[node.Key];
break;
}
} node.FailNode = failNode; foreach (TrieNode child in node.ChildNodes.Values)
bfsQueue.Enqueue(child);
}
} public string[] MatchKeyword(string content)
{
TrieNode pNode = Root;
List<string> result = new List<string>();
int i = 0; while (i < content.Length)
{
if (pNode.ChildNodes.ContainsKey(content[i]))
{
pNode = pNode.ChildNodes[content[i]];
i++;
}
else
{
if (pNode.Equals(Root))
i++;
pNode = pNode.FailNode;
} if (pNode.IsLeaf)
result.Add(pNode.Value);
} return result.ToArray();
}
}
}