2016-07-23 9 views
0

Word.std :: set. 사용자 지정 집합 집합

은 내가 비교 동등성을 위해 사용하도록 설정 하시겠습니까 하나의 필드를 포함하는 구조체를 가지고 있고, 메타 데이터 등 기타 분야 :

:

struct read_tag{ 
    unsigned int read_id; // want std::set to use this 
    int offset;   // metadata 
    bool orientation;  // metadata 
}; 

내가 일을 할 수있는 펑이

struct read_tag_compare { 
    bool operator() (const read_tag &a, const read_tag &b) const { 
     return a.read_id > b.read_id 
    } 
}; 

및 decl. 필요한 설정은

std::set<read_tag, read_tag_compare> block; 

으로 설정되었습니다. 문제는 다음과 같습니다.

std::set<read_tag, read_tag_compare>을 포함하는 세트를 만드는 방법은 무엇입니까? 나는 이런 식으로 뭔가 싶어 :

std::set< std::set<read_tag, read_tag_compare> > blocks; 
blocks.insert(a_block); // comp error 

을하지만 이것은 나에게 매우 큰, 그리고 해독하기 어려운 오류가 있습니다.

내부 집합이 어떻게 비교되는지를 반복적으로 확인하고 이것을 외부 집합으로 확장한다고 생각했습니다. 모든 일은 가장 안쪽 집합에 대한 비교기를 정의하는 것입니다. - 5.3 그것은 ++ 내 g와 오류없이 컴파일 D

+0

아니야, 동등성에 의해 정의 된'blocks'에서 하나의'std :: set '만 원하기 때문에. –

+0

두 세트의 메타 데이터가 동일하지 않은 경우에는주의하지 않습니다. 두 세트가'read_tag ​​'에 관해서 모두 같은'read_tag'을 포함한다면 말입니다.read_id' 메타 데이터는 수치 적 의미로는 동일하지 않지만 나중에 동일한 정보를 유도 할 수 있습니다. 그래서 두 세트 중 하나를 가져갈 수는 있지만 두 가지를 원하지 않습니다 –

답변

3

< -comparison on std::set은 비교기가없는 std::lexicographical_compare을 사용합니다. 즉, 요소 ​​유형의 <으로 전달됩니다. (표준 라이브러리의 제한 사항입니다. 순서가 설정된 컨테이너가 아닌 모든 컨테이너에 대해 정의 되었기 때문입니다.) 따라서 사전 식 비교의 올바른 오버로드를 사용하는 세트 세트에 대한 사용자 정의 비교기가 필요합니다.

using read_tag_set = std::set<read_tag, read_tag_compare>; 

struct read_tag_set_compare { 
    bool operator()(const read_tag_set &a, const read_tag_set &b) const noexcept { 
     return std::lexicographical_compare(a.begin(), a.end(), 
              b.begin(), b.end(), a.key_comp()); 
     //              ^^^^^^^^^^^^ 
    } 
}; 

지금 사용 std::set<read_tag_set, read_tag_set_compare>


이 "그냥 작동"할 것이라고 주문 연관 컨테이너 명백한 "수정"이 아닌 이유 코드는 보여줍니다 컨테이너 사용자 정의를 사용하는 경우, 상태를 술어를 사용하면 일반적으로 두 개의 별개 컨테이너의 구성원을 실제로 하나의 ano와 비교할 수 없다는 보장이 없습니다. ther 전혀. 아시다시피, 내의 한 컨테이너는 해당 컨테이너의 비교기와 비교됩니다. 따라서 사용자 지정 비교기를 사용하는 경우 명시 적으로 두 개의 별개 컨테이너가 어떻게 관련되는지 명시해야하며 두 컨테이너를 비교하는 것이 타당하다는 것을 명시해야합니다.

+0

[데모] (http://melpon.org/wandbox/permlink/52qhsJZVO8FhIQXL) –

+0

선생님, 당신은 참으로 사람들 사이의 신입니다. 정말 고마워! 그래서'a.key_comp()'는 두 개의'std :: set '사이의 비교를 수행하기 위해'read_tag_compare' 펑터의 사용을 "프롬프트"할 것인가? –

+0

사용자 정의로 정의 된 사용자 정의 문제를 잘 설명했습니다. 비교할 수없는 유형; 오히려 아래쪽 투표에 의해 두려워지기 전에 너무 모호한 "구두"처럼 그것을 페어링하기보다는 ... oh so –

0

예를

std::set<std:set<unsigned int>> set_o_sets; 

를 들어

나에게 어떤 도움이 무초는 평가입니다 std::set<unsigned int>

비교하는 방법을 정의 할 필요없이 잘 작동 . 우분투 ..

#include<set> 
#include<iostream> 
using namespace std; 

struct read_tag{ 
    unsigned int read_id; // want std::set to use this 
    int offset;   // metadata 
    bool orientation;  // metadata 
}; 
struct read_tag_compare { 
    bool operator() (const read_tag &a, const read_tag &b) const { 
     return a.read_id > b.read_id; 
    } 
}; 
struct read_compare { 
bool operator() (const set<read_tag, read_tag_compare> &a, const  set<read_tag, read_tag_compare> &b) const { 
    return true; 
} 
}; 

int main() 
{ 
    set<read_tag, read_tag_compare> block; 
    set<set<read_tag, read_tag_compare>, read_compare> blocks; 
    blocks.insert(block) 
} 

위는 내가 편집 한 것입니다.

+1

그걸 보여줄 수 있습니까? –

+0

코드를 복사하여 붙여 넣기 만하면됩니다. 오류없이 정상적으로 컴파일되었습니다. 어떻게 보여줄 수 있니? – Parker

+0

사실, 네,이 컴파일, 그 blocks.insert() 그 오류입니다. –