2012-06-17 62 views
0

我想擦除deque的元素。當你有一個包含結構的雙端隊列並且你想從後到前打印這些元素,但是你不想打印具有相同結構元素的元素時,你如何做呢?擦除Deque容器的元素

我有這樣的結構:

struct New_Array {      
    array<array<int,4>,4> mytable;  
    int h; 
}; 

雙端隊列充滿了從前面的過程元素。 您想要打印所有位於雙側的元素,但您打印的每個表格必須具有唯一的「h」。只有您找到的具有特定「h」的第一張表必須打印,其他具有相同「h」的表不應打印。我認爲這也可以用「查找」功能來實現。

我們將從deque後面開始找到的「h」值將爲0,並且它將增加其對deque前面的值。

我已經試過這樣:

void Find_Solution_Path(deque<New_Array> Mydeque) 
{ 
    while(Mydeque.size()>0) 
    { 
     New_Array y=Mydeque.back(); 
     PrintBoard(y);   //this is a function that prints the 4x4 array. 
     Mydeque.pop_back(); 
     for(unsigned int i=0; i<Mydeque.size(); i++) 
     { 
      New_Array xxx=Mydeque[i]; 
      if(xxx.h==y.h) 
      { 
       Mydeque.erase(Mydeque[i]); 
      } 
     } 
    } 
} 
+0

我認爲你在for循環中有一個索引問題:當你刪除第i個元素時,你增加了i,但是所有下列元素的索引已經移動了1. –

+0

@EitanT The deque不是從0開始的?它從1開始? –

+0

不,我的意思是以下內容:假設你有一個元素隊列{10,20,30,40},並且你在'i = 1'(第二個元素)擦除元素。你的隊列現在是{10,30,40}。在'i ++'之後,你得到'i = 2',這意味着要評估的下一個元素是40元素30被跳過。 –

回答

2

我不會用一個雙端隊列,而是一組。如果你絕對需要這個deque,那麼創建一個集合。用適當的標準<來定義一個<運算符,以反映唯一性。您將每個打印的元素插入到集合中。在打印之前,檢查元素是否已經存在於集合(查找)中。

HTH,馬丁

1

的一種方法是使用std::unique_copy

#include <iostream> 
#include <algorithm> 
#include <iterator> 
#include <deque> 

struct New_Array { 
    array<array<int,4>,4> mytable; 
    int h; 
    // unique_copy needs this: 
    bool operator==(const New_Array& other) { return h == other.h; } 
}; 

ostream& operator<<(ostream& out, const New_Array& v) 
{ 
    return out << v.h; 
} 

int main() 
{ 
    std::deque<New_Array> q; 
    New_Array temp; 

    // {1, 1, 2, 2, 3, 3} 
    temp.h = 1; 
    q.push_back(temp); 
    q.push_back(temp); 
    temp.h = 2; 
    q.push_back(temp); 
    q.push_back(temp); 
    temp.h = 3; 
    q.push_back(temp); 
    q.push_back(temp); 

    unique_copy(q.begin(), q.end(), ostream_iterator<New_Array>(cout, "\n")); 
} 

範圍必須分類unique_copy正常工作。由於我們按順序插入了元素,所以在上面的例子中不需要排序。

+0

您需要先排序隊列,因爲'unique_copy'只處理連續的相等元素。 – betabandido

+0

@betabandido好點,我會更新。 – jrok

+0

@jrok:如果你需要排序和刪除(如上所述),你可以立即使用一個集合。它具有相同的複雜性。 – Martin

0

我相信@Martin的答案可能是最好的解決方案。如果你不能爲函數返回一個deque更改簽名,你可以從它構建一個set,所有的副本會自動消失:

// First you need to declare a compare function for NewArray objects 
struct NewArrayComp { 
    bool operator()(const NewArray& a1, const NewArray& a2) const { 
     return a1.h < a2.h; 
    } 
}; 

// Then you can construct a set from the deque 
deque<NewArray> dq; 
// ... 
std::set<NewArray, NewArrayComp> s(dq.begin(), dq.end()); 

// Finally you can just print the arrays (without duplicates) 
for (const auto& a : s) 
    PrintBoard(a); 

這個方案有一個爲O(n log n)的複雜性,同時你的代碼是O(n^2)。

此外,如果你不想重複支付從deque要素成本進入set您可以在C++ 11使用移動語義:

std::set<NewArray, NewArrayComp> s; 
std::move(dq.begin(), dq.end(), std::inserter(s, s.begin())); 

這將只是移動的所有元素沒有製作它們的副本。

+0

我不想打印deque的所有值。我只想打印出第一個h值等於1,2,3,4,5等的字符... ect –

+0

@georgemano我的解決方案中的代碼將完成這個工作。通過將deque轉換爲一個集合,您可以擺脫重複數組(具有相同「h」值的數組)。 – betabandido

+0

你能告訴我比較函數做什麼以及爲什麼你這樣實現它?我不太在乎擦除元素。我很關心打印它們。 –