1. 程式人生 > >資料結構與演算法實驗題 素數區間

資料結構與演算法實驗題 素數區間

★實驗任務
dark di 在做數學題目的時候發現了一個現象,2 個相鄰的素數之間存在一
個區間,他把這個區間稱為非素數區間,那麼 dark di 想知道,給定一個正整數
x,x 所在的非素數區間長度是多少呢?
例如 23 和 29 是 2 個相鄰的素數,他們之間的非素數區間是[24,28],長度
是 5,假設 x=27,那麼 x 所在的非素數區間長度就是 5。如果 x 是一個素數,則
答案是 0。
注意:素數指的是除了 1 和它本身以外不再有其他因數的自然數。

★資料輸入
第一行輸入一個正整數 T,表示接下去有 T 次詢問。
接下去 T 行,每行一個正整數 x。(x<=100000)。
對於 30%的資料,T<=5,x<=100
對於 80%的資料,T<=10,x<=5000
對於 100%的資料,T<=100000,x<=100000

★資料輸出
輸入 T 行,每行一個整數表示非素數區間的長度。
輸入示例
2
27
1
輸出例項
5
0

分析:
這題的重點有兩個:如何判斷一個數是不是素數;以及通過什麼方法獲得區間長度。
1、關於判斷素數的函式,最普通的就是這種寫法:

bool is_prime(int number) {
	if (number <= 1) {
		return false;
	}
	for (int i = 2; i <= sqrt(number); i++) {
		if (number%i == 0) {
			return false;
		}
	}
	return true;
}

      然而就是這種寫法也有可以改進的地方:sqrt(number)是一個固定值,沒必要每次迴圈完都要重新計算一次。所以,應該事先用一個變數sqr把sqrt(number)的值存起來,迴圈時這個sqr來判斷。
用這個方法在n比較小的時候,可以在給定的端點前後不斷執行is_prime函式,可在這題中10^5的情況下時間有可能不夠。所以另外想辦法,參考同學的優秀作業,可以使用“素數篩

”的方法,具體如下(以下摘抄於這位同學的講解PPT):

可以提前用所謂的“素數篩”的方法,對範圍內的所有數的是素數與否進行標記。具體操作過程如下:

顧名思義,就是要在給定範圍的數內,篩出所有素數
從小到大列舉所有數,對每一個素數,篩去它的所有倍數,剩下的就是素數了。可是一開始並不知道那些數是素數。
沒有關係,僅僅需要知道2是素數就足夠了,

例如:
求1—15中所有素數
篩去2的倍數
2、3、4、5、6、7、8、9、10、11、12、13、14、15
3之前沒有被篩掉,所以3是素數,篩除3的倍數
2、3、4、5、6、7、8、9、10、11、12、13、14、15
4被篩去,則4不是素數,看5,5之前沒被篩,則篩去5的倍數
2、3、4、5、6、7、8、9、10、11、12、13、14、15
6被篩去,看7。。。。。。
直到遍歷完15後,便得到了1–15的素數表

我們可以申請一個長度為MAX的bool陣列,false表示是未被篩除,true表示已被篩除。
程式碼如下:

const int MAX=100010;
bool PrimeNum[MAX]={false};//將陣列元素全初始化為false
for (int i = 2; i < MAX; ++i) {
	if (PrimeNum[i] == false)//如果i是素數
		for (int j = i + i; j < MAX; j += i)
			PrimeNum[j] = true;//篩去i的倍數
}

這樣就得到了1~MAX-1之間的素數表,有了表以後,對於每次查詢,只需查表即可,無需再執行isPrime函式,可以節省大量的時間。
此法是典型的空間換時間的策略,消耗空間儲存好素數結果後,便可處理查詢次數T接近10^5的情況。

相關推薦

資料結構演算法實驗 素數區間

★實驗任務 dark di 在做數學題目的時候發現了一個現象,2 個相鄰的素數之間存在一 個區間,他把這個區間稱為非素數區間,那麼 dark di 想知道,給定一個正整數 x,x 所在的非素數區間長度是多少呢? 例如 23 和 29 是 2 個相鄰的素數,他們之

資料結構演算法-->互為素數

