Blog (http://blog.csdn.net/livelylittlefish
) Post the notes prepared by the author (@ Xiaoyu) on the relevant research and study content. You are welcome to correct them!
1. macro definition
# Define aspect_ratio 1.653
The macro definition aspect_ratio may never be seen by the compiler, and may be replaced by the pre-processor before the compiler starts to process the source code. We know that the macro definition will be replaced with a string in the preprocessing phase, and any part of aspect_ratio will be replaced with 1.653. Therefore, aspect_ratio does not enter the symbol table.
Symbol table Review
(1) What is a symbol table? What are the important functions of a symbol table?
A symbolic table is a table used to record various information during compilation.
Role of the symbol table:
- Register the input and output information of the compilation process
- Used for semantic check and intermediate code generation during Semantic Analysis
- As the basis for Address Allocation in the generation phase of the target code
(2) What are the common parts of a symbol table? What are their descriptions?
The table items in the symbol table contain two columns: The name column and the information column;
The name column is also called the main column, and the identifier for storing the name is called a keyword;
The information column contains many sub-columns and flag spaces, which are used to record different attributes of the corresponding name.
(3) How do I organize a symbol table? What factors does the Organization depend on?
The organization of a symbol table is divided into two types: direct organization and indirect organization.
Items in the direct organization mode are stored in a fixed length order;
In indirect organization, the main column of the symbol table stores an indicator and an integer (start position and length of the identifier) of the identifier, and the string of the identifier is stored in a string array.
The organization of the symbol table depends on the following factors:
- Whether the storage unit and length of each column in the table item are fixed
- Length limit of the identifier in a language
- Which items have common values?
- Operation and usage of symbol tables
(4) How can I view the executable program symbol table on Win32 and Linux platforms?
Dumpbin command
For example,> dumpbin/Symbols filename (where> is a command line prompt)
Objdump command
For example, # objdump-s filename (where # is a command line prompt)
Therefore, when compilation errors occur in 1.653, it is difficult to figure out the problem. In addition, during the debugging stage, it is also difficult to locate (we cannot find the defined macro value during debugging through visual stiduo or GDB on Linux, because the symbol table does not have this symbol ), therefore, the macro definition cannot be seen as WYSIWYG. You must check the code to understand the macro definition.
So how can we solve it? As follows.
2. Use const to define Constants
For example, the macro defined in define can be changed:
Const double aspectratio = 1.653; // an upper-case name is usually used for macros.
From the above, we can see that the constant has a type, which is double. As a language constant, it will certainly be seen by the compiler, and of course it will enter the symbol table. You can also check the value of this constant during debugging.
3. exclusive class Constants
If you limit the scope of a constant to a class, you must make it a member of the class ). To ensure that this constant has at most one entity, you must make it a static member.
For example, the following program can describe the definition method of the class exclusive constant.
[C-sharp]
View plaincopy
- /**
- * <Valid tive C ++>, page 14
- * Const data of class
- * Platform: Visual Studio 2005, Win32
- * Filename: item2.1.cpp
- */
- # Include <iostream>
- Using namespace STD;
- Class mytest
- {
- // (1) Error c2864: 'mytest: maxnumber1': only static const integral data members can be initialized within a class
- // Int maxnumber1 = 5;
- // (2) Error c2864: 'mytest: maxnumber2': only static const integral data members can be initialized within a class
- // Const int maxnumber2 = 5;
- // (3) Error c2864: 'mytest: maxnumber3': only static const integral data members can be initialized within a class
- // Static int maxnumber3 = 5;
- // (4) OK
- Static const int maxnumber4 = 5;
- Static const char cconst4 = 'B ';
- // (5) Error c2864: 'mytest: dconst4': only static const integral data members can be initialized within a class
- // Static const double dconst4 = 200.00;
- Public:
- // (6) Error c2758: 'mytest: maxnumber2': Must be initialized in constructor base/member initializer list
- Mytest ()
- {
- Cout <"mytest constructor! "<Endl;
- Cout <"maxnumber4 =" <maxnumber4 <Endl;
- Cout <"cconst4 =" <cconst4 <Endl;
- }
- };
- Int main ()
- {
- Mytest OBJ;
- Return 0;
- }
(1), (2), (3) in the code comment indicates the step number.
From (1), (2), (3), we can see that only static const Integral Data member (static integer constant data member) can be initialized in the class. It can also be proved from (4) and (5. The char type is equivalent to an integer.
The running result is as follows.
Mytest constructor!
Maxnumber = 5
Cconst1 =
Cconst2 = B
Dconst1. = 100
Another example is.
[C-sharp]
View plaincopy
- /**
- * <Valid tive C ++>, page 14
- * Const data of class
- * Platform: Visual Studio 2005, Win32
- * Filename: item2.2.cpp
- */
- # Include <iostream>
- Using namespace STD;
- Class mytest
- {
- Int maxnumber1;
- Const int maxnumber2;
- Static int maxnumber3;
- Static const int maxnumber4 = 5;
- Static const char cconst4 = 'B ';
- Static const int maxnumber5;
- Public:
- // (1) Error c2758: 'mytest: maxnumber2': Must be initialized in constructor base/member initializer list
- // (4) Error c2438: 'maxnumber3': Cannot initialize static class data via Constructor
- // (7) Error c2438: 'maxnumber5': Cannot initialize static class data via Constructor
- Mytest (): maxnumber1 (5), maxnumber2 (5) //, maxnumber5 (5) //, maxnumber3 (5)
- {
- // (2) Error c2166: L-value specifies const object
- // Maxnumber2 = 5;
- // (3) Error lnk2001: unresolved external symbol "Private: static int mytest: maxnumber3 "(? Maxnumber3 @ mytest @ 0HA)
- // Maxnumber3 = 5;
- // (6) Error c3892: 'maxnumber5': you cannot assign to a variable that is const
- // Maxnumber5 = 5;
- Cout <"mytest constructor! "<Endl;
- Cout <"maxnumber1 =" <maxnumber1 <Endl;
- Cout <"maxnumber2 =" <maxnumber2 <Endl;
- Cout <"maxnumber3 =" <maxnumber3 <Endl;
- Cout <"maxnumber4 =" <maxnumber4 <Endl;
- Cout <"maxnumber5 =" <maxnumber5 <Endl;
- Cout <"cconst4 =" <cconst4 <Endl;
- }
- };
- // (5) OK
- Int mytest: maxnumber3 = 5;
- // (8) OK
- Const int mytest: maxnumber5 = 5;
- // (9) Error c2761: 'int mytest: maxnumber1': member function redeclaration not allowed
- // Int mytest: maxnumber1 = 5;
- Int main ()
- {
- Mytest OBJ;
- Return 0;
- }
The running result is as follows.
Mytest constructor!
Maxnumber1 = 5
Maxnumber2 = 5
Maxnumber3 = 5
Maxnumber4 = 5
Maxnumber5 = 5
Cconst4 = B
(1), (2), (3) in the code comment indicates the step number.
From (1), (2) We can see that non-static constant data members must be initialized in the constructor's initialization list. If they are initialized in the constructor, the error c2166 may occur, that is, the constant object is read-only (read only) and cannot be assigned a value.
From (3), (4), (5), we can see that the static extraordinary data members can only be initialized outside the class (implementation file of the class.
We can see from (6), (7), and (8) that static constant data members can also be initialized outside the class (implementation file of the class.
Conclusion:
- Static constant data members can be initialized within the class (that is, they can be declared at the same time), or they can be initialized outside the class, that is, in the class implementation file, and cannot be initialized in the constructor, it cannot be initialized in the initialization list of the constructor;
- Static extraordinary data members can only be initialized in the class implementation file outside the class. They cannot be initialized in the constructor or in the constructor initialization list;
- Non-static constant data members cannot be initialized in the class or in the constructor, but must be initialized only in the constructor initialization list;
- Non-static non-constant data members cannot be initialized in the class. They can be initialized in the constructor or in the constructor initialization list;
Summary:
Type Initialization Method |
Class (Declaration) |
Out-of-class (class implementation file) |
Constructor |
List of constructor Initialization |
Non-static extraordinary data member |
N |
N |
Y |
Y |
Non-static constant data member |
N |
N |
N |
Y (must) |
Static extraordinary data member |
N |
Y (must) |
N |
N |
Static constant data member |
Y |
Y |
N |
N |
4. Exclusive constants of class of Enum type
All data members of the above 4 types have their own initialization methods. The only column is that a class constant is required during the class compilation, except for static constant data members, you can also use data of the enum type, that is, use the so-called "The Enum hack" compensation method. The theoretical basis is "an enumerated type) the value of can be used as an integer ". For example,
Class mytest
{
PRIVATE:
Enum {maxnumber = 5}; // "The Enum hack" makes maxnumber a mark name of 5
Int score [maxnumber];
};
The behavior of Enum hack is more like # define than Const. For example, you can get a const address, not an Enum address, or a # Define address;
5. Use inline function instead of Macro function
(Template) benefits of the inline function:
- Obtain the efficiency of macros (macros do not have additional overhead for function calls)
- Type Safety)
Remember
For constants, it is best to replace # defines with a const object or enum;
Replace # defines with the inline function for macro (macros) Like a function.
Note: This program can also be run on Linux.
Blog (http://blog.csdn.net/livelylittlefish
) Post the notes prepared by the author (@ Xiaoyu) on the relevant research and study content. You are welcome to correct them!
1. macro definition
# Define aspect_ratio 1.653
The macro definition aspect_ratio may never be seen by the compiler, and may be replaced by the pre-processor before the compiler starts to process the source code. We know that the macro definition will be replaced with a string in the preprocessing phase, and any part of aspect_ratio will be replaced with 1.653. Therefore, aspect_ratio does not enter the symbol table.
Symbol table Review
(1) What is a symbol table? What are the important functions of a symbol table?
A symbolic table is a table used to record various information during compilation.
Role of the symbol table:
- Register the input and output information of the compilation process
- Used for semantic check and intermediate code generation during Semantic Analysis
- As the basis for Address Allocation in the generation phase of the target code
(2) What are the common parts of a symbol table? What are their descriptions?
The table items in the symbol table contain two columns: The name column and the information column;
The name column is also called the main column, and the identifier for storing the name is called a keyword;
The information column contains many sub-columns and flag spaces, which are used to record different attributes of the corresponding name.
(3) How do I organize a symbol table? What factors does the Organization depend on?
The organization of a symbol table is divided into two types: direct organization and indirect organization.
Items in the direct organization mode are stored in a fixed length order;
In indirect organization, the main column of the symbol table stores an indicator and an integer (start position and length of the identifier) of the identifier, and the string of the identifier is stored in a string array.
The organization of the symbol table depends on the following factors:
- Whether the storage unit and length of each column in the table item are fixed
- Length limit of the identifier in a language
- Which items have common values?
- Operation and usage of symbol tables
(4) How can I view the executable program symbol table on Win32 and Linux platforms?
Dumpbin command
For example,> dumpbin/Symbols filename (where> is a command line prompt)
Objdump command
For example, # objdump-s filename (where # is a command line prompt)
Therefore, when compilation errors occur in 1.653, it is difficult to figure out the problem. In addition, during the debugging stage, it is also difficult to locate (we cannot find the defined macro value during debugging through visual stiduo or GDB on Linux, because the symbol table does not have this symbol ), therefore, the macro definition cannot be seen as WYSIWYG. You must check the code to understand the macro definition.
So how can we solve it? As follows.
2. Use const to define Constants
For example, the macro defined in define can be changed:
Const double aspectratio = 1.653; // an upper-case name is usually used for macros.
From the above, we can see that the constant has a type, which is double. As a language constant, it will certainly be seen by the compiler, and of course it will enter the symbol table. You can also check the value of this constant during debugging.
3. exclusive class Constants
If you limit the scope of a constant to a class, you must make it a member of the class ). To ensure that this constant has at most one entity, you must make it a static member.
For example, the following program can describe the definition method of the class exclusive constant.
[C-sharp]
View plaincopy
- /**
- * <Valid tive C ++>, page 14
- * Const data of class
- * Platform: Visual Studio 2005, Win32
- * Filename: item2.1.cpp
- */
- # Include <iostream>
- Using namespace STD;
- Class mytest
- {
- // (1) Error c2864: 'mytest: maxnumber1': only static const integral data members can be initialized within a class
- // Int maxnumber1 = 5;
- // (2) Error c2864: 'mytest: maxnumber2': only static const integral data members can be initialized within a class
- // Const int maxnumber2 = 5;
- // (3) Error c2864: 'mytest: maxnumber3': only static const integral data members can be initialized within a class
- // Static int maxnumber3 = 5;
- // (4) OK
- Static const int maxnumber4 = 5;
- Static const char cconst4 = 'B ';
- // (5) Error c2864: 'mytest: dconst4': only static const integral data members can be initialized within a class
- // Static const double dconst4 = 200.00;
- Public:
- // (6) Error c2758: 'mytest: maxnumber2': Must be initialized in constructor base/member initializer list
- Mytest ()
- {
- Cout <"mytest constructor! "<Endl;
- Cout <"maxnumber4 =" <maxnumber4 <Endl;
- Cout <"cconst4 =" <cconst4 <Endl;
- }
- };
- Int main ()
- {
- Mytest OBJ;
- Return 0;
- }
(1), (2), (3) in the code comment indicates the step number.
From (1), (2), (3), we can see that only static const Integral Data member (static integer constant data member) can be initialized in the class. It can also be proved from (4) and (5. The char type is equivalent to an integer.
The running result is as follows.
Mytest constructor!
Maxnumber = 5
Cconst1 =
Cconst2 = B
Dconst1. = 100
Another example is.
[C-sharp]
View plaincopy
- /**
- * <Valid tive C ++>, page 14
- * Const data of class
- * Platform: Visual Studio 2005, Win32
- * Filename: item2.2.cpp
- */
- # Include <iostream>
- Using namespace STD;
- Class mytest
- {
- Int maxnumber1;
- Const int maxnumber2;
- Static int maxnumber3;
- Static const int maxnumber4 = 5;
- Static const char cconst4 = 'B ';
- Static const int maxnumber5;
- Public:
- // (1) Error c2758: 'mytest: maxnumber2': Must be initialized in constructor base/member initializer list
- // (4) Error c2438: 'maxnumber3': Cannot initialize static class data via Constructor
- // (7) Error c2438: 'maxnumber5': Cannot initialize static class data via Constructor
- Mytest (): maxnumber1 (5), maxnumber2 (5) //, maxnumber5 (5) //, maxnumber3 (5)
- {
- // (2) Error c2166: L-value specifies const object
- // Maxnumber2 = 5;
- // (3) Error lnk2001: unresolved external symbol "Private: static int mytest: maxnumber3 "(? Maxnumber3 @ mytest @ 0HA)
- // Maxnumber3 = 5;
- // (6) Error c3892: 'maxnumber5': you cannot assign to a variable that is const
- // Maxnumber5 = 5;
- Cout <"mytest constructor! "<Endl;
- Cout <"maxnumber1 =" <maxnumber1 <Endl;
- Cout <"maxnumber2 =" <maxnumber2 <Endl;
- Cout <"maxnumber3 =" <maxnumber3 <Endl;
- Cout <"maxnumber4 =" <maxnumber4 <Endl;
- Cout <"maxnumber5 =" <maxnumber5 <Endl;
- Cout <"cconst4 =" <cconst4 <Endl;
- }
- };
- // (5) OK
- Int mytest: maxnumber3 = 5;
- // (8) OK
- Const int mytest: maxnumber5 = 5;
- // (9) Error c2761: 'int mytest: maxnumber1': member function redeclaration not allowed
- // Int mytest: maxnumber1 = 5;
- Int main ()
- {
- Mytest OBJ;
- Return 0;
- }
The running result is as follows.
Mytest constructor!
Maxnumber1 = 5
Maxnumber2 = 5
Maxnumber3 = 5
Maxnumber4 = 5
Maxnumber5 = 5
Cconst4 = B
(1), (2), (3) in the code comment indicates the step number.
From (1), (2) We can see that non-static constant data members must be initialized in the constructor's initialization list. If they are initialized in the constructor, the error c2166 may occur, that is, the constant object is read-only (read only) and cannot be assigned a value.
From (3), (4), (5), we can see that the static extraordinary data members can only be initialized outside the class (implementation file of the class.
We can see from (6), (7), and (8) that static constant data members can also be initialized outside the class (implementation file of the class.
Conclusion:
- Static constant data members can be initialized within the class (that is, they can be declared at the same time), or they can be initialized outside the class, that is, in the class implementation file, and cannot be initialized in the constructor, it cannot be initialized in the initialization list of the constructor;
- Static extraordinary data members can only be initialized in the class implementation file outside the class. They cannot be initialized in the constructor or in the constructor initialization list;
- Non-static constant data members cannot be initialized in the class or in the constructor, but must be initialized only in the constructor initialization list;
- Non-static non-constant data members cannot be initialized in the class. They can be initialized in the constructor or in the constructor initialization list;
Summary:
Type Initialization Method |
Class (Declaration) |
Out-of-class (class implementation file) |
Constructor |
List of constructor Initialization |
Non-static extraordinary data member |
N |
N |
Y |
Y |
Non-static constant data member |
N |
N |
N |
Y (must) |
Static extraordinary data member |
N |
Y (must) |
N |
N |
Static constant data member |
Y |
Y |
N |
N |
4. Exclusive constants of class of Enum type
All data members of the above 4 types have their own initialization methods. The only column is that a class constant is required during the class compilation, except for static constant data members, you can also use data of the enum type, that is, use the so-called "The Enum hack" compensation method. The theoretical basis is "an enumerated type) the value of can be used as an integer ". For example,
Class mytest
{
PRIVATE:
Enum {maxnumber = 5}; // "The Enum hack" makes maxnumber a mark name of 5
Int score [maxnumber];
};
The behavior of Enum hack is more like # define than Const. For example, you can get a const address, not an Enum address, or a # Define address;
5. Use inline function instead of Macro function
(Template) benefits of the inline function:
- Obtain the efficiency of macros (macros do not have additional overhead for function calls)
- Type Safety)
Remember
For constants, it is best to replace # defines with a const object or enum;
Replace # defines with the inline function for macro (macros) Like a function.
Note: This program can also be run on Linux.