Oracle 中實現隨機抽取數據

轉載來源:http://www.orafans.org/2006/09/oracle-random-record.htmlhtml

轉載來源:http://kb.cnblogs.com/a/1443619/java

 

1、Oracle取隨機數據
一、Oracle訪問數據的基本方法:
1)、全表掃描(Full table Scan):執行全表掃描,Oracle讀表中的全部記錄,考查每一行是否知足WHERE條件。Oracle順序的讀分配給該表的每個數據塊,且每一個數據塊Oracle只讀一次.這樣全表掃描可以受益於多塊讀.
 
2)、採樣表掃描(sample table scan):掃描返回表中隨機採樣數據,這種訪問方式須要在FROM語句中包含SAMPLE選項或者SAMPLE BLOCK選項. 
 
注:從Oracle8i開始Oracle提供採樣表掃描特性 

 
二、使用sample得到隨機結果集
2.一、語法: SAMPLE [ BLOCK ](sample_percent)[ SEED (seed_value) ] 
SAMPLE選項:表示按行採樣來執行一個全表掃描,Oracle從表中讀取特定百分比的記錄,並判斷是否知足WHERE子句以返回結果。
BLOCK: 表示使用隨機塊例舉而不是隨機行例舉。
sample_percent:是隨機獲取一張表中記錄的百分比。好比值爲10,那就是表中的隨機的百分之10的記錄。
               值必須大於等於.000001,小於100。
SEED:表示從哪條記錄返回,相似於預先設定例舉結果,於是每次返回的結果都是固定的。該值必須介於0和4294967295之間。 
 
2.二、舉例說明
   建立測試臨時表: mysql

Sql代碼
  1. SQL>create table zeeno as select * from dba_objects;      
SQL>create table zeeno as select * from dba_objects;

 
1)、sample(sample_percent): linux

Sql代碼
  1. -- 從表zeeno中「全表掃描」隨機抽取10%的記錄,隨機查詢5條記錄    
  2. SQL>select object_name from zeeno sample(10) where rownum<6;    
  3.   
  4. OBJECT_NAME    
  5. --------------------------------------------------------------------------------    
  6. UET$    
  7. VIEW$    
  8. I_SUPEROBJ2    
  9. TRIGGERCOL$    
  10. I_VIEW1       
  11.                              
  12. SQL&gt; /    
  13.   
  14. OBJECT_NAME    
  15. --------------------------------------------------------------------------------    
  16. I_FILE1    
  17. IND$    
  18. CLU$    
  19. FET$    
  20. I_COBJ#    
  21.     
-- 從表zeeno中「全表掃描」隨機抽取10%的記錄,隨機查詢5條記錄 
SQL>select object_name from zeeno sample(10) where rownum<6; 

OBJECT_NAME 
-------------------------------------------------------------------------------- 
UET$ 
VIEW$ 
I_SUPEROBJ2 
TRIGGERCOL$ 
I_VIEW1    
                          
SQL&gt; / 

OBJECT_NAME 
-------------------------------------------------------------------------------- 
I_FILE1 
IND$ 
CLU$ 
FET$ 
I_COBJ#

 
2)、sample block(sample_percent) sql

Sql代碼
  1. -- 從表zeeno中「採樣表掃描」隨機抽取10%的記錄,隨機查詢5條記錄    
  2. SQL> select object_name from zeeno sample block(10) where rownum<6;    
  3.   
  4. OBJECT_NAME    
  5. --------------------------------------------------------------------------------    
  6. URIFACTORY    
  7. DBMS_XMLGEN    
  8. DBMS_XMLGEN    
  9. DBMS_XMLSTORE    
  10. DBMS_XMLSTORE    
  11.     
-- 從表zeeno中「採樣表掃描」隨機抽取10%的記錄,隨機查詢5條記錄 
SQL> select object_name from zeeno sample block(10) where rownum<6; 

OBJECT_NAME 
-------------------------------------------------------------------------------- 
URIFACTORY 
DBMS_XMLGEN 
DBMS_XMLGEN 
DBMS_XMLSTORE 
DBMS_XMLSTORE

 

 3)、sample block(sample_percent) seed(seed_value) 數據庫

Sql代碼
  1. -- 使用seed,返回固定的結果集。從表zeeno中「採樣表掃描」隨機抽取10%的記錄,隨機查詢5條記錄。    
  2. SQL> select object_name from zeeno sample(10) seed(10) where rownum<6;    
  3.   
  4. OBJECT_NAME    
  5. --------------------------------------------------------------------------------    
  6. UET$    
  7. I_CON1    
  8. I_FILE2    
  9. FET$    
  10. I_COL1    
  11.   
  12. SQL&gt; select object_name from zeeno sample(10) seed(10) where rownum&lt;6;    
  13.   
  14. OBJECT_NAME    
  15. --------------------------------------------------------------------------------    
  16. UET$    
  17. I_CON1    
  18. I_FILE2    
  19. FET$    
  20. I_COL1    
  21.     
