2009-02-03 2 views
7

(transact-sql을 통해) 모든 데이터베이스 문자열 필드를 다듬을 수있는 빠른 방법이 있는지 알고 계십니까?모든 데이터베이스 필드 다듬기

+0

열의 길이를 해당 열의 값에서 찾을 수있는 최대 길이로 업데이트 하시겠습니까?나는 Name이 VARCHAR (200)이고 10000 개의 행 모두에서 VARCHAR (23)으로 열을 수정하기 위해 가장 긴 Name이 23 인 Person 테이블에서 Name을 갖는 것과 같은 의미인가요? –

답변

19

없음 커서를. 출력을 복사하여 붙여 넣습니다. varchar (max)가없는 SQL 2000에서도 작동합니다. 원하는 경우 각 업데이트의 끝 부분에 GO 라인을 추가하기 위해 쉽게 확장 할 수 있습니다.

SELECT SQL 
FROM (  SELECT t.TABLE_CATALOG 
       ,  t.TABLE_SCHEMA 
       ,  t.TABLE_NAME 
       ,  0    SORT 
       ,  'UPDATE ' + QUOTENAME(t.TABLE_CATALOG) + '.' + QUOTENAME(t.TABLE_SCHEMA) + '.' + QUOTENAME(t.TABLE_NAME)  SQL 
       FROM INFORMATION_SCHEMA.TABLES  t 
       JOIN INFORMATION_SCHEMA.COLUMNS  c 
        ON t.TABLE_CATALOG = c.TABLE_CATALOG 
        AND t.TABLE_SCHEMA = c.TABLE_SCHEMA 
        AND t.TABLE_NAME = c.TABLE_NAME 
       WHERE t.TABLE_TYPE = 'BASE TABLE' 
       AND c.DATA_TYPE  IN ('char','nchar','varchar','nvarchar') 
       GROUP BY  t.TABLE_CATALOG 
       ,    t.TABLE_SCHEMA 
       ,    t.TABLE_NAME 
       UNION ALL 
       SELECT x.TABLE_CATALOG 
       ,  x.TABLE_SCHEMA 
       ,  x.TABLE_NAME 
       ,  CASE WHEN x.COLUMN_NAME_MIN  = y.COLUMN_NAME 
           THEN 1 
           ELSE 2 
         END              SORT 
       ,  CASE WHEN x.COLUMN_NAME_MIN  = y.COLUMN_NAME 
           THEN 'SET  ' 
           ELSE ' ,  ' 
         END + y.SQL            SQL 
       FROM (  SELECT t.TABLE_CATALOG 
           ,  t.TABLE_SCHEMA 
           ,  t.TABLE_NAME 
           ,  MIN(c.COLUMN_NAME)  COLUMN_NAME_MIN 
           FROM INFORMATION_SCHEMA.TABLES  t 
           JOIN INFORMATION_SCHEMA.COLUMNS  c 
            ON t.TABLE_CATALOG = c.TABLE_CATALOG 
            AND t.TABLE_SCHEMA = c.TABLE_SCHEMA 
            AND t.TABLE_NAME = c.TABLE_NAME 
           WHERE t.TABLE_TYPE = 'BASE TABLE' 
           AND c.DATA_TYPE  IN ('char','nchar','varchar','nvarchar') 
           GROUP BY  t.TABLE_CATALOG 
           ,    t.TABLE_SCHEMA 
           ,    t.TABLE_NAME 
         )  x 
       JOIN (  SELECT t.TABLE_CATALOG 
           ,  t.TABLE_SCHEMA 
           ,  t.TABLE_NAME 
           ,  c.COLUMN_NAME 
           ,  QUOTENAME(c.COLUMN_NAME) + ' = LTRIM(RTRIM(' + QUOTENAME(c.COLUMN_NAME) + '))' SQL 
           FROM INFORMATION_SCHEMA.TABLES  t 
           JOIN INFORMATION_SCHEMA.COLUMNS  c 
            ON t.TABLE_CATALOG = c.TABLE_CATALOG 
            AND t.TABLE_SCHEMA = c.TABLE_SCHEMA 
            AND t.TABLE_NAME = c.TABLE_NAME 
           WHERE t.TABLE_TYPE = 'BASE TABLE' 
           AND c.DATA_TYPE  IN ('char','nchar','varchar','nvarchar') 
         )  y 
        ON x.TABLE_CATALOG = y.TABLE_CATALOG 
        AND x.TABLE_SCHEMA = y.TABLE_SCHEMA 
        AND x.TABLE_NAME = y.TABLE_NAME 
     )  x 