package com.xiaojihua.datastructure; public class Zhishu { public static void main(String[] args) { // TODO Auto-generated method stub Sy

資料結構演算法·實驗

1、利用順序棧將一個非負的十進位制整數N轉換為對應的B進位制數。    要求:非負的十進位制整數N和B都從鍵盤輸入;轉換結果從螢幕輸出。 2、括號匹配問題,編寫一個判別表示式中括號是否正確配對的函式,並設計一個測試主函式。 #include<stdio.h>

資料結構演算法·實驗

1.構造一棵二叉樹,樹的形態如下圖所示,打印出前序遍歷、中序遍歷、後序遍歷的遍歷序列。 2.選擇一種遍歷方式計算該樹中葉子結點的個數,並打印出葉子結點。 3.編寫一個查詢演算法,查詢資料“E”是否存在。 #include"stdlib.h" #include"stdio

資料結構演算法·實驗

求二叉樹的層序遍歷問題 要求:(1)編寫一個建立二叉樹的函式。 (2)編寫按層次(同一層自左至右)輸出二叉樹中所有的結點的函式。            (3)編寫一個測試主函式。 #include<stdlib.h> #include<stdio.h&

哈工大資料結構演算法實驗4

實驗要求 寫一個快速排序演算法,實現資料的快速排序 思路 隨便網上都能找到快排演算法,然後照抄就ok。。。當然理解快排是必要的,只是快排不是很好理解,詳情請百度 #include <i

資料結構演算法-------斐波那契數列、位運算、素數、最大公約數、最小公倍數

1、斐波那契數列 function fabeliq(n){ var arr=[]; if(n==1){ return arr=[0]; } if(n==2){ return arr=[0,1];

資料結構演算法A》實驗1:按資料元素升序建立單鏈表

** 實驗題目 ** 對輸入的正整數序列建立有序單鏈表。在建立單鏈表的過程中,連結串列中的資料元素按升序排列。當輸入的資料元素在單鏈表中已經存在時,不進行插入操作。 請使用面向物件形式定義結點類和連結串列類,參考程式碼如下。 class Node { int

資料結構演算法A》實驗2:棧的應用

題目: Description 根據棧的特點,實現十進位制到其他進位制之間的轉換,具體要求如下: (1)利用棧進行十進位制數與N進位制(如二進位制、八進位制、十六進位制)資料之間的轉換; (2)通過順序棧記錄進位制轉換的中間結果,該順序棧有一個指示棧頂的變數top,

2017級軟體工程專業《資料結構演算法A》實驗2:棧的應用

題目: Description 根據棧的特點,實現十進位制到其他進位制之間的轉換,具體要求如下: (1)利用棧進行十進位制數與N進位制(如二進位制、八進位制、十六進位制)資料之間的轉換; (2)通過順序棧記錄進位制轉換的中間結果,該順序棧有一個指示棧頂的變數top,

資料結構演算法設計》實驗報告書之二叉樹的基本操作實現及其應用

《資料結構與演算法設計》實驗報告書之二叉樹的基本操作實現及其應用 實驗專案 二叉樹的基本操作實現及其應用 實驗目的 1.熟悉二叉樹結點的結構和對二叉樹的基本操作。 2.掌握對二叉樹每一種操作的具體實現。 3.學會利用遞迴方法編寫對二叉樹這種遞迴資料結構進行處理的演算法。 4.會用二叉

資料結構演算法設計》實驗報告書之字串和陣列的基本操作

《資料結構與演算法設計》實驗報告書之字串和陣列的基本操作 實驗專案        字串和陣列的基本操作 實驗目的        1.掌握陣列的定

資料結構演算法設計》實驗報告書之圖的遍歷操作

《資料結構與演算法設計》實驗報告書之圖的遍歷操作 實驗專案 圖的遍歷操作 實驗目的 掌握有向圖和無向圖的概念;掌握鄰接矩陣和鄰接連結串列建立圖的儲存結構;掌握DFS及BFS對圖的遍歷操作;瞭解圖結構在人工智慧、工程等領域的廣泛應用。 實驗內容 採用鄰接矩陣和鄰接連結串列其中一種作

資料結構演算法A》實驗3:字串的簡單加密

題目: Description 假設字串中只可能包含“大小寫英文字母”、“阿拉伯數字”和10種其他符號(包括:'!'、'#'、'@'、'+','-','*','?','$',':',';')。請編寫程式碼,當讀入一個字串(長度不超過50個字元)之後,使用順序表儲存字串,

PTA資料結構演算法題目集(中文) 函式 (1)

4-1 單鏈表逆轉 code: List Reverse(List head) { if(NULL==head|| NULL==head->Next) return head; List p; List

PTA資料結構演算法題目集(中文) 函式(2)

4-6 帶頭結點的鏈式表操作集 code: List MakeEmpty() { List L; L = (List)malloc(sizeof(struct LNode)); L->Data = NULL; L->

挑戰資料結構演算法面試題——80全解析(三)

題目來源“資料結構與演算法面試題80道”。這是第三部分,包含其中的第11題到第15題。 在此給出我的解法,如你有更好的解法,歡迎留言。 問題分析:涉及的知識點是二叉樹的遍歷,遍歷的方法主要有: 先序遍歷 中序遍歷 後序遍歷 層次遍歷 在本題中,使用先序遍歷的方法。 方法:

資料結構演算法》第一次實驗內容•線性表的建立、銷燬、插入、刪除、遍歷等操作的實現

《資料結構與演算法》第一次課內容安排 線性表的建立、銷燬、插入、刪除、遍歷等操作的實現 實驗目的: 1、通過實驗掌握、複習C++有關基本知識; 2、通過實驗熟練掌握在連結串列結構中實現線性表操作的方法,並實現基本操作:查詢、插入和刪除等演算法。 實驗內容: 一、連

資料結構演算法】刷彙總 Python 版

我的BLOG裡寫了一部分演算法和資料結構,題目都是從網上和書上找的。當然一下這些並不全面,我打算利用今後的時間把各類的演算法題都用Python寫一遍(因為我主要是用Python),儘可能囊括所有的演算法題。寫這些題並不是目的,主要還是為了能夠提升自己的資料結構和

演算法資料結構演算法基礎總覽(中)——刷Leetcode等演算法時一些很實用的jdk輔助方法錦集

        最近重新學習資料結構與演算法以及刷leetcode演算法題時,發現不少jdk自帶的方法可以提升刷題的效率。這些小技巧不僅僅對刷演算法題帶來便利,對我們平時開發也是很有幫助的。本文以java語言為基礎,記錄了目前已經使用或看到過的一些小技巧,後續在刷題過程