-- 使用seed,返回固定的結果集。從表zeeno中「採樣表掃描」隨機抽取10%的記錄,隨機查詢5條記錄。 
SQL> select object_name from zeeno sample(10) seed(10) where rownum<6; 

OBJECT_NAME 
-------------------------------------------------------------------------------- 
UET$ 
I_CON1 
I_FILE2 
FET$ 
I_COL1 

SQL&gt; select object_name from zeeno sample(10) seed(10) where rownum&lt;6; 

OBJECT_NAME 
-------------------------------------------------------------------------------- 
UET$ 
I_CON1 
I_FILE2 
FET$ 
I_COL1

 

注意如下幾點:windows

1.sample只對單表生效,不能用於錶鏈接和遠程表
2.sample會使SQL自動使用CBO
 
oracle

 

 

三、使用DBMS_RANDOM包
  DBMS_RANDOM有兩種主要的使用方法分別是:DBMS_RANDOM.VALUE()和DBMS_RANDOM.RANDOMdom

 

3.一、取隨機數函數

Sql代碼
  1. SQL> select dbms_random.value() from dual;   
  2.     
  3. DBMS_RANDOM.VALUE()   
  4. -------------------   
  5.   0.146123095968043   
  6.     
  7. SQL> select dbms_random.value() from dual;   
  8.     
  9. DBMS_RANDOM.VALUE()   
  10. -------------------   
  11.    0.90175764902345  
SQL> select dbms_random.value() from dual;
 
DBMS_RANDOM.VALUE()
-------------------
  0.146123095968043
 
SQL> select dbms_random.value() from dual;
 
DBMS_RANDOM.VALUE()
-------------------
   0.90175764902345

 

Sql代碼
  1. SQL> select dbms_random.value(1,10) from dual;   
  2.     
  3. DBMS_RANDOM.VALUE(1,10)   
  4. -----------------------   
  5.        9.86601968210438   
  6.     
  7. SQL> select dbms_random.value(1,10) from dual;   
  8.     
  9. DBMS_RANDOM.VALUE(1,10)   
  10. -----------------------   
  11.        3.43475105499398  
SQL> select dbms_random.value(1,10) from dual;
 
DBMS_RANDOM.VALUE(1,10)
-----------------------
       9.86601968210438
 
SQL> select dbms_random.value(1,10) from dual;
 
DBMS_RANDOM.VALUE(1,10)
-----------------------
       3.43475105499398

 

 3.二、舉例說明

  

Sql代碼
  1. SQL> select * from (select object_name from zeeno order by dbms_random.random) where rownum<6;   
  2.     
  3. OBJECT_NAME   
  4. --------------------------------------------------------------------------------   
  5. /6dd0fe0e_CertificateCertifica   
  6. /cf5224d7_SunJSSE_a4   
  7. KU$_PARSED_ITEMS   
  8. javax/swing/text/IconView   
  9. oracle/xml/jdwp/XSLJDWPString   
  10.     
  11. SQL> select * from (select object_name from zeeno order by dbms_random.random) where rownum<6;   
  12.     
  13. OBJECT_NAME   
  14. --------------------------------------------------------------------------------   
  15. java/io/ObjectOutputStream$1   
  16. sun/security/krb5/KrbAsReq   
  17. /2d52a21c_Last   
  18. SYS_YOID0000006594$   
  19. /308fbfa1_BeanContextServices  
SQL> select * from (select object_name from zeeno order by dbms_random.random) where rownum<6;
 
OBJECT_NAME
--------------------------------------------------------------------------------
/6dd0fe0e_CertificateCertifica
/cf5224d7_SunJSSE_a4
KU$_PARSED_ITEMS
javax/swing/text/IconView
oracle/xml/jdwp/XSLJDWPString
 
SQL> select * from (select object_name from zeeno order by dbms_random.random) where rownum<6;
 
OBJECT_NAME
--------------------------------------------------------------------------------
java/io/ObjectOutputStream$1
sun/security/krb5/KrbAsReq
/2d52a21c_Last
SYS_YOID0000006594$
/308fbfa1_BeanContextServices

 

Sql代碼
  1. SQL> select * from (select object_name from zeeno order by trunc(dbms_random.value(1,3))) where rownum<6;   
  2.     
  3. OBJECT_NAME   
  4. --------------------------------------------------------------------------------   
  5. ICOL$   
  6. C_COBJ#   
  7. PROXY_ROLE_DATA$   
  8. I_OBJ#   
  9. UET$   
  10.     
  11. SQL> select * from (select object_name from zeeno order by trunc(dbms_random.value(1,3))) where rownum<6;   
  12.     
  13. OBJECT_NAME   
  14. --------------------------------------------------------------------------------   
  15. ICOL$   
  16. UNDO$   
  17. I_PROXY_ROLE_DATA$_1   
  18. I_CDEF2   
  19. UET$  
