asp sql like分词查询

SQL&Server全文索引的个人总结(上)&-关于中文分词
大家都知道LIKE查询很慢,全文索引就是事先做好相关的索引,表示哪个主题词可以在哪些记录里找到,甚至事先计算好RANK,检索时可以把相关度高的先列出来,这可以大大提高检索的速度。
打个比方,你有很多的小抽屉,每个抽屉里面放一些杂物,假如你要找东西,最原始的方法就是一个个抽屉翻,这就是没有索引的情况。
假如聪明一点,给抽屉编号(唯一键),把哪个号码的抽屉有什么东西记录在纸上,找东西先看看这张纸,这就是普通索引,假如你要知道哪个抽屉有什么,你可以在纸上迅速找到抽屉号码(大家知道这是使用查找树),然后得到相关的信息,这种情况普通索引是很快的;但是要找到一个特定的东西哪些抽屉有,你就要把整张纸遍历一次,这就是LIKE查询,假如你要找哪些抽屉同时有2种甚至更多种物品,LIKE就更加繁琐了。假如一个表有上千万的纪录,大家可以想象查询的代价。
可以换一个思路,另外找张纸,记录一样东西存在于哪些抽屉:
夹子:1,3,4,5,6,9,12...
钱币:2,3,4,7,12...
药丸:1,3,5,6...
这样找到某样东西或者某几样东西都很容易。
全文索引和普通的SQL索引有很多的区别:
普通 SQL 索引
存储时受定义它们所在的数据库的控制。
存储在文件系统中,但通过数据库管理。
每个表允许有若干个普通索引。
每个表只允许有一个全文索引。
当对作为其基础的数据进行插入、更新或删除时,它们自动更新。
将数据添加到全文索引称为填充,全文索引可通过调度或特定请求来请求,也可以在添加新数据时自动发生。
在同一个数据库内分组为一个或多个全文目录。
使用 SQL Server 企业管理器、向导或 Transact-SQL 语句创建和除去。
使用 SQL Server 企业管理器、向导或存储过程创建、管理和除去。
使用全文索引的话,可以看看下面的帖子(感谢大力和lihonggen0):
???? 如何在sqlserver中建立全文索引:???? ??? ???? 如何使用image字段:????
发现大家有一个常问的问题,就是关于以下的信息的:
查询子句只包含被忽略的词
这是因为使用一些很简单的词,比如'是',进行查询的缘故。
提出的解决办法不外乎是把C:\Program Files\Microsoft SQL Server\MSSQL\FTDATA\SQLServer\Config\noise.chs 清空
觉得这种方法是不可取的,大家打开这个文件看看,发现里面是一些这样的词:is,are,be,at,我,是
这些词都是频率很高的词,而且在查询中的意义不大,就好像几乎每个抽屉里面都有纸屑一样,为这些词作索引得不偿失,所以全文引擎把这些词称为干扰词不做索引,个人觉得在应用中过滤这些词然后向用户提出友好的提示更好,而不是使用清空noise.chs粗暴的对待全文引擎。比方大家可以看看在Google中搜索“的”
-------------------------------------------------------------------------
另外谢谢ghj,一个很重要的东西遗漏了,与一般的索引立即更新不同,全文索引一般是定期维护索引的,所以对于频繁更新的数据不合适,需要做全文索引的对象一般都是论文网页之类,还算适合拉!
个人觉得我的数据库没有代表性,所以也不细说:作索引的时候,CPU和内存使用都很高,时间也很长(下面我的数据库是整个晚上),完成以后并不需要使用很多的系统资源,多个全文查询并发的时候也有不小的CPU消耗,但是比LIKE强。
我的系统上数据库是123M,太小,使用全文索引没有感到特别的优势,但是可以想想对于GOOGLE那样的海量数据,使用LIKE是不可想象的:)当然别人也没有使用关系数据库。
以上网友发言只代表其个人观点,不代表新浪网的观点或立场。trackbacks-0
随笔分类 - Sql Server全文检索
摘要: 今天偶然搜到msdn上放出来的信息, SQL Server 2008 未来将不再包含全文检索功能, 但哪个版本未定,再研究此功能已经没多大意思了, 可怜之前我们还花了不少时间仔细研究了这个技术, 最终因为中文分词不行才抛弃了它.推荐资料:SQL Server 2008 中已被取代的全文檢索搜尋功能/zh-tw/library/cc646010(v=SQL.100).aspxSQL Server 2008 R2 中不推荐使用的全文搜索功能/zh-cn/library/cc646010.asp
BobLiu 阅读(976) |
摘要: SQL server 全文检索使用中有时会遇到下面这个错误:7625: 全文表或全文索引视图在其全文索引列中有多个 LCID。English translation: Full-text table or indexed view has more than one LCID among its full-text indexed columns.见外国一帖子, 忘记链接了,照抄如下:It seems that in your full-text query are querying more than one column and one of the columns is using a
BobLiu 阅读(252) |
摘要: 一. 看了几篇不错的帖子, SQL Server 2008 Full-Text Search Overview(SQL Server 2008全文检索概览)/galaxyyao/archive//1390139.html全文索引 /liulun/articles/1368655.html先照抄一段:Q:为什么要Full-text search(全文检索)?A:因为对文字的查询速度慢(不建议在文字上建索引也就是这个道理)Q:和2005有区别么?A;当然有区别,名字前都加了个integrat
BobLiu 阅读(2460) |
摘要: 全文索引填充:/zh-cn/library/ms142575(v=SQL.100).aspxSql Server 2008 全文索引支持填充方式有三种:1.完全填充创建全文索引时找不到在哪里选择完全填充,原来,它默认只要创建好全文检索就来一次完全填充。2.基于更改跟踪的填充 在跟踪更改处选择自动就行了,这就ok了,太他妈省心了。如果选择手动,他可是不管给你自动填充的。 3.基于时间戳的增量填充基本用不到,因为他要求你表里必须具有 timestamp 数据类型的列,没有这种列,就甭考虑了。总结:使用跟踪更改的自动填充方式,就不用操心定期计划更新全
BobLiu 阅读(892) |
摘要: 1.Like 模糊查询例如: select * from table where productdes like '%cad%'它不能利用索引查询, 只能是全表扫描, 效率较低, 而且不会分词, 只能按关键字老老实实的查, 但查询实时数据, 结果准确.2.SQL Server 2008全文检索为了提高效率, 换用sql server的全文检索, 怎么建全文检索就此略去, 不提, 只看查询方法.例如: select * from table where contains(ProductDesc, '*cad*')它查询的效率很高, 支持中文分词(但好不好就另说了)
BobLiu 阅读(4812) |
摘要: 这两天做了一下测试, 发现MS SQL Server 2008 full-text search 全文检索对英文内容的检索有个很大的问题, 就是它只支持前缀模糊查询(即*号在后面), 而不支持后缀模糊查询(即*号在前面), 举个例子:1.不用全文检索, 用传统的like, 能模糊查询到所有带cad后缀的英文条目.select * fromTable1 where Productname like '%cad'结果AutocadTT cadcad2.用全文检索, 用contains, 却不能模糊查询到所有带cad后缀的英文条目.select * fromTable1 where
BobLiu 阅读(1614) |1303人阅读
Q:站内搜索为什么不能使用Like模糊查找
A:模糊契合度太低,匹配关键字之间不能含有其他内容。最重要的是它会造成全表扫描,效率底下,即使使用视图,也会造成数据库服务器&亚历山大&
Lucene简介:
Lucene.Net只是一个全文检索开发包,不是一个成型的搜索引擎
它提供了类似SQLServer数据库正式版中的全文检索功能的索引库
你把数据扔给Lucene.Net,【Lucene.Net只针对文本信息建立索引,所以他只接收文本信息,如果不是文本信息,则要转换为文本信息】它会将文本内容分词后保存在索引库中,当用户输入关键字提交查询时,Lucene.Net从索引库中检索关键字数据,所以搜索速度非常快,适合于用户开发自己站内的搜索引擎
A:即将&不是所有痞子都叫一毛&文本内容通过分词算法 &分割成为“不是” “所有” “痞子” “都” “叫” &一毛& &。 但是Lucene.Net内置分词算法对中文支持不是很好,以下会使用国内较为流行的分词算法 -- 盘古分词
以下是运行图解:
下面以用户查询数据库Book表 & 内容描述【对应字段名:ContentDescription】中包含其输入的关键字key的数据 &演示Lucene.Net使用
运行界面效果如下:
本人使用的盘古分词版本为V2.3.1.0& Lucene.Net为2.9
在项目下新建Dict文件以及dll文件包含Lucene与盘古分词所需的组件及文件信息如图示
1、项目添加对dll文件夹中四个程序集的引用
2、添加图书搜索页面SearchBlogs.aspx代码如下:
&%&@&Page&Language=&C#&&AutoEventWireup=&true&&CodeBehind=&SearchBook.aspx.cs&&Inherits&=&BookShop.Web.SearchBook&&%&
&!&DOCTYPE&html&PUBLIC&&-//W3C//DTD XHTML 1.0 Transitional//EN&&&http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd&&
&&html&xmlns&=&http://www.w3.org/1999/xhtml&&
&&head&runat&=&server&&
&&&&&title&&&/&title&
&&&&&form&id=&form1&&runat=&server&&
&&&&&asp&:&TextBox&ID&=&txtSerach&&runat&=&server&&Width&=&494px&&&/asp&:&TextBox&
&&&&&asp&:&Button&ID&=&btnSearch&&runat&=&server&&onclick&=&btnSearch_Click&&Text&=&搜索&&/&
&&&&&asp&:&Button&ID&=&CreateView&&runat&=&server&&onclick&=&CreateView_Click&&Text&=&创建索引&&/&
&&&&&div&&
&&&&&&&&&&asp:&Repeater&ID&=&Repeater1&&runat&=&server&&
&&&&&&&&&&ItemTemplate&
&&&&&&&&&&table&
&&&&&&&&&&&&&&&&&&tbody&
&&&&&&&&&&&&&&&&&&&&&&tr&
&&&&&&&&&&&&&&&&&&&&&&&&&&td&style&=&font-size&:&color: red&&width=&650&&
&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&a&&id&=&link_prd_name&&href&='&%&#&Eval(&Id&,&/book.aspx?id={0}&)&%&&'
&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&target&=&_blank&&name&=&link_prd_name&&
&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&%#&Eval(&&Title&)&%&
&&&&&&&&&&&&&&&&&&&&&&&&&&&&&/&a&
&&&&&&&&&&&&&&&&&&&&&&&&&/&td&
&&&&&&&&&&&&&&&&&&&&&/&tr&
&&&&&&&&&&&&&&&&&&&&&&tr&
&&&&&&&&&&&&&&&&&&&&&&&&&&td&align&=&left&&
&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&span&style&=&font-size&: 12&line-height: 20px&&
&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&%#&Eval(&&ContentDescription&)&%&&/&span&&
&&&&&&&&&&&&&&&&&&&&&&&&&/&td&
&&&&&&&&&&&&&&&&&&&&&/&tr&
&&&&&&&&&&&&&&&&&/&tbody&
&&&&&&&&&&&&&/&table&
&&&&&&&&&/&ItemTemplate&
&&&&&&&&&/&asp:&Repeater&&
&&&&&/div&&
&&&&&/form&&
3、后台调用
using&System.Collections.G
using&System.IO;
using&BookShop.BLL;
using&Lucene.Net.Analysis.PanGu;
using&Lucene.Net.D
using&Lucene.Net.I
using&Lucene.Net.S
using&Lucene.Net.S
namespace&BookShop.Web {
&&&&public&partial&class&SearchBook&: System.Web.UI.&Page&{
&&&&&&&&protected&void&Page_Load(&object&sender,&EventArgs&e) {
& & & &&//创建索引事件& 可以防止在用户点击查询事件前执行 去掉页面中的&创建索引&按钮
&&&&&&&&protected&void&CreateView_Click(&object&sender,&EventArgs&e) {
&&&&&&&&&&&&string&indexPath =&@&C:\luceneTest&&;&//索引文档保存位置
&&&&&&&&&&&&FSDirectory&directory =&FSDirectory&.Open(&new&DirectoryInfo&(indexPath),&new&NativeFSLockFactory&());
&&&&&&&&&&&&bool&isUpdate =&IndexReader&.IndexExists(directory);&//是否存在索引库文件夹以及索引库特征文件
&&&&&&&&&&&&if&(isUpdate) {
&&&&&&&&&&&&&&&&//如果索引目录被锁定(比如索引过程中程序异常退出或另一进程在操作),则解锁
&&&&&&&&&&&&&&&&if&(IndexWriter&.IsLocked(directory)) {
&&&&&&&&&&&&&&&&&&&&IndexWriter&.Unlock(directory);
&&&&&&&&&&&&&&& }
&&&&&&&&&&& }
&&&&&&&&&&&&//创建索引库对象&& new PanGuAnalyzer()指定使用盘古分词进行切词
&&&&&&&&&&&&IndexWriter&writer =&new&IndexWriter(directory,&new&PanGuAnalyzer&(), !isUpdate, Lucene.Net.Index.IndexWriter&.&MaxFieldLength.UNLIMITED);
&&&&&&&&&&&&BooksManager&bookManager =&new&BooksManager();
&&&&&&&&&&&&List&&Model.Books&& bookList = bookManager.GetModelList(&&&&);
&&&&&&&&&&&&foreach&(var&book&in&bookList) {
&&&&&&&&&&&&&&&&Document&document =&new&Document();&//new 一篇文档 对象
&&&&&&&&&&&&&&&&//所有字段的值都将以字符串类型保存
&&&&&&&&&&&&&&&&//Field.Store表示是否保存字段原值。指定Field.Store.YE的字段在检索时才能用document.Get取出来值& NOT_ANALYZED指定不按照分词后的结果保存
&&&&&&&&&&&&&&& document.Add(&new&Field&(&&id&, book.Id.ToString(),&Field&.Store&.YES,&Field&.Index&.NOT_ANALYZED));
&&&&&&&&&&&&&&& document.Add(&new&Field&(&&title&, book.Title,&Field&.Store&.YES,&Field&.Index&.ANALYZED, Lucene.Net.Documents.Field&.TermVector&.WITH_POSITIONS_OFFSETS));
&&&&&&&&&&&&&&&&//Field.Index. ANALYZED指定文章内容按照分词后结果保存& 否则无法实现后续的模糊查找& WITH_POSITIONS_OFFSETS指示不仅保存分割后的词 还保存词之间的距离
&&&&&&&&&&&&&&& document.Add(&new&Field&(&&content&, book.ContentDescription,&Field&.Store&.YES,&Field.&Index&.ANALYZED, Lucene.Net.Documents.Field&.TermVector&.WITH_POSITIONS_OFFSETS));
&&&&&&&&&&&&&&& writer.AddDocument(document);&//文档写入索引库
&&&&&&&&&&& }
&&&&&&&&&&& writer.Close();
&&&&&&&&&&& directory.Close();&//不要忘了Close,否则索引结果搜不到
&&&&&&&&protected&void&btnSearch_Click(&object&sender,&EventArgs&e) {
&&&&&&&&&&&&string&indexPath =&@&C:\luceneTest&&;
&&&&&&&&&&&&FSDirectory&directory =&FSDirectory&.Open(&new&DirectoryInfo&(indexPath),&new&NoLockFactory&());
&&&&&&&&&&&&IndexReader&reader =&IndexReader&.Open(directory,&true);
&&&&&&&&&&&&IndexSearcher&searcher =&new&IndexSearcher(reader);&//Index:索引
&&&&&&&&&&&&//搜索条件
&&&&&&&&&&&&PhraseQuery&query =&new&PhraseQuery();
&&&&&&&&&&&&//把用户输入的关键字进行分词
&&&&&&&&&&&&foreach&(string&word&in&Common.SplitContent&.SplitWords(txtSerach.Text.ToLower())) {
&&&&&&&&&&&&&&& query.Add(&new&Term&(&&content&, word));
&&&&&&&&&&& }
&&&&&&&&&&& query.SetSlop(100);&//指定关键词相隔最大距离
&&&&&&&&&&&&//TopScoreDocCollector盛放查询结果的容器
&&&&&&&&&&&&TopScoreDocCollector&collector =&TopScoreDocCollector&.create(1000,&true&);
&&&&&&&&&&& searcher.Search(query,&null&, collector);//根据query查询条件进行查询,查询结果放入collector容器
&&&&&&&&&&&&//TopDocs 指定0到GetTotalHits() 即所有查询结果中的文档
&&&&&&&&&&&&ScoreDoc&[] docs = collector.TopDocs(0, collector.GetTotalHits()).scoreD
&&&&&&&&&&&&//展示数据实体对象集合
&&&&&&&&&&&&List&&Model.Books&& bookResult =&new&List&&Model.Books&&();
&&&&&&&&&&&&for&(int&i = 0; i & docs.L i++) {
&&&&&&&&&&&&&&&&//需要获得文档的详细内容的时候通过searcher.Doc来根据文档id来获得文档的详细内容对象Document
&&&&&&&&&&&&&&&&int&docId = docs[i].//得到查询结果文档的id(Lucene内部分配的id)
&&&&&&&&&&&&&&&&Document&doc = searcher.Doc(docId);//找到文档id对应的文档详细信息
&&&&&&&&&&&&&&& Model.&Books&book =&new&Model.&Books();
&&&&&&&&&&&&&&& book.Title = doc.Get(&&title&&);
&&&&&&&&&&&&&&&&//book.ContentDescription = doc.Get(&content&);//未使用高亮
&&&&&&&&&&&&&&&&//搜索关键字高亮显示
&&&&&&&&&&&&&&& book.ContentDescription = Common.SplitContent&.HightLight(txtSerach.Text, doc.Get(&content&&));
&&&&&&&&&&&&&&& book.Id =&Convert&.ToInt32(doc.Get(&id&&));
&&&&&&&&&&&&&&& bookResult.Add(book);
&&&&&&&&&&& }
&&&&&&&&&&&&//设置Repeater1& 绑定查询结果集合
&&&&&&&&&&& Repeater1.DataSource = bookR
&&&&&&&&&&& Repeater1.DataBind();
4、使用到的公共类&Common下的SplitContent类
using&System.Collections.G
using&System.IO;
using&Lucene.Net.A
using&Lucene.Net.Analysis.PanGu;
using&PanGu;
namespace&mon {
&&&&public&class&SplitContent&{
&&&&&&&&public&static&string[] SplitWords(&string&content) {
&&&&&&&&&&&&List&&string&& strList =&new&List&&string&&();
&&&&&&&&&&&&Analyzer&analyzer =&new&PanGuAnalyzer();
&&&&&&&&&&&&TokenStream&tokenStream = analyzer.TokenStream(&&&,&new&StringReader&(content));
&&&&&&&&&&& Lucene.Net.Analysis.&Token&token =&null&;
&&&&&&&&&&&&while&((token = tokenStream.Next()) !=&null&) {&//Next继续分词 直至返回null
&&&&&&&&&&&&&&& strList.Add(token.TermText());&//得到分词后结果
&&&&&&&&&&& }
&&&&&&&&&&&&return&strList.ToArray();
&&&&&&&&//需要添加PanGu.HighLight.dll的引用
&&&&&&&&///&&summary&
&&&&&&&&///&搜索结果高亮显示
&&&&&&&&///&&/summary&
&&&&&&&&///&&param name=&keyword&&&关键字&&/param&
&&&&&&&&///&&param name=&content&&&搜索结果&&/param&
&&&&&&&&///&&returns&&高亮后结果&&/returns&
&&&&&&&&public&static&string&HightLight(&string&keyword,&string&content) {
&&&&&&&&&&&&//创建HTMLFormatter,参数为高亮单词的前后缀
&&&&&&&&&&& PanGu.HighLight.&SimpleHTMLFormatter&simpleHTMLFormatter =
&&&&&&&&&&&&&&&&&&&new&PanGu.HighLight.SimpleHTMLFormatter&(&&&font color=\&red\&&&b&&,&&&/b&&/font&&&);
&&&&&&&&&&&&//创建 Highlighter ,输入HTMLFormatter 和 盘古分词对象Semgent
&&&&&&&&&&& PanGu.HighLight.&Highlighter&highlighter =
&&&&&&&&&&&&&&&&&&&&&&&&&&&&new&PanGu.HighLight.Highlighter&(simpleHTMLFormatter,
&&&&&&&&&&&&&&&&&&&&&&&&&&&&new&Segment&());
&&&&&&&&&&&&//设置每个摘要段的字符数
&&&&&&&&&&& highlighter.FragmentSize = 50;
&&&&&&&&&&&&//获取最匹配的摘要段
&&&&&&&&&&&&return&highlighter.GetBestFragment(keyword, content);
5、使用Dict、Dll文件夹以及盘古分词的开发文档&&&&&&&&实际应用中当然不会存在上图中的创建索引按钮&&而且索引需随数据库数据同步更新&&&本章暂不介绍
* 以上用户言论只代表其个人观点,不代表CSDN网站的观点或立场
访问:32398次
排名:千里之外
转载:71篇
(8)(29)(6)(16)(19)sql语句过长,求能分词处理的查询语句
[问题点数:20分,结帖人ronanljy2]
sql语句过长,求能分词处理的查询语句
[问题点数:20分,结帖人ronanljy2]
不显示删除回复
显示所有回复
显示星级回复
显示得分回复
只显示楼主
相关帖子推荐:
本帖子已过去太久远了,不再提供回复功能。

我要回帖

更多关于 asp sql like 的文章

 

随机推荐