2013-07-11 3 views
1

이제이 문제에 대해 많은 것을 알게되었으므로이 문제를 완전히 다시 작성해야했습니다.새로운 기능으로 내 개체가 올바르게 작동하지 않습니다.

배경 :

내 프로그램이 directx11에서 일부 3D 객체를 끌고있다. 필요한 3D 객체를 그리는 데 필요한 데이터, 포인터 및 함수가 포함 된 클래스가 있습니다. 모든 것이 잘 작동했다. 나는 많은 다른 3d 객체를 생성 할 수 있었고, 내가 원했던 곳에 그것들을 그릴 수 있었다. 큰!

그런 다음 컨테이너에 넣고 벡터에 넣을 필요가있어서 수동으로 각 객체를 만들 필요가 없었습니다. 문제가 발생한 곳이었습니다. 5시에 1 번 충돌합니다.

Unhandled exception at 0x00C308C1 in SpritesNTextN3D.exe: 0xC0000005: Access violation reading location 0xFFFFFFFF. 

벡터 및지도를 사용할 때 충돌이 발생했습니다. 나는 질문이 줄을 계속하고 새로운 포인터 및 사용하여 시도 :이 또한 나는 그것의 그리기 기능을 실행 할 때 충돌이 발생

ThreeD_Cube* threed_cube_p; 
threed_cube_p = new ThreeD_Cube; 

합니다.

threed_cube_p->draw(threeD, camera, d3dContext_mp); 

그러나 표준 객체로 만든 경우 :

ThreeD_Cube threed_cube_; 

추첨 기능이 충돌하지 않습니다.

threed_cube_-.draw(threeD, camera, d3dContext_mp); 

마찬가지로 threed_cube_에 대한 포인터를 만들면 예상대로 작동합니다.

질문 : 기본 생성자가 아니라고하고 새로운 기능

. 이 문제를 해결하기 위해 내가 봐야 할 것이 있습니까?

+0

'threed_cube_vec'는 어디에 있나요? 당신이 얻는 에러는 비어 있음을 나타내는 것처럼 보이고,'operator [] (size_t)'를 사용하면'.at (size_t)'와는 달리 경계를 검사하지 않을 것입니다. – WhozCraig

+0

당신은 뭔가를 잡고있는 벡터입니까? 예, 확실히 새로운 객체에 복사 할 수 있습니다. 난 그냥 = threed_cube_vec.size() 루프에 넣고 동일한 결과가 있습니다. 나는 당신의 의견을 잘못 이해하지 않기를 바랍니다. – David

+2

나는 야생 예측을하고 그것이'vector' 구현이 아니라, 당신의 코드에서, 아마도 ThreeD_Cube 구현이 그 범인이라고 말할 것이다. [Three of Rule] (http://stackoverflow.com/questions/4172722/what-is-the-rule-of-three)에 복종하고 있습니까? – Praetorian

답변

0

Crash after m = XMMatrixIdentity() - aligment memory in classes?

이 항목에서는 내 문제에 대한 답을 다룹니다. 결국 XMMATRIX가 메모리 정렬로 인해 새로운 충돌을 일으키는 것을 추적했습니다.

는 여기에 문제의 단축 버전입니다 :

void matrix_test_pointer() 
{ 
    XMMATRIX* xmmatrix_p; 
    xmmatrix_p = new XMMATRIX; 
    *xmmatrix_p = XMMatrixIdentity(); // this is where it crashes 
} 

void matrix_test() 
{ 
    XMMATRIX xmmatrix; 
    xmmatrix = XMMatrixIdentity(); 
} 

int main() 
{ 
    string wait; 

    matrix_test(); 
    cout << "matrix_test() completed.\n"; 
    matrix_test_pointer(); 
    cout << "matrix_test_pointer() completed.\n"; // If it does you are lucky :) 

    cin >> wait; 
    return 0; 
} 

기회는 완료 matrix_test하지만 포인터가 완료되기 전에이 충돌합니다.

1

생성자가 좋지만 불량/부족 (기본값) 할당 연산자와 불량/불충분 (기본값) 복사 생성자가있는 것 같습니다.

//threed_cube_vec[0].draw(threeD, camera, d3dContext_); // doesnt work!!! 

그것은 threed_cube_vec [0]는 나쁜/손상 개체에 무엇이 당신을 알려줍니다

는 일부 코드의 작품의 일부하지만 일부하지 왜 보자.

ThreeD_Cube test = threed_cube_vec[0]; // But, if I copy it... 

이 줄에서 (어떤 이유로) 먼저 생성자가 호출되어 좋은 개체를 제공합니다. 그런 다음 "=이"라고, 일부 개체가 수정되어 있지만 개체는이 "="이

ThreeD_Cube* test = &threed_cube_vec[0]; 

포인터에 관해서는, 그것은 본질적으로 [0 threed_cube_vec 객체 전에 이미 좋은 이후 여전히 좋은 ] 자체는 여전히 손상되었습니다.

ThreeD_Cube test = threed_cube_vec[0]; 
vector<ThreeD_Cube> test2; 
test2.push_back(test); 
test2[0].draw(threeD, camera, d3dContext_); 

이것은 말한대로 문제가 해결되지 않았습니다. "test"는 좋은 객체이지만 test2로 push_back (test)하면 복사본을 푸시 백합니다 [test2.push_back (std :: move (test))로 변경하면 문제가 사라질 수 있습니다. 복사 생성자가 불완전하고 test2 [0]의 개체가 손상되었습니다. 비슷한 시나리오가 맵에서 발생합니다.

결론 : 개체가 생성자에서 생성 된 경우 좋은 개체를 얻을 수 있습니다. 객체가 복사 생성자에서 비롯된 경우 객체가 손상되었습니다.

빨리 테스트 할 수 있습니다 : 선언 한 후에 벡터 크기를 조정하면 오류가 일시적으로 사라집니다.

+0

답장 작성자 주셔서 감사합니다. 메인 포스트에 복사 생성자 예제를 추가했습니다. 이것은 문제없이 작동합니다. 벡터 그리기에 resize를 호출 해 보았습니다. 충돌합니다. 새 벡터를 만든 다음 크기를 조정하고 복사하면 충돌합니다. 이것을 시험해 볼 수있는 또 다른 시험이 있습니까? 내가이 시험 결과를 올리 길 원한다. – David

+1

gdb를 사용하는 경우 줄 바로 다음에서 분리하십시오. ThreeD_Cube test = threed_cube_vec [0]; "test"와 "thread_cube_vec [0]"을 출력하고 어떤 차이가 있는지 확인하십시오. –

+0

Visual Studio 2012를 실행 중이므로 어떻게 할 것인지 잘 모르겠습니다. 나는 내가 할 시간이있을 때 더 많은 시험을하려고 노력할 것입니다. 일단 내가 가지고 있으면 해결책을 게시하고 싶습니다. 나는 사람들이 지적한 것처럼 객체를 복사 할 때 무언가가 될 것이라고 확신합니다. – David