日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

oracle质数怎么算,借花献佛之使用Oracle sql求质数(笔记)

發布時間:2025/4/16 编程问答 37 豆豆
生活随笔 收集整理的這篇文章主要介紹了 oracle质数怎么算,借花献佛之使用Oracle sql求质数(笔记) 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

首先聲明一點,文章內容從itpub論壇上看到的,原文鏈接外鏈網址已屏蔽,本文主要是記錄下筆記,原文中有更詳細的分析。使用sql求質素沒什么實用價值,重要的是思路。

(一)最簡單的方法

思路:將2和所有大于等于3小于XX的奇數取出來,做一中間結果集t。然后逐一校驗t中的每個N是否是質數。如果發現一個數字N不能被其他所有數字整除——當然,這些數字要小于等于SQRT(N),那么N就是質數

with t as(select 2 n from dual union select rownum*2+1 from dual connect by rownum<=(10000-2)/2)

select count(*) from t a where not exists (select null from t b where b.n<=sqrt(a.n) and mod(a.n, b.n)=0)

最直接的方法,可惜速度最慢。

(二)篩選法

思路:將從2到XX的數都列出來,作為一個全集,然后減去所有的合數,即可得到素數集合

WITH t AS (

SELECT ROWNUM+1 rn FROM DUAL CONNECT BY ROWNUM <= 10000-1)

SELECT COUNT(*)

FROM (SELECT rn

from t

MINUS

SELECT t1.rn * t2.rn--4=2*2 2*3 9=3*3 3*4 16=4*4 4*5

FROM t t1, t t2

WHERE t1.rn <= t2.rn

AND t1.rn <= (SELECT SQRT(10000) FROM DUAL))

(三)改進的篩選法

思路:除了2之外的偶數,可以從全集和合數集中排除

WITH t AS (

--2-10000/2

SELECT ROWNUM+1 rn FROM DUAL CONNECT BY ROWNUM <= 10000/2-1

)

,t_odd AS (

--奇數

SELECT 2*ROWNUM+1 rn FROM DUAL CONNECT BY ROWNUM <= 10000/2-1

)

SELECT COUNT(*) + 1--+2

FROM (SELECT rn

from t_odd

MINUS

SELECT t1.rn * t2.rn

FROM t t1, t t2

WHERE t1.rn <= t2.rn

AND t1.rn <= (SELECT SQRT(10000) FROM DUAL)

AND t1.rn * t2.rn < 10000)

另一種寫法:排除偶數

WITH t_odd AS (

SELECT 2*ROWNUM+1 rn FROM DUAL CONNECT BY ROWNUM <= 10000/2-1

)

SELECT COUNT(*) + 1

FROM (SELECT rn

from t_odd

MINUS

SELECT t1.rn * t2.rn --9=3*3 3*5 25=5*5 5*7 49=7*7

FROM t_odd t1, t_odd t2

WHERE t1.rn <= t2.rn

AND t1.rn <= (SELECT SQRT(10000) FROM DUAL)

AND t1.rn * t2.rn < 10000)

(四)逆向exists

with t as(select 2 n from dual union select rownum*2+1 from dual connect by rownum<=(10000-2)/2)

, z as (select * from t minus

select * from t a where exists (select null from t b where b.n<=sqrt(a.n) and mod(a.n, b.n)=0))

select count(*) from z

或者:

with t as(select rownum*2+1 n from dual connect by rownum<=(10000-2)/2

union select 3 from dual --F5執行計劃 走MERGE JOIN

),z as (select * from t minus

select * from t a where exists (select null from t b where b.n<=sqrt(a.n) and mod(a.n, b.n)=0))

select count(*)+1 from z

加了union select 3 from dual 之后,執行計劃走MERGE JOIN,這一點還沒想明白,歡迎指教。

(五)提前剔除奇數

WITH t0 AS (

SELECT 2*ROWNUM+1 rn FROM DUAL CONNECT BY ROWNUM <= (10000)/2-1

),

t as(SELECT rn from t0 where mod(rn,3)<>0 and mod(rn,5)<>0 and mod(rn,7)<>0 and mod(rn,11)<>0 and mod(rn,13)<>0 and mod(rn,17)<>0 and mod(rn,19)<>0)

SELECT COUNT(*) + 1 + 7 --2,3,5,7,11,13,17,19

FROM (SELECT rn

from t

MINUS

SELECT t1.rn * t2.rn

FROM t t1, t t2

WHERE t1.rn <= t2.rn

AND t1.rn BETWEEN 9 AND (SELECT SQRT(10000) FROM DUAL)

AND t1.rn * t2.rn < 10000)

其實后面的大部分寫法都是采用提前篩選掉不合格的數字來減少源數據大小達到加快查詢速度。

全文完。

總結

以上是生活随笔為你收集整理的oracle质数怎么算,借花献佛之使用Oracle sql求质数(笔记)的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。