演算法四:數字盒子

問題描述

你有一個盒子,你可以往裡面放數,也可以從裡面取出數。

初始時,盒子是空的,你會依次做 Q 個操作,操作分為兩類:

插入操作:詢問盒子中是否存在數 x,如果

不存在

則把數 x 丟到盒子裡。

刪除操作:詢問盒子中是否存在數 x,如果

存在

則取出 x。

對於每個操作,你需要輸出是否成功插入或刪除。

輸入

第一行一個正整數 Q,表示操作個數。

接下來 Q 行依次描述每個操作。每行 2 個用空格隔開的非負整數 op,x 描述一個操作:op 表示操作型別,op=1 則表示這是一個插入操作,op=2 則表示這是一個刪除操作;x 的意義與操作型別有關,具體見題目描述。

輸出

按順序對所有操作輸出,對於每個操作輸出一行,如果成功則輸出“Succeeded”(不含引號),如果失敗則輸出“Failed”(不含引號)。

樣例輸入

61 100 插入1 100 插入2 100 刪除1 200 插入2 100 刪除2 200 刪除

樣例輸出

SucceededFailedSucceededSucceededFailedSucceeded

提示

[對於 x 較小的情況,我們只需要用陣列記錄每個數是否在盒子裡即可。]

[對於 x 較大的情況,我們可不可以用什麼方法把它們“變小”呢?可以想想雜湊表哦!]

一。 圖解

演算法四:數字盒子

二。 具體實現(C++版)

typedef long long ll;const int Mod = 1000003;vector table[Mod];//雜湊函式int Hash(ll x){ return x%Mod;}// 執行操作時會呼叫這個函式// op:對應該次操作的 op(具體請見題目描述)// x:對應該次操作的 x(具體請見題目描述)// 返回值:如果輸出為“Succeeded”,則這個函式返回 1,否則返回 0bool check(int op, ll x) { int h = Hash(x);//求出x的雜湊值 //在連結串列中找到x(採用C++中的vector或者Java中的List去實現連結串列的功能) vector::iterator ptr = table[h]。end();//返回向量尾指標 for(vector::iterator it = table[h]。begin();it!=table[h]。end();++it) //如果x存在 if((*it)==x){ptr = it;break;} if(op==1){//x不存在則插入 if(ptr == table[h]。end()){ table[h]。push_back(x);//向量尾部增加一個元素X return 1; } return 0; }else{//op為2,則執行刪除操作 if(ptr != table[h]。end()){//用最後一個元素去填補要刪除的元素 *ptr = table[h]。back();//back()得到陣列的最後一個單元的引用,即最後一個單元元素的數值 table[h]。pop_back();//去掉陣列的最後一個元素 return 1; } return 0; }}

補充C++的vector知識

int main(){ vector a; for(int i=0;i<10;i++) { a。push_back(i);//向尾部增加元素 } printf(“%d”,a。at(3));//返回位置1元素的引用,輸出3 printf(“%d”,a。begin());//返回向量頭指標,指向第一個元素 printf(“%d”,a。end());//返回向量尾指標,指向向量最後一個元素的下一個位置 printf(“%d”,a。back());//返回尾元素的引用,輸出9 a。pop_back();//去掉陣列的最後一個元素 return 0;}