ORDER BY  x.TABLE_CATALOG 
,    x.TABLE_SCHEMA 
,    x.TABLE_NAME 
,    x.SORT 
,    x.SQL 
+0

+1. 내 하루를 아무 것도 아닌 것처럼 구했다. –

13

귀하의 질문은 다소 모호하지만 다음은 귀하가하는 것입니까?

UPDATE mytable SET mycolumn= LTRIM(RTRIM(mycolumn)) 
'MYTABLE'표에서 'mycolumn'열에서 모든 값에서 모두 선행 및 후행 공백 제거

. 업데이트 문을 작성하여 INFORMATION_SCHEMA.COLUMNS 및 RTRIM VARCHAR를/NVARCHAR 열 이상

2

그냥 당신이 VARCHAR 문자열 필드가 아닌 CHAR 필드 :

그 같으면에서 트림을하고 있는지 확인 많이 좋아하지 않아. 사람이 커서없이이 작업을 수행하는 방법을 알고있는 경우

+0

선행 공백은 어떻게됩니까? – alyssackwan

+0

좋아, LTRIM CHAR 열에 몇 가지 장점이 있습니다. RTRIM이 아닙니다. – BradC

3

, 그것을 게시하지 않습니다하십시오

DECLARE @CRLF AS varchar(2) 
SET @CRLF = CHAR(13) + CHAR(10) 
DECLARE @TAB AS varchar(1) 
SET @TAB = CHAR(9) 

DECLARE @template AS varchar(max) 
SET @template = 'UPDATE {@OBJECT_NAME}' + @CRLF + 'SET {@column_list}' 

DECLARE c CURSOR FAST_FORWARD 
    FOR SELECT DISTINCT 
       QUOTENAME(T.TABLE_CATALOG) + '.' + QUOTENAME(T.TABLE_SCHEMA) 
       + '.' + QUOTENAME(T.TABLE_NAME) AS [OBJECT_NAME] 
     FROM INFORMATION_SCHEMA.TABLES AS T 
     INNER JOIN INFORMATION_SCHEMA.COLUMNS AS C 
       ON T.TABLE_CATALOG = C.TABLE_CATALOG 
        AND T.TABLE_SCHEMA = C.TABLE_SCHEMA 
        AND T.TABLE_NAME = C.TABLE_NAME 
        AND T.TABLE_TYPE = 'BASE TABLE' 
        AND C.DATA_TYPE IN ('varchar', 'nvarchar') 
     ORDER BY 1 

DECLARE @OBJECT_NAME AS sysname 

OPEN c 

FETCH NEXT FROM c INTO @OBJECT_NAME 
WHILE @@FETCH_STATUS = 0 
    BEGIN 
     DECLARE @column_list AS varchar(max) 
     SELECT @column_list = COALESCE(@column_list + @CRLF + @TAB + ',', '') 
       + QUOTENAME(C.COLUMN_NAME) + ' = LTRIM(RTRIM(' 
       + QUOTENAME(C.COLUMN_NAME) + '))' 
     FROM INFORMATION_SCHEMA.COLUMNS AS C 
     WHERE C.DATA_TYPE IN ('varchar', 'nvarchar') 
       AND QUOTENAME(C.TABLE_CATALOG) + '.' 
       + QUOTENAME(C.TABLE_SCHEMA) + '.' + QUOTENAME(C.TABLE_NAME) = @OBJECT_NAME 
     ORDER BY C.ORDINAL_POSITION 

     PRINT REPLACE(REPLACE(@template, '{@column_list}', @column_list), 
         '{@OBJECT_NAME}', @OBJECT_NAME) 

     FETCH NEXT FROM c INTO @OBJECT_NAME 
    END 

