指針雖然這編譯:分配指針帶或不帶預選賽
char* p2c;
const char* p2cc = p2c; //fine
因爲LHS尖類型有RHS尖類型的所有預選賽,這並不:
char** p2p2c;
const char** p2p2cc = p2p2c; //fail
但這種作用:
const char * const * p2cp2cc = p2p2c; //fine
爲什麼會發生這種情況?
指針雖然這編譯:分配指針帶或不帶預選賽
char* p2c;
const char* p2cc = p2c; //fine
因爲LHS尖類型有RHS尖類型的所有預選賽,這並不:
char** p2p2c;
const char** p2p2cc = p2p2c; //fail
但這種作用:
const char * const * p2cp2cc = p2p2c; //fine
爲什麼會發生這種情況?
這不起作用:
char** p2p2c;
const char** p2p2cc = p2p2c; //fail
如果允許你將被允許破壞const,正確性:
const int k = 10;
int *p;
int **pp = &p;
int const **kpp = pp; // Should this be allowed, if so:
*kpp = &k; // fine, kpp promises not to change it
// yet this does p = &k;
// p made no such promise! this is a hidden const_cast!
*p = 5;
如果轉讓是允許的,你會這樣設置一個非常量指針(中間值)來引用一個常量值,可能會導致一個不明顯的行爲在非顯而易見的方式看到。通過禁止該操作,類型系統更安全。
但這樣做:
const char * const * p2cp2cc = p2p2c; //fine
這是好的,由於中間指針是固定的,這是不可能重置中間指針指const對象和打破常量-正確性
cdecl確實有助於這種情況。
const char** p2p2cc = declare p2p2cc as pointer to pointer to const char
和
const char * const * p2cp2cc = declare p2cp2cc as pointer to const pointer to const char
正如你所看到的,第二個版本有內部和外部指針常量,這意味着它也不能修改。第一個版本有INNER指針const和外部非const從而破壞const。
在另一方面,這個工程:
char** const p = p2p2c;
最後一個例子只會編譯C++,但不是在C. – AnT
@AndreyT爲何如此? – emesx
這就是它在C和C++中的方式。這是兩種不同的語言,具有不同的常量正確性規則。在C++中'T **'可以轉換爲'const T * const *'。在C'T **'中可以轉換爲'T * const *',但不能轉換爲'T * const *'。 http://stackoverflow.com/a/5249001/187690 – AnT