C++ non const to const 캐스팅 컴파일 오류
-
12-11-2019 - |
문제
아래 코드는 컴파일되지 않습니다
void aaa(const int **a) {
}
int *a[] = {new int[2]};
aaa(a);
"'int에서 매개변수 1을 변환할 수 없습니다. [1]'을 'const int *로VS2010의 " 및 gcc의 유사한 오류
내 선언을 다음과 같이 변경할 때:
int const *a[] = {new int[2]};
또는
const int *a[] = {new int[2]};
컴파일되지만 const가 아닌 변수 선언을 허용하지 않는 이유를 이해할 수 없습니다.
해결책
유형 a
~이다 int*[]
;당신이 원하는 유형은 int const**
.
int*[]
로 변환 int**
, 그러나 이는 암시적으로 다음으로 변환되지 않습니다.int const**
.이유를 이해하려면 다음 코드를 고려하십시오.
static int const ci = 42;
void aaa( int const** out )
{
*out = &ci;
}
int
main()
{
int* pa;
aaa( &pa ); // NOT LEGAL, because...
*pa = 0; // would now change ci
std::cout << ci << std::endl;
return 0;
}
보시다시피,이 변환을 허용하면 캐스트가 필요하지 않고 Const가 끊어집니다.
수행 중인 작업에 따라 다음을 사용할 수 있습니다.
void aaa( int const* const* out );
암시적 변환 int**
에게 int const *const *
합법적입니다.(그렇지 않으면 const_cast
어딘가에, 컴파일러에게 당신이하고있는 일을 알고 있고 그것이 실제로 문제가되지 않는다고 말하기 위해.)
다른 팁
함수 aaa
포인터-포인터-상수-int를 기대합니다.귀하의 변수 a
포인터 대 포인터 대 int입니다.후자를 전자에 할당하는 것은 오류입니다.
둘 다 int const *a[]
그리고 const int *a[]
실제로는 동일합니다. 서명과 일치합니다. aaa
.시도했다면 int * const a[]
, 이는 다른 유형(포인터-상수-포인터-to-int)이 되며 유형 오류가 다시 발생합니다.
원하는 기능이 있다면 aaa
상수 포인터-포인터-int를 취하려면 다음을 작성해야 합니다. aaa(int ** const a)
, 하지만 매개변수 값에 상수성을 갖는 것은 실제로 호출할 수 있는 항목에 영향을 주지 않습니다.
편집하다: "하지만 constness는 암시적으로 추가되지 않았나요? 암시적 캐스트로 완료되었나요?(실제 질문은 무엇입니까)"
전달하는 값에 암시적으로 불변성을 추가할 수 있습니다.
void aaa(const int a) {}
int b=5;
aaa(b);
...또는 한 레벨 포인터
void aaa(const int* a) {}
int *b=new int;
aaa(b);
...하지만 더 깊게 추가할 수는 없습니다.예를 들어 다음은 유효하지 않습니다.
void aaa(const int** a) {}
int* b=new int;
int** c=&b;
aaa(c);
나는 James Kanze가 그의 답변에서 그것을 훨씬 더 잘 설명한다고 생각합니다.