Annotation of mstools/mfc/doc/tn004.txt, revision 1.1.1.1

1.1       root        1: Microsoft Foundation Classes                           Microsoft Corporation
                      2: Technical Notes              
                      3: 
                      4: #4 : Template Classes and MFC
                      5: 
                      6: This note describes MFC template class issues and the MFC "templdef" 
                      7: template expansion sample code.
                      8: =============================================================================
                      9: The Problem
                     10: ===========
                     11: 
                     12: There has long been recognized within the C++ community the need for
                     13: template classes -- classes that can be instantiated based on an
                     14: exact type specified by the user.  A common example would be a linked
                     15: list class -- a linked list of what type of object?  With template
                     16: classes the user of the class can specify that:  "I want a linked
                     17: list of CFoo objects."
                     18: 
                     19: -----------------------------------------------------------------------------
                     20: The templdef sample
                     21: ===================
                     22: 
                     23: While a syntax for template classes has been generally agreed-upon
                     24: within the C++ community, exact details have not been worked out.
                     25: We found it useful to provide template classes to the user in the
                     26: interim.  The approach decided upon was to use a syntax for our
                     27: template classes based on that generally used within the C++
                     28: community.  This syntax is then expanded and modified slightly by a
                     29: simple template expander called "templdef."  For this expansion the
                     30: user specifies a "typedef'ed" name to be used as an alternative to
                     31: the template_class<type_specifier> class name.
                     32: 
                     33: With this approach the Foundation user can begin to write template
                     34: classes following the generally agreed-upon syntax for C++
                     35: templates.  This code can be ported to the eventual final agreed-upon
                     36: syntax when the ANSI C++ report is issued.  Also, the Foundation user
                     37: can read the Foundation template classes as general examples of how
                     38: one writes templates.  And the templdef source code provides an
                     39: example of how one can use the Foundation classes.
                     40: 
                     41: In order to provide easily readable output from the templdef template
                     42: expander, we have chosen to leave comments in the expanded output,
                     43: and to substitute-in textually the type parameters the user
                     44: specifies.  If the user desires to expand template classes over
                     45: complicated types, use of typedef'ed type names is suggested for
                     46: template parameters.
                     47: 
                     48: We advise users wanting to experiment with template classes and
                     49: templdef should first write and completely debug a non-template
                     50: version of their class.  For example, first write a
                     51: linked-list-of-CFoos class.  When you have that working, then
                     52: generalize your linked-list-of-CFoos class to a
                     53: linked-list-of-whatever template class.  By taking this approach, you
                     54: introduce the complicating factor of "template <class CXyz>" syntax
                     55: *after* you have an already working linked-list class.  Finally, you
                     56: should expect some small changes between the template classes you
                     57: write today, and the final syntax agreed upon by the ANSI-C++
                     58: committee.
                     59: 
                     60: A good way to get started is by examining the .ctt template classes
                     61: provided with Foundation (found in mfc\sample\templdef subdirectory). 
                     62: The mkcoll.bat file gives examples of the command line syntax of the
                     63: templdef tool.  The general form of the command line syntax is
                     64: modeled after a C++ typedef of the equivalent template class.  As a
                     65: hypothetical exammple:
                     66: 
                     67: typedef CArray<CString> CStringArray;
                     68: 
                     69: becomes:
                     70: 
                     71: templdef "CArray<CString> CStringArray" array.ctt strarray.h strarray.cpp
                     72: 
                     73: Note: The actual Foundation template classes are slightly more complicated
                     74: than this example, taking a number of boolean constant template
                     75: parameters which allow several slightly different flavors of arrays
                     76: to be expanded.
                     77: 
                     78: -----------------------------------------------------------------------------
                     79: Template source formatting
                     80: ==========================
                     81: 
                     82: A source file containing a templdef template class is divided into
                     83: three sections.
                     84: 
                     85: The first section consists of comments, usage instructions, copyright
                     86: notices and the like.  This first section is stripped by templdef and
                     87: is not emitted.  The second section starts with a special:
                     88: 
                     89: //$DECLARE_TEMPLATE
                     90: 
                     91: directive, after which the template class declaration appears. 
                     92: templdef processes this section to result in the output .h file. 
                     93: After the declaration section comes a special:
                     94: 
                     95: //$IMPLEMENT_TEMPLATE
                     96: 
                     97: directive followed by any member function definitions required by the
                     98: template class.  This final section is processed into the resulting 
                     99: .cpp output file.
                    100: 
                    101: Friend functions, static member definitions, and the like can be
                    102: included as needed in these sections.  Other than #if/#else/#endif
                    103: sections expanded on a template parameter (see next section),
                    104: preprocessor commands are left unexpanded in the output files.  This
                    105: permits additional processing by the native compiler preprocessor.
                    106: 
                    107: One restriction of the templdef implementation is that the first
                    108: occurance of a template declaration (typically *the* template class
                    109: declaration) defines *all* name-wise correspondences between template
                    110: formal parameters and actual parameters throughout the template class
                    111: file.  Thus template parameter names must be used consistently
                    112: throughout all template declarations and definitions in the template
                    113: class file.  This approach is consistent with the fact that you are
                    114: expanding on only one particular, out of n possible, template
                    115: possibilities.
                    116: 
                    117: -----------------------------------------------------------------------------
                    118: Template parameters and special #if/#else/#endif processing
                    119: ===========================================================
                    120: 
                    121: Templdef template parameters can either be types, or can be
                    122: compile-time constant expressions.  In particular, if a template
                    123: parameter is "0" or "1", then templdef will evaluate (only)
                    124: #if/#else/#endif statements based on that constant parameter, and
                    125: emit only those lines of code corresponding to the true condition. 
                    126: Again, see mkcoll.bat and the Foundation template classes for
                    127: examples of how to use this feature.  
                    128: 
                    129: The #if/#else/#endif expansion depends on having exactly the manifest
                    130: constant "1" or "0" as a template parameter.  For example, if you
                    131: were to say "TRUE" or "FALSE" instead, then templdef would leave in
                    132: the #if/#else/#endif expressions for the preprocessing phase of the
                    133: compiler to expand later.  Also, this templdef evaluation does not
                    134: take into account nested #if/#else statements -- either make sure
                    135: your expansion corresponds to an inner-most nesting and use "0" or
                    136: "1" as your boolean constant template parameter, or say "FALSE" or
                    137: "TRUE" and let the compiler's preprocessing phase do the
                    138: #if/#else/#endif expansion later.  Another limitation on templdef's
                    139: capabilities in this area is that it expects #if/#else/#endif
                    140: statements to be written following the common convention of no
                    141: intervening space after the '#' sign.  If you need to write # .... if
                    142: / # .... else / # .... endif then let the compiler's preprocessor
                    143: handle the job instead.
                    144: 
                    145: -----------------------------------------------------------------------------

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.