2013-04-12 58 views
3

我在自動完成下拉列表上使用存儲過程來檢索客戶端列表。某些客戶在名稱中具有'&'(和號)符號,例如'H & M','Marks & Spencers'和用戶想搜索'&'標誌。在MS SQL Server中使用containstable時搜索「&」(&)

當我直接使用&符號時,它使用它作爲分詞器並且不選擇具有'&'符號的列表。

有沒有什麼辦法可以使用'&'和'&'符號的retreive值來搜索表格。

希望我已經解釋了我需要做的事情。

感謝您的幫助!

+0

這可以幫助你:http://stackoverflow.com/questions/995478/sql-server-full-text-search-escape-characters –

+0

其他問題的答案中的兩種不同的方法:[在存儲之前更改文本它在數據庫中](http://stackoverflow.com/questions/3914798/can-i-define-which-word-breakers-to-use-when-building-a-mssql-fulltext-index)或[create使用不同規則確定單詞邊界的自定義DLL](http://support.microsoft.com/kb/1542708/how-to-change-word-break-characters-in-sql-server-full-text-indexing)(更多細節[here](http://stackoverflow.com/questions/7123546/is-there-such-a-thing-as-third-party-sql-server-word-breaker-for-hungarian-langu)) – hvd

回答

0

嘗試這一個 -

DECLARE @char CHAR(1) 
SELECT @char = '&' 

DECLARE @sql NVARCHAR(MAX) 
SELECT @sql = (
    SELECT CHAR(13) + 
     'IF EXISTS(SELECT 1 FROM ' + 
      QUOTENAME(s.name) + '.' + QUOTENAME(o.name) + 
      ' WHERE' + b.cols + ') 
     SELECT table_name = ''[' + s.name + '].[' + o.name + ']'' ' + c.cols +' FROM ' + 
      QUOTENAME(s.name) + '.' + QUOTENAME(o.name) + 
      ' WHERE' + b.cols + ';' 
    FROM sys.objects o 
    JOIN sys.schemas s ON o.[schema_id] = s.[schema_id] 
    JOIN (
     SELECT DISTINCT p.[object_id] 
     FROM sys.partitions p 
     WHERE p.[rows] > 0 
    ) p ON p.[object_id] = o.[object_id] 
    OUTER APPLY (
     SELECT cols = STUFF((
      SELECT 'OR CHARINDEX(''' + @char + ''', ' + QUOTENAME(c.name) + ') > 0 ' 
      FROM sys.columns c 
      JOIN sys.types t ON c.user_type_id = t.user_type_id 
      WHERE t.name IN ('char', 'nchar', 'ntext', 'nvarchar', 'text', 'varchar') 
       AND c.[object_id] = o.[object_id] 
      ORDER BY c.column_id 
      FOR XML PATH(''), TYPE, ROOT).value('root[1]', 'NVARCHAR(MAX)'), 1, 2, '') 
    ) b 
    OUTER APPLY (
     SELECT cols = (
      SELECT ', ' + QUOTENAME(c.name) + ' ' 
      FROM sys.columns c 
      JOIN sys.types t ON c.user_type_id = t.user_type_id 
      WHERE t.name IN ('char', 'nchar', 'ntext', 'nvarchar', 'text', 'varchar') 
       AND c.[object_id] = o.[object_id] 
      ORDER BY c.column_id 
      FOR XML PATH(''), TYPE, ROOT).value('root[1]', 'NVARCHAR(MAX)') 
    ) c 
    WHERE o.[type] = 'U' 
     AND b.cols IS NOT NULL 
    FOR XML PATH(''), TYPE, ROOT).value('root[1]', 'NVARCHAR(MAX)') 

    EXEC sys.sp_executesql @sql 

爲子此查詢搜索所有數據庫的具有表與文本字段 -

DECLARE @phrase NVARCHAR(100) 
SELECT @phrase = '&' 

DECLARE 
     @db_name SYSNAME 
    , @output NVARCHAR(200) 

DECLARE db CURSOR READ_ONLY FAST_FORWARD LOCAL FOR 
    SELECT d.name 
    FROM sys.databases d 
    WHERE d.state_desc = 'ONLINE' 
     AND d.name NOT IN ('tempdb', 'model', 'msdb', 'master') 
      --AND d.name = 'your db name' 
    ORDER BY d.name 

OPEN db 

FETCH NEXT FROM db INTO @db_name 

WHILE @@FETCH_STATUS = 0 BEGIN 

    SELECT @output = CONVERT(NVARCHAR(15), GETDATE(), 114) + ': Find in ' + QUOTENAME(@db_name) + ':' 
    RAISERROR(@output, 0, 1) WITH NOWAIT 

    DECLARE @tsql NVARCHAR(MAX) = ' 
    USE [' + @db_name + ']; 
    DECLARE @sql NVARCHAR(MAX) 
    SELECT @sql = ''USE [' + @db_name + '];'' + (
     SELECT 
      CHAR(13) + 
       ''IF EXISTS(SELECT 1 FROM '' + 
       QUOTENAME(s.name) + ''.'' + QUOTENAME(o.name) + 
       '' WHERE'' + b.cols + '') PRINT ''''['' + 
       s.name + ''].['' + o.name + '']'''';'' 
     FROM sys.objects o 
     JOIN sys.schemas s ON o.[schema_id] = s.[schema_id] 
     JOIN (
      SELECT DISTINCT p.[object_id] 
      FROM sys.partitions p 
      WHERE p.[rows] > 0 
     ) p ON p.[object_id] = o.[object_id] 
     OUTER APPLY (
      SELECT cols = STUFF((
       SELECT ''OR CHARINDEX(''''' + @phrase + ''''', '' + QUOTENAME(c.name) + '') > 0 '' 
       FROM sys.columns c 
       JOIN sys.types t ON c.user_type_id = t.user_type_id 
       WHERE t.name IN (''char'', ''nchar'', ''ntext'', ''nvarchar'', ''text'', ''varchar'') 
        AND c.[object_id] = o.[object_id] 
       ORDER BY c.column_id 
       FOR XML PATH(''''), TYPE, ROOT).value(''root[1]'', ''NVARCHAR(MAX)''), 1, 2, '''') 
     ) b 
     WHERE o.[type] = ''U'' 
      AND b.cols IS NOT NULL 
     FOR XML PATH(''''), TYPE, ROOT).value(''root[1]'', ''NVARCHAR(MAX)'') 

     EXEC sys.sp_executesql @sql 
    ' 

    EXEC sys.sp_executesql @tsql 
    PRINT REPLICATE('-', 100) + CHAR(13) 

    FETCH NEXT FROM db INTO @db_name 

END 

CLOSE db 
DEALLOCATE db 
+0

我低估了這一點,因爲它沒有回答這個問題,它回答了一個完全不同的問題。 – hvd

+0

除非我誤讀,否則您已將問題擴展到在所有表格中搜索,而這不是問題所在。 – hvd

+0

你可以這樣做。如果你這樣做了,國際海事組織仍然會採取完全錯誤的做法,但這將是對這個問題的回答。但'o.name'不會有你期望的值。 – hvd

2

也許是這樣的:

WHERE column LIKE REPLACE(@searchvalue, '&', '/&') ESCAPE '/' 

另一個idea:

DECLARE @randomstring @text 

SET @randomstring ='randomstringthatwillneverbeusedforsearch' 

WHERE REPLACE(column, @searchvalue, @randomstring) LIKE '%'[email protected]+'%' 

雖然不瞭解性能問題。

+0

我認爲你的意思是'列LIKE REPLACE(@searchvalue,'&','/&')ESCAPE'/'',但如果搜索值包含' /'。 – hvd

+0

@ hvd在我看來,兩種方式都一樣嗎?你的方式如何表現不同?但是,如果搜索值中有一個/,則會再次出現問題。 –

+0

'ESCAPE'只適用於模式,而不適用於正在搜索的文本。 '''LIKE'\'ESCAPE'\''是真的,''''LIKE'a'ESCAPE'\''是錯誤的。 – hvd

相關問題