2013-04-18 9 views
0

ID (정수) 목록이 있습니다. 내 응용 프로그램을 쉽게 처리 할 수 ​​있도록 그들은 (이런 종류의 내 응용 프로그램에서 정말 중요하다) C++ 인덱스 - 인덱스 맵

9382 
297832 
92 
83723 
173934 

예를

를 들어, 정말 효율적인 방법으로 정렬됩니다.

이제 다른 벡터에서 특정 값의 ID에 액세스해야하는 문제에 직면하고 있습니다.

예를 들어 ID 9382의 특정 값은 someVectorB [30]에 있습니다. 나는 그러나

const int UNITS_MAX_SIZE = 400000; 

class clsUnitsUnitIDToArrayIndex : public CBaseStructure 
{ 
private: 
    int m_content[UNITS_MAX_SIZE]; 
    long m_size; 
protected: 
    void ProcessTxtLine(string line); 
public: 
    clsUnitsUnitIDToArrayIndex(); 
    int *Content(); 
    long Size(); 
}; 

을 사용하고있다

지금은 400.000에 UNITS_MAX_SIZE 살리신 것을, 나는 페이지 스택 오류를 얻을, 그리고 내가 뭔가 잘못하고있는 중이 야 하더군요. 나는 전체 접근법이 정말로 좋지 않다고 생각한다.

"위치"가 다른 경우 다른 벡터에서 ID를 찾으려면 어떻게해야합니까?

ps : 파일에서 쉽게 읽을 수 있고 파일로 쉽게 serialize 할 수있는 간단한 것을 찾고 있습니다. 그래서 전에이 무차별 대입 방식을 사용 해왔다.

+2

당신이 사용을 고려 셨나요 표준 : : 벡터 또는 표준 : 맵을 사용하여, 당신은 또한 당신의 clsUnitsUnitIDToArrayIndex

을 파괴하면서 자원을 해제 기억해야하지만, 권장 사용량이 다른 회원들에 의해 제안으로'표준 : :지도 '? –

+1

현재 m_content 배열이 즉각적인 오류를 일으킬 스택의 크기를 초과하면 나는 놀라지 않을 것입니다. 관계없이이 접근 방식은 꺼져 있습니다. 어떤 문제를 해결하려고합니까? –

+0

특정 ID가 벡터의 어느 위치에 있는지 알려주는 목록을 보관하고 싶습니다. – tmighty

답변

3

당신은 INT 년대 INT 년대와 인덱스 번호 비 연속적인 대응 관계를 원하는 경우 std::map을 고려해야합니다. 이 경우 다음과 같이 정의합니다.

std::map<int, int> m_idLocations; 

지도는 두 유형 간의 매핑을 나타냅니다. 첫 번째 유형은 "키"이며 두 번째 유형 인 "값"을 조회하는 데 사용됩니다. 각 ID 조회를 위해 당신은 그것을 삽입 할 수 있습니다

m_idLocations[id] = position; 
// or 
m_idLocations.insert(std::pair<int,int>(id, position)); 

그리고 다음과 같은 구문을 사용하여 조회 할 수 있습니다 : 일반적으로

m_idLocations[id]; 

worse-이 red-black trees를 사용하여 구현하는 STL에서 std::map을 O (log n)의 캐스트 검색 속도. 이것은 거대한 배열에서 얻을 수있는 O (1)보다 약간 느립니다. 그러나 공간을 상당히 효율적으로 사용하기 때문에 실제로 엄청난 양의 숫자를 저장하지 않으면 연습의 차이를 눈치 채기 어렵습니다. 엄청난 양의 조회를 수행합니다.

편집 : 의견의 일부에 대응

나는 그것이 (1) O (로그 n)에 O에서 이동하는 응용 프로그램의 속도에 큰 차이를 만들 수 있다는 것을 지적하는 것이 중요하다고 생각합니다 고정 된 메모리 블록에서 트리 기반 구조로 옮겨가는 것에 대한 실질적인 속도 문제는 말할 것도 없습니다. 그러나 나는 당신이 말하고자하는 것을 int-to-int 매핑으로 표현하고 조숙 한 최적화의 함정을 피하는 것이 중요하다고 생각한다.

개념을 표현한 후에는 프로파일러을 사용하여 속도 문제가있는 곳과 위치를 확인하십시오. 맵이 문제를 일으킨다는 것을 알게되면 맵핑을보다 빠른 것으로 생각하는 것으로 대체해야합니다. 최적화가에 도움이되었는지 테스트했는지 확인하고 대표하는 내용과 변경해야하는 이유에 대한 커다란 설명을 포함하는 것을 잊지 마십시오.

+0

으로 편집했습니다. 두 벡터의 값은 같지만 vector1 : 43, 98, 11 및 vector2 : 98, 11, 43 – tmighty

+0

과 같이 혼합되어 있습니다. 설명해 주셔서 감사합니다. 하지만 너무 많은 데이터 (400.000 * 2 ID 아마 RAM을 위해 너무 많이) 아마, 내가 파일 매핑을 사용하여 파일에서 그것을 얻고 단순히 memcopy를 사용하여 값을 검색해야합니까? 내 코드는 거대하며 간단하게 시도해보기 위해 몇 시간이 필요합니다. 그래서 내 접근법이 논리적으로 보이는지 미리 질문하고 싶습니다. – tmighty

+1

800,000 개의 ID는 로그 연산에 비해 상대적으로 작습니다. 원근감 로그 (800000) ~ = 5.903에 넣으려면 큰 계산의 규모가 작습니다. 많은 양의 데이터를 복사하는 것은지도 검색을 수행하는 것이 훨씬 느립니다. 이 모든 것은 응용 프로그램이 어떻게 결합되어 있느냐에 달려 있습니다. –

1

아마 당신은 int m_content [UNITS_MAX_SIZE]로 인해 stackoverflow 오류가 발생합니다. 배열은 스택에 할당되며 400000은 스택에 꽤 큰 숫자입니다. 복사 작업을 피하기 위해 당신은 동적으로 할당되고, 대신에 표준 : : 벡터를 사용할 수 있으며 벡터 부재의 참조를 반환 할 수 있습니다

std::vector<int> m_content(UNITS_MAX_SIZE); 

const std::vector<int> &clsUnitsUnitIDToArrayIndex::Content() const 
{ 
    return m_content; 
} 
+0

결국 동적 할당과 고정 할당의 차이점은 무엇입니까? 둘 다 같은 크기가됩니까? 예를 들어, 실제로 벡터에 400.000의 ID가있는 경우 동적으로 할당했는지 또는 바로 할당했는지는 중요하지 않습니다. – tmighty

+1

@tmighty, 고정 할당은 스택에 할당되고 스택에는 제한된 크기가 있지만 동적 할당의 한계는 사용 가능한 RAM으로 제한됩니다. 그런 거대한 배열을 사용하려면 std :: vector와 같은 표준 컨테이너를 사용하여 stackoverflow 문제를 피하거나 힙 wtih 키워드에 배열을 정의 할 수 있습니다. –

+0

다음 코드에서 벡터에 액세스 할 수있는 방법을 알려주십시오. 외부? 내 "int * Content();" 쓸모가 없습니다. 그리고 나는 당신이 잘못 입력했다고 생각합니다. "std :: vector m_content();"가 아니면 안됩니다. ? – tmighty

1

아무 것도 작동하지 않으면 배열을 생성자에서 동적으로 할당 할 수 있습니다. 그러면 힙에서 큰 배열이 이동하고 페이지 스택 오류가 발생하지 않습니다.