2010-07-20 99 views
2

如何選擇所有記錄的所有記錄,可能含有被稱爲特定值,沒有SQL表達式指特定列SQL選擇可能擁有特定值

舉例來說,我知道,有些未知列包含值「XXX」,並有表中的列和記錄。

謝謝。

+2

只是一個評論(您可能剛纔聽到的是科德在他的墳墓紡那聲音):儘量避免這種情況。 SQL不允許直接使用它(沒有特定的語法),即使有動態SQL的解決方法,健壯的數據庫應用程序應該保持簡單和愚蠢,而動態SQL隱藏了複雜性,這通常意味着遲早會出現問題(在意外功能條款,性能問題和/或安全問題)。 – Unreason 2010-07-20 09:19:07

+2

您想要在數據庫管理系統中執行最基本的任務之一(即應用搜索條件返回結果集),但是您的模式阻止您這樣做。我會斷定你已經誤解了架構或架構是致命的缺陷。 – onedaywhen 2010-07-20 10:21:58

+0

謝謝你的答案,我只是想補充說,這樣的選擇表達式我不會在應用程序中使用,它需要我定義以下映射:記錄從文件(輸入ASCII) - >從現有DB – sergionni 2010-07-20 12:50:14

回答

9

因此,您希望對您的數據庫執行類似谷歌的免費文本搜索。這可以做,但表現將是Teh Suck! Google的速度很快,因爲它的索引有索引,重複數據存儲,並且通常會針對這種搜索進行優化。

無論如何,這裏是使用動態SQL和Oracle數據字典的概念證明。請注意,我將列限制爲要搜索的數據類型,即字符串。

SQL> set serveroutput on size unlimited 
SQL> declare 
    2  dummy varchar2(1); 
    3 begin 
    4  for r in (select table_name, column_name from user_tab_cols 
    5     where data_type in ('VARCHAR2', 'CHAR', 'CLOB')) 
    6  loop 
    7   begin 
    8    execute immediate 'select null from '||r.table_name 
    9      ||' where '||r.column_name||' like ''%&search_value%'' ' 
10      ||' and rownum = 1' 
11     into dummy; 
12    dbms_output.put_line('Found it in >>>' 
13      ||r.table_name||'.'||r.column_name); 
14   exception 
15    when others then 
16     -- bad practice ahoy! 
17     null; 
18   end; 
19  end loop; 
20 end; 
21/
Enter value for search_value: MAISIE 
old 9:    ||' where '||r.column_name||' like ''%&search_value%'' ' 
new 9:    ||' where '||r.column_name||' like ''%MAISIE%'' ' 
Found it in >>>T23.NAME 

PL/SQL procedure successfully completed. 

SQL> 

更健壯的實現可能需要處理的情況下,整個單詞等,如果你在10g或更高版本,然後正則表達式可能是有用的,但正則表達式相結合,動態SQL是一個,呃,有趣前景。

我再說一次,表現會是Teh Suck!在一個大型數據集上。調整幾乎是不可能的,因爲我們無法對每一列進行索引,當然也不支持LIKE或類似的模糊匹配。另一種方法是使用XQuery生成數據的XML表示,然後使用文本對其進行索引。維護這樣一個存儲庫將會是開銷,但是如果您需要定期使用這種功能,那麼這種努力將是一個合理的投資,尤其是在生產環境中。

2
SELECT * FROM table WHERE column='xxx'; 

但如果你有其中可以包含該值多少列,您需要使用OR:

SELECT * FROM table WHERE column1='xxx' or column2='xxx' or column3='xxx'; 
+0

列嘗試,得到: ORA-00936:缺少表達式 00936. 00000 - 「缺少表達式」 – sergionni 2010-07-20 08:33:28

+0

我提到了選擇查詢而沒有提及特定列,是否可以在SQL中使用。也許存在一些特定的關鍵字。 – sergionni 2010-07-20 08:35:45

+2

問題不在於指定列號 – 2010-07-20 08:51:32

0

select * from table_name where(Table_Attribute ='XXX');

這會告訴你這得到期望的結果與屬性XXX

+0

sagar,你是什麼意思作爲TABLE_ATTRIBUTE? – sergionni 2010-07-20 08:43:18

+0

那你列的像 student_id數據 – 2010-07-20 08:45:57

+0

或類似Student_Name =「XXX」 – 2010-07-20 08:46:33

-1

運行的所有記錄,使用SRY壞命名。

declare @_var nvarchar(1000) 
declare @var1 nvarchar(1000) 
declare @var2 nvarchar(1000) 
declare _cur cursor 
for select 

case Column_name 
      when '' then '' 
      else Column_name+'=''asd'' OR ' 
     end 
from information_schema.columns 
    where table_name='M_Patient' 
      and 
      data_type ='nvarchar' 

open _cur 
fetch _cur into @_var 
while(@@fetch_status=0) 
begin 
set @var2=isnull(@var2,'')[email protected]_var 
fetch _cur into @_var 

