Compile errors when porting from VC++ 6 to VC++ .Net
I have an existing project which we currently compile (successfully) on VC++ 6.0
I am trying to compile it in VC++ 7 but I get some compile errors which I don't really understand.
1. std:: vector< MyInfo >::iterator ListIter = ...
if( ListIter ) { ... }
I get an error C2451: conditional expression of type 'std::vector<_Ty, Ax>::iterator' is illegal with....
If I change this to the more explicit: if( ListIter != 0 ), it compiles fine.
2. char newData[sizeof( MyInfo )];
std::vector< MyInfo >::iterator ListIter = ...
memcpy( newData, ListIter, sizeof(MyInfo) );
I get an error C2664: cannot convert parameter 2 from std::vector<_Ty,_Ax>::iterator to const void * with...
3. if ( !ListIter ) ...
get an error C2675: unary '!' : 'std::vector< _Ty, _Ax >::const_iterator' does not define this operator or a conversion to a type acceptable to the predefined operator
I don't understand why it doesn't compile in VC7 but it does in VC6. Can anyone help?
Thanks
Stef
Re: Compile errors when porting from VC++ 6 to VC++ .Net
Quote:
Originally posted by SPatten
I have an existing project which we currently compile (successfully) on VC++ 6.0
I am trying to compile it in VC++ 7 but I get some compile errors which I don't really understand.
1. std:: vector< MyInfo >::iterator ListIter = ...
if( ListIter ) { ... }
I get an error C2451: conditional expression of type 'std::vector<_Ty, Ax>::iterator' is illegal with....
If I change this to the more explicit: if( ListIter != 0 ), it compiles fine.
The compiler is correct -- iterators may not be NULL. Therefore you are relying on undefined and undocumented internals of your implementation of STL.
There is no such thing defined in the C++ language as a NULL iterator, therefore to have your code compile for all versions of Visual C++, plus any other C++ compiler, you'll have to think up another way to determine if an element doesn't exist. An iterator can equal the end() iterator -- maybe you can rewrite your code using the end() iterator to determine validity.
Quote:
2. char newData[sizeof( MyInfo )];
std::vector< MyInfo >::iterator ListIter = ...
memcpy( newData, ListIter, sizeof(MyInfo) );
I get an error C2664: cannot convert parameter 2 from std::vector<_Ty,_Ax>::iterator to const void * with...
Again, this is incorrect -- the value of an iterator has no use to the program, except when comparing with other iterators (for example, comparing an iterator to end() or begin()). To use them in any other way, such as an argument to memcpy(), is undefined behavior. You can dereference iterators, but other than that, you assume you know nothing about the internals of them (I'm refering to the user of the iterator's point of view -- if you are writing your own iterators, then of course, you need to know the internals of your own iterators). You are assuming that iterators are implemented in a certain way -- your assumptions were incorrect for the newer versions of Visual C++.
Also, if MyInfo is a non-POD class, usage of memcpy() is illegal and leads to undefined behavior. If MyInfo contains member functions, or contain members that contain member functions, then your code is dangerous and may not work correctly. The memcpy() function is reserved for low-level C compatible structs, types, and arrays, not C++ objects. I don't know exactly what you're trying to do -- maybe you can tell us.
Quote:
3. if ( !ListIter ) ...
get an error C2675: unary '!' : 'std::vector< _Ty, _Ax >::const_iterator' does not define this operator or a conversion to a type acceptable to the predefined operator
Again, relying on the internals of how the iterator is implemented.
Regards,
Paul McKenzie