En utilisant SQL Server 2008, disons que j'ai une table appelée testing
avec 80 colonnes et que je veux trouver une valeur appelée foo
.
Je peux faire:
SELECT *
FROM testing
WHERE COLNAME = 'foo'
Est-il possible que je puisse interroger les 80 colonnes et retourner tous les résultats où foo
est contenu dans l'une des 80 colonnes?
Merci d'avance.
Première méthode (testée) Commencez par obtenir la liste des colonnes dans une variable de chaîne séparée par des virgules, puis vous pouvez rechercher 'foo' en utilisant cette variable en utilisant IN
Vérifiez la procédure stockée ci-dessous qui obtient d'abord les colonnes, puis recherche la chaîne:
DECLARE @TABLE_NAME VARCHAR(128)
DECLARE @SCHEMA_NAME VARCHAR(128)
-----------------------------------------------------------------------
-- Set up the name of the table here :
SET @TABLE_NAME = 'testing'
-- Set up the name of the schema here, or just leave set to 'dbo' :
SET @SCHEMA_NAME = 'dbo'
-----------------------------------------------------------------------
DECLARE @vvc_ColumnName VARCHAR(128)
DECLARE @vvc_ColumnList VARCHAR(MAX)
IF @SCHEMA_NAME =''
BEGIN
PRINT 'Error : No schema defined!'
RETURN
END
IF NOT EXISTS (SELECT * FROM sys.tables T JOIN sys.schemas S
ON T.schema_id=S.schema_id
WHERE T.Name=@TABLE_NAME AND S.name=@SCHEMA_NAME)
BEGIN
PRINT 'Error : The table '''+@TABLE_NAME+''' in schema '''+
@SCHEMA_NAME+''' does not exist in this database!'
RETURN
END
DECLARE TableCursor CURSOR FAST_FORWARD FOR
SELECT CASE WHEN PATINDEX('% %',C.name) > 0
THEN '['+ C.name +']'
ELSE C.name
END
FROM sys.columns C
JOIN sys.tables T
ON C.object_id = T.object_id
JOIN sys.schemas S
ON S.schema_id = T.schema_id
WHERE T.name = @TABLE_NAME
AND S.name = @SCHEMA_NAME
ORDER BY column_id
SET @vvc_ColumnList=''
OPEN TableCursor
FETCH NEXT FROM TableCursor INTO @vvc_ColumnName
WHILE @@FETCH_STATUS=0
BEGIN
SET @vvc_ColumnList = @vvc_ColumnList + @vvc_ColumnName
-- get the details of the next column
FETCH NEXT FROM TableCursor INTO @vvc_ColumnName
-- add a comma if we are not at the end of the row
IF @@FETCH_STATUS=0
SET @vvc_ColumnList = @vvc_ColumnList + ','
END
CLOSE TableCursor
DEALLOCATE TableCursor
-- Now search for `foo`
SELECT *
FROM testing
WHERE 'foo' in (@vvc_ColumnList );
2ème méthode Dans le serveur SQL, vous pouvez obtenir l'ID d'objet de la table, puis en utilisant cet ID d'objet, vous pouvez récupérer les colonnes. Dans ce cas, ce sera comme ci-dessous:
Étape 1: Obtenez d'abord l'ID d'objet de la table
select * from sys.tables order by name
Étape 2: Maintenant, récupérez les colonnes de votre table et recherchez-y:
select * from testing where 'foo' in (select name from sys.columns where object_id =1977058079)
Remarque: object_id est ce que vous obtenez à la première étape pour votre table pertinente
Vous pouvez utiliser in
:
SELECT *
FROM testing
WHERE 'foo' in (col1, col2, col3, . . . );
Vous pouvez utiliser dans et vous pouvez obtenir les noms de colonne dynamiquement et les passer à la clause IN
en créant une chaîne sql et en l'exécutant à l'aide de execute sp_executesql
.
declare @sql nvarchar(2100)
declare @cols nvarchar(2000)
declare @toSearch nvarchar(200)
declare @tableName nvarchar(200)
set @tableName = 'tbltemp'
set @toSearch = '5'
set @cols =(
SELECT LEFT(column_name, LEN(column_name) - 1)
FROM (
SELECT column_name + ', '
FROM INFORMATION_SCHEMA.COLUMNS where table_name = @tableName
FOR XML PATH ('')
) c (column_name )
)
set @sql = 'select * from tbltemp where '''+ @toSearch + ''' in (' + @cols + ')';
execute sp_executesql @sql
J'ai pris l'idée de la réponse d'Ubaid Ashraf, mais je l'ai fait fonctionner. Modifiez simplement MyTableName ici:
SELECT STUFF((
SELECT ', ' + c.name
FROM sys.columns c
JOIN sys.types AS t ON c.user_type_id=t.user_type_id
WHERE t.name != 'int' AND t.name != 'bit' AND t.name !='date' AND t.name !='datetime'
AND object_id =(SELECT object_id FROM sys.tables WHERE name='MyTableName')
FOR XML PATH('')),1,2,'')
Vous pouvez l'ajuster à vos besoins et ajouter ou supprimer des conditions dans la colonne where (la partie 't.name! =' Int 'AND t.name! =' Bit 'etc.), par ex. ajoutez 't.name! =' uniqueidentifier '' pour éviter d'obtenir Conversion failed when converting the varchar value 'myvalue' to data type int
type d'erreurs ..
Puis copier coller le résultat dans cette requête (sinon cela n'a pas fonctionné):
SELECT * from MyTableName where 'foo' in (COPY PASTE PREVIOUS QUERY RESULT INTO HERE)
Je pense que c'est l'une des meilleures façons de le faire
SELECT * FROM sys.columns a
inner join
(
SELECT object_id
FROM sys.tables
where
type='U'--user table
and name like 'testing'
) b on a.object_id=b.object_id
WHERE a.name like '%foo%'