C/C++ Naming conventions (Part II)
I estimate about half the code I have reverse engineered has inconsistent naming conventions. Actually, nearly all code I have ever reverse engineered (and most of the code I have written) has some naming inconsistency. At issue is grossly inconsistent naming.
Consistent naming provides the following benefits:
- The sames kinds of objects, entities, types will all have names that have the same sort of "smell" (for lack of a better word). That is, when you see something of a name with a certain visual pattern and semantic structure, it becomes much easier to make a "scientific wild-a** guess" (SWAG) concerning what sort of function that object or entity performs, and what it's capabilities are.
- Consistent naming schemes can promote automatic code generation. Given a choice between code, or writing a generator to write code, it's often more cost effective to write the code generator instead. This may be true even when an API is a "one-of" given it has a sufficient number of independent entities.
Naming conventions provide a fertile ground for programming “wars of religion.” What follows is a workable scheme for naming conventions in object-oriented c (and in c++), including rationale for the scheme.
My Personal Scheme
- use_lower_case: For accessor methods, using all lower case in a verb/object form where the words in the method name are separated by underscores (`_`) works really, really well.
- Capitalization: A capitalized noun, e.g., Vertex, always denotes a locally derived and typedef'ed class.
- CamelCase: Strictly limited to tydedefs. AdjectiveNoun always denotes a typedefed function pointer. For example:
typedef int (*PrintFunc)(int a, float b, double c);
The scheme used above has a lot in common with a large number of APIs both commercially available (e.g., Qt) or available as Free Software (e.g., glib, GTK). The differences reflect my personal experience. I personally use these conventions for Java as well, but CamelCase is so widely entrenched in the Java community I keep my opinion to myself.
In any sufficiently large code base, there is always one or more exceptions, where the same naming scheme is used for more than one type. I attempt to make the two types as far apart in function as possible, to make it easier to determine it’s function by context.