|
cartobase
4.7.0
|
A few tips for portable programming :
It's a list of little things
std:: in .h files before all classes of the standard namespace:string streams: istream ostream ifstream ofstream cout cerr cin streambuf iomanips: ios setw setprec vector set map multimap std in .cc files: #include <cstdlib> (put it after the #include lines) -> no need to use std:: everywhere in .cc files
"using something" in a .h (it's not a portability issue but a potential cause of conflicts)<something.h> and <something>, always use the <something> version (without .h):etc... Using *.h variants causes conflicts in modern compilers (gcc 3 and later), and even with older ones (egcs and gcc 2.95) in some conditions (vector<bool> for instance has diffent implementations in <vector> and <vector.h> with distinct internal organization and objects sizes, and mixing them is a source of ununderstandable crashes and bugs...)
<iostream> as soon as cin or cout is used in a source file, on some systems/compilers they are not always needed but thay may not be defined when <fstream> is included and not <iostream> do NOT use:
MAXFLOAT etc
but rather:
FLT_MAX
FLT_MAX is defined in <float.h>
Or even better: use std::numeric_limits, which is part of standard C++ since gcc 3.x, but also available in cartobase with older compilers:
do NOT use <values.h>
Some systems don't provide it. Some (old) compilers do not provide <limits> either. Instead, use the following:
<cartobase/config/cartobase_config.h> defines type limits macros on integer types (INT32_MAX for instance) and includes <limits.h> or equivalents in a portable way. It also defines isnan() <cartobase/type/limits.h> includes in a portable way <limits> (C++) or defines equivalents<cartobase/config/cartobase_config.h> before using file IO functions: cartobase config takes care of making use of 64 bit file IO functions.but rather:
I know it should not cause any problem in principle, but even the Intel compiler (which is not so bad in other situations) doesn't accept such re-declarations. In any case, it's very simple to avoid, so please do it...
I personnally liked such a convenient code, and it works well with gcc, but other compilers don't allow it (it's simply not correct C). We have to go back to more primitive forms (and far less convenient) such as:
You can also use STL vectors, or a carto::block, instead in most situations:
near, far (which are calling modes on Windows)small, large <unistd.h> etc.rint() is defined in <cartobase/config/cartobase_config.h> max() is not defined in every compiler. But STL provides some templated versions of itopendir(), closedir(), readdir() - use carto::FileUtil and carto::Directorymkdir( name, access_rights ) -> mkdir( name ) (on windows, no access rights, only 1 parameter). Use carto::Directory.isnan() is defined in <cartobase/config/cartobase_config.h> xxxFileMapping() functions: use cartobase allocators