end 
close _cur 
deallocate _cur 

set @var1='select * from M_Patient where '+ substring(@var2, 0,len(@var2)-2) 

execute (@var1) 
+0

什麼是Column_name? – sergionni 2010-07-20 08:50:31

+0

@sergionni:它是存儲在sql server中的元數據。在sql server查詢分析器中寫入一個查詢,如下所示:** select * from information_schema.columns **,您將開始得到你需要做什麼來查詢結果 – 2010-07-20 08:53:53

+0

有錯誤: ORA-00942:表或視圖不存在 – sergionni 2010-07-20 09:00:22

-1

我通常使用這個腳本,如果我需要在數據庫中搜索一個值並且我不知道表和/或列。只需設置@SearcStr參數並按下播放即可。也許它可以幫助你。

DROP TABLE #Results 

DECLARE @SearchStr nvarchar(100) 
SET  @SearchStr = '' 

CREATE TABLE 
    #Results(ColumnName nvarchar(370), ColumnValue nvarchar(3630)) 

SET NOCOUNT ON 
DECLARE @TableName nvarchar(256) 
DECLARE @ColumnName nvarchar(128) 
DECLARE @SearchStr2 nvarchar(110) 

SET @TableName = '' 
SET @SearchStr2 = QUOTENAME('%' + @SearchStr + '%','''') 

WHILE @TableName IS NOT NULL 
BEGIN 
    SET @ColumnName = '' 
    SET @TableName = 
    (
     SELECT 
      MIN(QUOTENAME(TABLE_SCHEMA) + '.' + QUOTENAME(TABLE_NAME)) 
     FROM  
      INFORMATION_SCHEMA.TABLES 
     WHERE 
       TABLE_TYPE = 'BASE TABLE' 
      AND QUOTENAME(TABLE_SCHEMA) + '.' + QUOTENAME(TABLE_NAME) > @TableName 
      AND OBJECTPROPERTY(OBJECT_ID(QUOTENAME(TABLE_SCHEMA) + '.' + QUOTENAME(TABLE_NAME)), 'IsMSShipped') = 0) 

    WHILE (@TableName IS NOT NULL) AND (@ColumnName IS NOT NULL) 
    BEGIN 
     SET @ColumnName = 
     (
      SELECT 
       MIN(QUOTENAME(COLUMN_NAME)) 
      FROM  
       INFORMATION_SCHEMA.COLUMNS 
      WHERE   
        TABLE_SCHEMA = PARSENAME(@TableName, 2) 
       AND TABLE_NAME = PARSENAME(@TableName, 1) 
       AND DATA_TYPE IN ('char', 'varchar', 'nchar', 'nvarchar') 
       AND QUOTENAME(COLUMN_NAME) > @ColumnName 
     ) 

     IF @ColumnName IS NOT NULL 
     BEGIN 
      INSERT INTO #Results 
      EXEC 
      (
       'SELECT ''' + @TableName + '.' + @ColumnName + ''', LEFT(' + @ColumnName + ', 3630) 
       FROM ' + @TableName + ' (NOLOCK) ' + 
       ' WHERE ' + @ColumnName + ' LIKE ' + @SearchStr2 
      ) 
     END 
    END 
END 

SELECT 
    ColumnName 
    ,ColumnValue 
FROM 
    #Results 
+0

問題標記爲[Oracle],不幸的是您的查詢不使用Oracle數據字典或Oracle語法。 – APC 2010-07-20 12:11:12

+0

我似乎已經失去了我的眼睛 - 謝謝:) – ramad 2010-07-20 12:20:36

1

如果您需要這樣做一次或兩次,那麼APC的答案是好的。如果這在某種程度上(不寒而慄)是持續需求的一部分,那麼我認爲您可以做的最好的事情是在感興趣的表或表上創建一個Oracle計算字段並在其上進行搜索。使用您確定不會顯示在實際文本值中的分隔符,例如:

alter table mytable add search_column 
as (mycolumn1||'^'||mycolumn2||'^'||mycolumn3); 

現在您的查詢就會變成這樣的:

select <whatever transformation you want to see here> 
from mytable where search_column like '%^xxx^%' 

+0

這是一個聰明的解決方案;我希望我能想到它。 (你會的,奧斯卡,你會的)。有幾個問題。首先,虛擬列是在11g中引入的,所以它不適用於任何早期數據庫的人。更嚴重的問題是虛擬列受限於VARCHAR2列的4000個字符限制。再一次,它拋出了'ORA-54004'(誰知道OERR數字變得那麼高?)。目前虛擬列不能是clobs。 – APC 2010-07-20 13:40:40

+0

@APC - 你是對的 - 我完全忽略了varchar2的限制,它減少了寬表的用處。感謝指向54004的指標 - 很高興知道。 – dpbradley 2010-07-20 14:37:54