2010-06-28 4 views
1

이 코드가 있습니다. 내가 사용한다연관 배열에서 값을 읽으면 새 키가 생성됩니다.

pvalueholder는 다형성 인 클래스 다. 모든 종류의 문자열을 보유 할 수있다. .. 또한 유형이 정의되지 않을 수있다.

typedef hash_map<pvalueholder,pvalueholder,pvaluehasher > hashtype; 
hashtype h; 
pvalueholder v; 
v="c"; 
h[v]=5; // h has one element 

pvalueholder v2=h[v]; // here h gets a new key/value how is that possible? 
cout << (string) (h[v]) << endl; // here h gets another new key/value how is that possible? 
int i =0; 
for (hashtype::iterator h1=h.begin(); h1!=h.end();h1++) 
{ 
    cout << "no: " << i++ << endl; 
} // this prints three lines, it should print one... 

여기서 두 값은 정의되지 않습니다. 세 번째 값은 예상대로 5입니다.

size_t pvaluehasher::operator() (const pvalueholder& p) const 
    { 
     cout << "hashvalue:" << p.value->hashvalue() << endl; 
    return p.value->hashvalue(); 

    } 

반환 여기에 인쇄 된 것입니다 : hashvalue : 84696444 hashvalue : 84696444 hashvalue : 84696444 반환 : 1 hashvalue : 84696444 반환 : 1 hashvalue : 84696444 반환 : 1 개 반환 : 1 hashvalue : 84696444

어떤 아이디어가 있습니까? 감사합니다.

솔루션 : Microsoft STL의 경우 함수 연산자() (매개 변수 1, 매개 변수 2)가 달라야합니다. Microsoft의 경우 매개 변수 1과 매개 변수 2 사이의 관계를 반환해야합니다. gcc의 경우 동등 함을 반환해야합니다. 나는 평등을 반환했다. 키에 대한 비교 함수가 올바르지 않습니다 ... Microsoft STL보다 작은 값을 반환해야 함에도 불구하고이 함수는 true를 반환했습니다.

답변

0

해결 방법 : Microsoft STL의 경우 operator() (parameter1, parameter2) 함수가 달라야합니다. Microsoft의 경우 매개 변수 1과 매개 변수 2 사이의 관계를 반환해야합니다. gcc의 경우 동등성을 반환해야합니다. 나는 평등을 반환했다. 키에 대한 비교 함수가 올바르지 않습니다 ... 함수는 Microsoft STL의 경우보다 반환해야하는 동안 동등 함을 위해 true를 반환했습니다.

2

제 생각에 해시 함수가 올바르지 않습니다. 동일한 키가 주어진 다른 해시 값을 생성한다는 의미입니다. "c".

pvalueholder에 대한 신고 및 전체 코드는 pvaluehasher으로 표시하십시오.

+0

연관 배열을 읽을 때라도 잘못된 해시 함수로 인해 새 키가 생성 될 수 있습니까? – Aftershock

+0

같은 번호를 반환하는 것처럼 보이는 해시 함수를 추적했습니다. – Aftershock

+1

@Aftershock, "인수 키 값을 찾을 수없는 경우 데이터 유형의 기본값과 함께 삽입됩니다"http://msdn.microsoft.com/en-US/library/h90ew76k%28v= VS.80 % 29.aspx –

2

표준화되지 않았기 때문에 hash_map에 대한 의견을 말하는 것이 거의 불가능하며 기존 구현은 완전히 일관성이 없습니다. 더 나쁜 것은 코드가 정확하지 않거나 컴파일 가능한 코드가 아닌 것입니다. 키와 연관된 값이 int이고 다른 곳이 문자열 인 것 같습니다.

std::tr1::unordered_map 사용하고 나머지 코드는 컴파일하고 다음과 같이 합리적인 것 같다하기 위해 고정 :

#include <unordered_map> 
#include <iostream> 
#include <string> 

using namespace std; 

typedef std::tr1::unordered_map<std::string, int> hashtype; 

std::ostream &operator<<(std::ostream &os, std::pair<std::string, int> const &d) { 
    return os << d.first << ": " << d.second; 
} 

int main() { 
    hashtype h; 
    std::string v = "c"; 

    h[v]=5; // h has one element 

    int v2=h[v]; 
    cout << h[v] << endl; 
    int i =0; 
    for (hashtype::iterator h1=h.begin(); h1!=h.end();h1++) 
    { 
     cout << *h1 << endl; 
    } // this prints three lines, it should print one... 

    return 0; 
} 

내가 얻을 출력은 다음과 같습니다

5 
c: 5 

이 꽤 합리적인 것 - 우리는 ' 예상대로 한 항목 만 삽입했습니다.

관련 문제