CLOSE c 

DEALLOCATE c 
+0

while 루프가 발생합니까?) – AlexCuse

0

감사들,

Entaroadun 코드가 난 그냥 내 requierements에 몇 가지 작은 변화를해야했다, 나를 위해 꽤 잘 작동하고, 또한 나는 각 반복에 @colum_list 재설정했다.

... 
    PRINT REPLACE(REPLACE(@template, '{@column_list}', @column_list), 
          '{@OBJECT_NAME}', @OBJECT_NAME) 
    PRINT 'GO' 
    SELECT @column_list = null 
      FETCH NEXT FROM c INTO @OBJECT_NAME 
... 
0

- V 빠르고 빠르다!

- 단일 테이블에서 실행할 코드를 생성하려면이 코드를 텍스트 출력과 함께 실행하십시오.

가 @Table NVARCHAR (100)를 선언

세트 NOCOUNT @Table = 'YourTableHere'

SELECT 'UPDATE'+ @Table + 'SET'SELECT 을 선택 '['+ COLUMN_NAME + ' = '+'LTRIM (RTRIM ([ '+ COLUMN_NAME +'])) 'INFORMATION_SCHEMA.COLUMNS FROM WHERE TABLE_NAME = @Table AND DATA_TYPE LIKE'% 숯불 % '

- 텍스트 출력으로서 실행 (질의/결과 결과 ... 결과 텍스트 - 텍스트 출력 (마지막 쉼표 제외)을 복사하여 새 쿼리 창에 붙여넣고 실행하십시오.

0

OK, 빠르고 빠르지 만 커서가 없어도 작은 'SQL 연결 트릭'을 사용하여 '올바르게'현재 프로젝트에서 충분히 동기 부여를 받았습니다.

--exec spGenerateTrimStatements 'StaticImportMaturities' 
ALTER PROCEDURE  spGenerateTrimStatements 
    (
      @TableName NVARCHAR(100) 
    ) 
AS 
    DECLARE @Cr char(2),  
        @OutputString nvarchar(max) 

    SELECT @Cr = CHAR(13) + CHAR(10) 
    SET  NOCOUNT ON 

    -- Create table to store commands 
    CREATE TABLE #tOutput(OutputText nvarchar(500), RowID int identity(1,1)) 

    -- Build up commands 
    INSERT #tOutput(OutputText) 
    SELECT 'UPDATE ' + @TableName + ' SET ' 

    INSERT #tOutput(OutputText) 
    SELECT '[' + Column_Name + '] = ' + 'LTRIM(RTRIM([' + Column_Name + '])), ' 
    FROM INFORMATION_SCHEMA.Columns 
    WHERE Table_Name = @TableName 
     AND Data_Type LIKE '%CHAR%' 

    --  Trim last comma 
    UPDATE #tOutput 
    SET    OutputText = LEFT(OutputText, LEN(OutputText)-1) 
    WHERE RowID = (SELECT Max(RowID) FROM #tOutput) 

    -- use subselect to concatenate the command string 
    SELECT @OutputString = ISNULL(@OutputString, '') + ISNULL(OutputText, '') 
    FROM (SELECT OutputText 
      FROM #tOutput) TextOutput 

    -- run the command 
    EXEC sp_ExecuteSQL @OutputString 
1

는 데이터베이스의 모든 테이블을 사용하는 단의 답을 업데이트 : 하지만 동적 SQL을 사용한다. 스 니펫을 실행하고 결과를 복사하여 실행하면됩니다.

SELECT 'UPDATE [' + TABLE_SCHEMA + '].[' + TABLE_NAME + '] SET [' + Column_Name + '] = ' + 'LTRIM(RTRIM([' + Column_Name + ']))' 
FROM INFORMATION_SCHEMA.Columns c 
WHERE Data_Type LIKE '%CHAR%' 
관련 문제