why in code:
void foo ( const int ** ); int main() { int ** v = new int * [10]; foo(v); return 0; }
this error:
invalid conversion ‘int**’ ‘const int**’ [-fpermissive]|
i thought possible convert non-const const.
it because trying convert int** const int**
int ** v = new int * [10]; // v int** foo(v); //but foo takes const int**
int **
is: "a pointer pointer integer".const int **
is: "a pointer pointer constant integer".
the use of const
contract , cannot meet contract going through indirection of 2 references.
from standard:
const char c = 'c'; char* pc; const char** pcc = &pc; // not allowed (thankfully!) ^^^ here bundit hidden under const: "i not modify" *pcc = &c; // *pcc "pointer const" right? allowed... *pc = 'c'; // allow modify const object, *pc char right?
so possible modify const char
always, use procedure above.
and also:
char *s1 = 0; const char *s2 = s1; // ok... char *a[max]; // aka char ** const char * const*ps = a; // no error!
nice cite link below:
by way of analogy, if hide criminal under lawful disguise, can exploit trust given disguise. that's bad.
http://www.parashift.com/c++-faq-lite/constptrptr-conversion.html
related invalid conversion derived** → base**
. if legal convert derived** → base**
, base**
dereferenced (yielding base*
), , base* made point object of different derived class, cause serious problems. see why:
class vehicle { public: virtual ~vehicle() { } virtual void startengine() = 0; }; class car : public vehicle { public: virtual void startengine(); virtual void opengascap(); }; class nuclearsubmarine : public vehicle { public: virtual void startengine(); virtual void firenuclearmissle(); }; int main() { car car; car* carptr = &car; car** carptrptr = &carptr; vehicle** vehicleptrptr = carptrptr; // error in c++ nuclearsubmarine sub; nuclearsubmarine* subptr = ⊂ *vehicleptrptr = subptr; // last line have caused carptr point sub ! carptr->opengascap(); // might call firenuclearmissle()! ... }
http://www.parashift.com/c++-faq-lite/derivedptrptr-to-baseptrptr.html
consider:
class vehicle { public: virtual ~vehicle() { } virtual void startengine() = 0; }; class car : public vehicle { public: virtual void startengine(){printf("car engine brummm\n");} virtual void opengascap(){printf("car: open gas cap\n");} virtual void opengascap2(){printf("car: open gas cap2\n");} virtual void opengascap3(){printf("car: open gas cap3\n");} virtual void opengascap4(){printf("car: open gas cap4\n");} }; class nuclearsubmarine : public vehicle { public: int i; virtual void startengine(){printf("nuclear submarine engine brummm\n");} virtual void firenuclearmissle3(){printf("nuclear submarine: fire missle3!\n");} virtual void firenuclearmissle(){printf("nuclear submarine: fire missle!\n");} virtual void firenuclearmissle2(){printf("nuclear submarine: fire missle2!\n");} }; int main(){ car car; car* carptr = &car; car** carptrptr = &carptr; //vehicle** vehicleptrptr = carptrptr; // error in c++, but: vehicle** vehicleptrptr = reinterpret_cast<vehicle**>(carptrptr); nuclearsubmarine sub; nuclearsubmarine* subptr = ⊂ *vehicleptrptr = subptr; // carptr points sub ! carptr->opengascap(); // nuclear submarine: fire missle3! carptr->opengascap2(); // nuclear submarine: fire missle! carptr->opengascap3(); // nuclear submarine: fire missle2! //carptr->opengascap4(); // seg fault }
Comments
Post a Comment