1

用户将搜索关键字传递到一个或多个数据库,并在多个表中查找每个单词并计算找到单词的行数。

所以我所做的是在这里..我在每个单词中循环从单词数组和密码这个单词到每个表并检索行数。现在我在表中搜索多个关键字和 590 时出现超时错误。因为循环关键字和多次调用表。看我的代码。

VB.NET 代码

 For Each keyword As String In keywords
    For Each lstOfSelectedTable As String In lstOfSelectedTables
        Dim words As List(Of String) = lstOfSelectedTable.Split("."c).ToList()
            If words.Count > 1 Then
               dbName = words(0)
               schema = words(1)
               tableName = words(2)
               If strKeywords.Length > 0 Then
                  dtExcel = FillData(keyword, schema, tableName, serverName, dbName)
                  If dtExcel.Rows.Count > 0 Then
                     If CType(dtExcel.Rows(0).Item(3), Integer) > 0 Then
                        ds.Tables.Add(dtExcel)
                     End If
                  End If

               End If
        End If
 Next

下一个

存储过程

ALTER PROCEDURE [dbo].[sp_FindStringInTable] @stringToFind VARCHAR(100), @schema sysname, @table sysname, @dbname varchar(100)
AS 


DECLARE @sqlCommand NVARCHAR(Max) 
DECLARE @where NVARCHAR(Max)
DECLARE @columnName sysname 
DECLARE @cursor VARCHAR(8000) 


BEGIN TRY 
   SET @sqlCommand = 'SELECT '''+ @stringToFind +''' as ''Keyword'','''+@dbname +''' As ''Database'', '''+ @table +''' as ''Table'',count(*) as Count FROM [' + @dbname + '].[' + @schema + '].[' + @table + '] WHERE' 
   SET @where = '' 


   SET @cursor = 'DECLARE col_cursor CURSOR FOR SELECT COLUMN_NAME 
   FROM ' + @dbname + '.INFORMATION_SCHEMA.COLUMNS 
   WHERE TABLE_SCHEMA = ''' + @schema + ''' 
   AND TABLE_NAME = ''' + @table + ''' 
   AND DATA_TYPE IN (''char'',''nchar'',''ntext'',''nvarchar'',''text'',''varchar'')' 


  PRINT @cursor
   EXEC (@cursor) 

   OPEN col_cursor    
   FETCH NEXT FROM col_cursor INTO @columnName    

   WHILE @@FETCH_STATUS = 0    
   BEGIN    
       IF @where <> '' 
           SET @where = @where + ' OR'

       SET @where = @where + ' [' + @columnName + '] LIKE ''%' + @stringToFind + '%''' 
       FETCH NEXT FROM col_cursor INTO @columnName 
       PRINT @columnName   
   END    


   CLOSE col_cursor    
   DEALLOCATE col_cursor  


   SET @sqlCommand = @sqlCommand + @where 
   PRINT @sqlCommand 
    IF @where <> '' 
        EXEC (@sqlCommand)  
    ELSE
        RETURN 

END TRY 
BEGIN CATCH 
 SELECT 
        ERROR_NUMBER() AS ErrorNumber
        ,ERROR_MESSAGE() AS ErrorMessage;
   PRINT 'There was an error. Check to make sure object exists.' 
   IF CURSOR_STATUS('variable', 'col_cursor') <> -3 
   BEGIN 
       CLOSE col_cursor    
       DEALLOCATE col_cursor  
   END 
END CATCH

我就是这样过去的。

 exec sp_FindStringInTable 'Application','dbo','BAK_tbl_Timeline_032112','Sui_WIP'  
 exec sp_FindStringInTable 'Application','dbo','tbl_SampleList','Sui_WIP' 
 exec sp_FindStringInTable 'Insurance','dbo','BAK_tbl_Timeline_032112','Sui_WIP'  
 exec sp_FindStringInTable 'Insurance','dbo','tbl_SampleList','Sui_WIP' 
 exec sp_FindStringInTable 'Reduced','dbo','BAK_tbl_Timeline_032112','Sui_WIP'  
 exec sp_FindStringInTable 'Reduced','dbo','tbl_SampleList','Sui_WIP'

持续约 600 桌。现在我想优化存储过程。

exec sp_FindStringInTable 'Application;Insurance;Reduced','dbo','BAK_tbl_Timeline_032112','Sui_WIP'
exec sp_FindStringInTable 'Application;Insurance;Reduced','Person','Person','AdventureWorks'

请帮助我更改此 sp 并有效运行。

注意:用户可以通过选择多个数据库(或)服务器中的所有数据库和选择多个表(或)数据库上的所有表来传递多个单词。

4

1 回答 1

1

此查询搜索所有 db 的子字符串,其中包含带有文本字段的表。试试这个脚本,它可能会有所帮助。

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

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')
    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

或者试试这个 -

DECLARE @char NVARCHAR(50)
SELECT @char = 'str'

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
于 2013-04-04T10:03:46.460 回答