Thread: unfamiliar syntax

  1. #1
    Registered User
    Join Date
    Aug 2007
    Posts
    42

    unfamiliar syntax

    Code:
    private:
        struct node
        {
            static const int values_size_lb =
                (NODE_SIZE - 2*sizeof(node*) - sizeof(int))/sizeof(T);
            static const int values_size =
                values_size_lb == 0 ? 1 : values_size_lb;
        
        
       node()
              : next(NULL), prev(NULL), count(0)
            {}
    
        
            node* next;
            node* prev;
            int   count;
            T values[values_size];
        };
    I'm unfamiliar with this syntax: "node() : next (NULL), prev(NULL), count(0) {} " .
    What does this do ?

    Thanks,
    Ken

  2. #2
    Sweet
    Join Date
    Aug 2002
    Location
    Tucson, Arizona
    Posts
    1,820
    Its an initializer list.

    It basically calls the constructor of those items and sets them to those values
    Woop?

  3. #3
    Registered User
    Join Date
    Mar 2009
    Posts
    14
    That is a constructor for struct node. The braces
    Code:
    {}
    indicate that it is in inline form. The colon and the statements before the braces are the initializer list. For more info on initializer lists, go to Initialization Lists in C++ - Cprogramming.com. For more info on inline functions, go to Cprogramming.com Tutorial: Function Tricks.

  4. #4
    Registered User
    Join Date
    Aug 2007
    Posts
    42
    As I'm new to C++ the initializer list for a structure is a new concept.

    However after reading the references and looking at this again I disagree that {} indicates an INLINE function. If I'm reading this all correctly isn't it just an empty constructor with an initialization list?

    Wouldn't this be the same as
    Code:
       node() { 
          next = NULL;
          prev = NULL;
          count= 0;
       }
    Is one form more efficient than the other? Do they have the same meanings?

    Thanks

  5. #5
    Sweet
    Join Date
    Aug 2002
    Location
    Tucson, Arizona
    Posts
    1,820
    The initialization list can be more efficient.

    It is also useful if you need to call a member whose constructor has a parameter.
    Code:
    class SomeClass
    {
    public:
        SomeClass(int value) : mValue(value) { }
    private
        int mValue;
    };
    
    class AnotherClass
    {
    public:
        AnotheClass(int value) : mContainedClass(value) { }
    private:
        SomeClass mContainedClass;
    };
    Last edited by prog-bman; 04-01-2009 at 04:14 PM.
    Woop?

  6. #6
    Registered User
    Join Date
    Mar 2009
    Posts
    14
    Since the constructor calls in the initializer list are made before the statements in the body of the constructor are executed, the list makes it possible have a fully created and initialized object when the constructor is run. The initializer list is the place to initialize any references and consts that you have in your class. As previously said, it's also the place to make calls to the constructors of classes that your class inherits from or contains.

    Any function defined within a class body is automatically inline.

  7. #7
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    Quote Originally Posted by DirkMaas View Post
    Any function defined within a class body is automatically inline.
    But bear in mind that it's entirely up to the compiler which functions are inlined and which are not. The compiler uses many different indicators to decide whether to inline a function or not, and one indicator is whether the user declared the function as an inline function (which is implied if the function is declared within the class definition). Other factors are:
    • How large is the function, how many times is it called.
      Large functions that are called only once can be inlined, but not large functions that are called several times, whilst small functions can be allowed to inline even if they are called many times.
    • The structure of the function itself.
      Functions that are recursive or contain try/catch are usually not possible to inline. Functions that have their address taken are usually not inlined.
      Functions that are virtual can not be inlined except where the compiler knows some other way exactly which variant of the function is supposed to be called.
    • Optimisation levels and other compiler settings.
      There is almost always a flag to say "do not inline functions" or "inline only functions that are explicitly marked inline".
      Many compilers also have settings to adjust the inlining - e.g. how many bytes copies of a function is allowed to take up, or number of instructions an inlined function is allowed to use up, number of times it can be called before it gets out-of-lined.

    There are other factors that are even more arbitrary (e.g. the compiler simply can't "figure out" how to inline a particular function because it can't generate correct code), but the above are the common factors that occur in almost all compilers.

    Note also that excessive inlining can lead to slower execution speed. It was found when testing large-scale system benchmarks that "keep the code as small as possible and don't inline' gave better performance on the Linux kernel than to inline functions all over the place. The main reason is that the inlined copies of functions are no longer shared between different paths, so if we have, say, a helper function that is called from open, read, write and close [say a function that checks that a handle is valid], and we call open, read, [modify some of the file content], write and close in sequence, each copy of the helper function needs to be read into the cache from the main memory. If we do not inline this function, it gets loaded when we call open, and then it's already there when we call read. Not only that, but the four copies of the common function throws out some other bits of code from the cache, which means that when that code needs to be executed, it is read from the slower main memory again - slowing down the system again.

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  8. #8
    Registered User
    Join Date
    Feb 2003
    Posts
    596
    Quote Originally Posted by matsp View Post
    But bear in mind that it's entirely up to the compiler which functions are inlined and which are not. The compiler uses many different indicators to decide whether to inline a function or not, and one indicator is whether the user declared the function as an inline function (which is implied if the function is declared within the class definition) ...
    --
    Mats
    I think I understand the distinction between declare and define wrt primitive types, but I'm not so sure when it comes to classes and functions. Can you help clarify that for me?

    Also, bearing in mind that the original question related specifically to the syntax of a constructor, what's the takeaway message here? Does it actually matter whether member variables are initialized in an initializer list or in the constructor body?

  9. #9
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,413
    Quote Originally Posted by R.Stiltskin
    I think I understand the distinction between declare and define wrt primitive types, but I'm not so sure when it comes to classes and functions. Can you help clarify that for me?
    Perhaps examples will help. This is a function declaration that is not also a function definition:
    Code:
    void foo();
    Whereas this is a function definition:
    Code:
    void foo() {}
    This is a class declaration that is not also a class definition:
    Code:
    class X;
    Whereas this is a class definition:
    Code:
    class X
    {
    public:
        void foo();
    private:
        int bar;
    };
    Quote Originally Posted by R.Stiltskin
    Also, bearing in mind that the original question related specifically to the syntax of a constructor, what's the takeaway message here? Does it actually matter whether member variables are initialized in an initializer list or in the constructor body?
    Yes, it may matter:
    • Assignment in the constructor body may mean more work since a member variable would be default constructed and then assigned to.
    • It may not be possible to assign to the member variable in the constructor body, e.g., for const and reference member variables, or those of types without default constructors.
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  10. #10
    Registered User
    Join Date
    Feb 2003
    Posts
    596
    That's very interesting. I don't think I've ever come across reference member variables before. Thanks, laserlight.

  11. #11
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,413
    Quote Originally Posted by R.Stiltskin
    I don't think I've ever come across reference member variables before.
    Eh, I just realised an inaccuracy: in the case of non-const reference member variables, it would certainly be possible to assign to them in the constructor body, but that would obviously not be the same as initialising the reference.
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  12. #12
    C++まいる!Cをこわせ!
    Join Date
    Oct 2007
    Location
    Inside my computer
    Posts
    24,654
    Also yielding a compile error since references must be initialized. So they must be provided in the initializer list, whether or not they're assigned or read from in the body.
    Quote Originally Posted by Adak View Post
    io.h certainly IS included in some modern compilers. It is no longer part of the standard for C, but it is nevertheless, included in the very latest Pelles C versions.
    Quote Originally Posted by Salem View Post
    You mean it's included as a crutch to help ancient programmers limp along without them having to relearn too much.

    Outside of your DOS world, your header file is meaningless.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. more then 100errors in header
    By hallo007 in forum Windows Programming
    Replies: 20
    Last Post: 05-13-2007, 08:26 AM
  2. We Got _DEBUG Errors
    By Tonto in forum Windows Programming
    Replies: 5
    Last Post: 12-22-2006, 05:45 PM
  3. Using VC Toolkit 2003
    By Noobwaker in forum Windows Programming
    Replies: 8
    Last Post: 03-13-2006, 07:33 AM
  4. Connecting to a mysql server and querying problem
    By Diod in forum C++ Programming
    Replies: 8
    Last Post: 02-13-2006, 10:33 AM
  5. Dikumud
    By maxorator in forum C++ Programming
    Replies: 1
    Last Post: 10-01-2005, 06:39 AM