SQL> select * from (select object_name from zeeno order by trunc(dbms_random.value(1,3))) where rownum<6;
 
OBJECT_NAME
--------------------------------------------------------------------------------
ICOL$
C_COBJ#
PROXY_ROLE_DATA$
I_OBJ#
UET$
 
SQL> select * from (select object_name from zeeno order by trunc(dbms_random.value(1,3))) where rownum<6;
 
OBJECT_NAME
--------------------------------------------------------------------------------
ICOL$
UNDO$
I_PROXY_ROLE_DATA$_1
I_CDEF2
UET$

 

Sql代碼
  1. SQL> select trunc(dbms_random.value(0, 1000)) randomNum from dual; --(0-1000的整數)   
  2.     
  3.  RANDOMNUM   
  4. ----------   
  5.        790   
  6.     
  7. SQL> select dbms_random.value(0, 1000) randomNum from dual; --(0-1000的浮點數)   
  8.     
  9.  RANDOMNUM   
  10. ----------   
  11. 997.876726  
SQL> select trunc(dbms_random.value(0, 1000)) randomNum from dual; --(0-1000的整數)
 
 RANDOMNUM
----------
       790
 
SQL> select dbms_random.value(0, 1000) randomNum from dual; --(0-1000的浮點數)
 
 RANDOMNUM
----------
997.876726

 

四、使用內部函數sys_guid()  

Sql代碼
  1. SQL>  select * from (select OBJECT_NAME from zeeno order by sys_guid()) where rownum < 6;    
  2.     
  3. OBJECT_NAME   
  4. --------------------------------------------------------------------------------   
  5. /6bedadd5_KeyManagerFactory1   
  6. /ffd795c8_AddCRIF   
  7. TABLE_EXPORT_OBJECTS   
  8. /278cd3a4_CGParselet   
  9. KU$_REFCOL_T   
  10.     
  11. SQL>  select * from (select OBJECT_NAME from zeeno order by sys_guid()) where rownum < 6;   
  12.     
  13. OBJECT_NAME   
  14. --------------------------------------------------------------------------------   
  15. sun/awt/InputMethodSupport   
  16. V_$RESTORE_POINT   
  17. COLORSLIST   
  18. java/util/WeakHashMap$Entry   
  19. DBMSOUTPUT_LINESARRAY  
SQL>  select * from (select OBJECT_NAME from zeeno order by sys_guid()) where rownum < 6; 
 
OBJECT_NAME
--------------------------------------------------------------------------------
/6bedadd5_KeyManagerFactory1
/ffd795c8_AddCRIF
TABLE_EXPORT_OBJECTS
/278cd3a4_CGParselet
KU$_REFCOL_T
 
SQL>  select * from (select OBJECT_NAME from zeeno order by sys_guid()) where rownum < 6;
 
OBJECT_NAME
--------------------------------------------------------------------------------
sun/awt/InputMethodSupport
V_$RESTORE_POINT
COLORSLIST
java/util/WeakHashMap$Entry
DBMSOUTPUT_LINESARRAY

 

注:

       在使用sys_guid() 這種方法時,有時會獲取到相同的記錄,即和前一次查詢的結果集是同樣的,查找相關資料,有些說是和操做系統有關,在windows平臺下正常,獲取到的數據是隨機的,而在linux等平臺下始終是相同不變的數據集,有些說是由於sys_guid()函數自己的問題,即sys_guid()會在查詢上生成一個16字節的全局惟一標識符,這個標識符在絕大部分平臺上由一個宿主標識符和進程或進程的線程標識符組成,這就是說,它極可能是隨機的,可是並不表示必定是百分之百的這樣。
      
       因此,爲確保在不一樣的平臺每次讀取的數據都是隨機的,咱們大多采用使用sample函數或者DBMS_RANDOM包得到隨機結果集,其中使用sample函數更經常使用,由於其查詢時縮小了查詢範圍,在查詢大表,且要提取數據不是很很少的狀況下,會對查詢速度上有明顯的提升。


 

2、其餘數據庫隨機取出n條記錄:

一、SqlServer中隨機提取數據庫記錄

select top n * from 表 order by newid()

--------------------------------------------------------------------------------
select top 10 * from tablename order by NEWID()  
select top 10 * from tablename order by NEWID()

二、mysql中隨機提取數據庫記錄

Select * From 表 order By rand() Limit n

-------------------------------------------------------------------------------
select * from tablename order by rand() limit 10
select * from tablename order by rand() limit 10

三、Access中隨機提取數據庫記錄

Select top n * FROM 表 orDER BY Rnd(id)

-------------------------------------------------------------------------------SELECT top 10 * FROM tablename ORDER BY Rnd(FId)   SELECT top 10 * FROM tablename ORDER BY Rnd(FId)FId:爲你當前表的ID字段名

相關文章
相關標籤/搜索