error: invalid use of nonstatic data member

Collapse
This topic is closed.
X
X
 
  • Time
  • Show
Clear All
new posts
  • The|Godfather

    error: invalid use of nonstatic data member

    Hi everybody,

    I read Scotte Meyer's "Effective C++" book twice and I know that
    he mentioned something specific about constructors and destructors that
    was related to the
    following error/warning: "error: invalid use of nonstatic data member "

    However, he did NOT mention this error in the book explicitly.It
    happens always in the constructor when you try to initialize some data
    members in the constructor and try to accsess other data members. Of
    course,one can always move the initialization away from the
    constructor , but that is not the goal:

    UP_SQLPrepQuery ::StatementInte rnals::Statemen tInternals(bool & status)
    : nParams(0),
    capacity(0),
    tuple_num(0),
    alter_session_s tatement(false) ,
    select_statemen t(false)
    {sprintf(stmt_i nternals->stmt_name,"%ll x",embeddedConn ection.GetConne ctionInternals( __LINE__,
    __FILE__)->prep_cnt++);
    }

    The error is in the line:

    sprintf(stmt_in ternals->stmt_name,"%ll x",embeddedConn ection.GetConne ctionInternals( __LINE__,
    __FILE__)->prep_cnt++);
    }

    Here , I try to get some value through a function. Scott said something
    about NOT doing that in constructors, but I am not sure and I could
    NOT find anything. The problem is with the Function
    embeddedConnect ion.GetConnecti onInternals(), which should return a
    pointer to an object.

    I am using gcc (GCC) 3.4.2 under: x86_64 GNU/Linux
    Please, advise.

    Cheers,
    Dragomir Stanchev

  • Miles Bader

    #2
    Re: error: invalid use of nonstatic data member

    It would help if you would actually give the related declarations...

    -miles

    --
    Is it true that nothing can be known? If so how do we know this? -Woody Allen

    Comment

    • Victor Bazarov

      #3
      Re: error: invalid use of nonstatic data member

      Disclaimer: I don't read 'gnu.gcc.help' newsgroup, so I removed it
      from my reply. BTW, did you know there is 'gnu.g++.help'?

      The|Godfather wrote:
      I read Scotte Meyer's "Effective C++" book twice and I know that
      he mentioned something specific about constructors and destructors
      that was related to the
      following error/warning: "error: invalid use of nonstatic data member
      "
      >
      However, he did NOT mention this error in the book explicitly.It
      happens always in the constructor when you try to initialize some data
      members in the constructor and try to accsess other data members. Of
      course,one can always move the initialization away from the
      constructor , but that is not the goal:
      >
      UP_SQLPrepQuery ::StatementInte rnals::Statemen tInternals(bool & status)
      >nParams(0),
      capacity(0),
      tuple_num(0),
      alter_session_s tatement(false) ,
      select_statemen t(false)
      {sprintf(stmt_i nternals->stmt_name,"%ll x",embeddedConn ection.GetConne ctionInternals( __LINE__,
      __FILE__)->prep_cnt++);
      }
      So, _assuming_ it's written correctly, I can divine that 'nParams',
      'capacity', 'tuple_num', 'alter_session_ statement', 'select_stateme nt',
      are all non-static members of 'StatementInter nals' class, which resides
      in 'UP_SQLPrepQuer y' namespace.

      Nothing else can be said about the class or the body of the c-tor.
      >
      The error is in the line:
      >
      sprintf(stmt_in ternals->stmt_name,"%ll x",embeddedConn ection.GetConne ctionInternals( __LINE__,
      __FILE__)->prep_cnt++);
      }
      So? What's "stmt_internals "? What's "embeddedConnec tion"?
      Here , I try to get some value through a function. Scott said
      something about NOT doing that in constructors, but I am not sure and
      I could NOT find anything. The problem is with the Function
      embeddedConnect ion.GetConnecti onInternals(), which should return a
      pointer to an object.
      There is no function 'embeddedConnec tion.GetConnect ionInternals()' .
      The syntax suggests that 'GetConnectionI nternals' is a _member_ of
      the class, of which 'embeddedConnec tion' _object_ is an instance.
      If 'embeddedConnec tion' *is* a type, you need '::' instead of '.'
      here:

      ... embeddedConnect ion::GetConnect ionInternals() ...

      but it's just a guess, given absence of any information about it.
      I am using gcc (GCC) 3.4.2 under: x86_64 GNU/Linux
      Please, advise.
      You should probably use G++...

      V
      --
      Please remove capital 'A's when replying by e-mail
      I do not respond to top-posted replies, please don't ask


      Comment

      • mlimber

        #4
        Re: error: invalid use of nonstatic data member

        The|Godfather wrote:
        I read Scotte Meyer's "Effective C++" book twice and I know that
        he mentioned something specific about constructors and destructors that
        was related to the
        following error/warning: "error: invalid use of nonstatic data member "
        >
        However, he did NOT mention this error in the book explicitly.
        Huh? Scotte (or Scott, as most people call him) mentioned something
        specific related to that error but he did not mention that error
        explicitly, so how do you know he was referring to that error
        specifically?
        It
        happens always in the constructor when you try to initialize some data
        members in the constructor and try to accsess other data members.
        You can't *initialize* static data members in the ctor
        (http://www.parashift.com/c++-faq-lit...tml#faq-10.10), but you
        can *use* them there. Regarding the "other data members," see this FAQ:


        Of
        course,one can always move the initialization away from the
        constructor ,
        Right, to enforce proper initialization, especially in the case that
        the constructor needs to call a virtual function. This is generally
        superior to forcing the user to call an Init() function, which can
        easily be forgotten, leaving the object uninitialized. This example is
        drawn from Sutter and Alexandrescu's _C++ Coding Standards_ (Item 49):

        class B // Hierarchy root
        {
        protected:
        B() { /*...*/ }

        // Called right after construction
        virtual void PostInitialize( ) { /*...*/ }

        public:

        // Interface for creating objects
        template<class T>
        static std::auto_ptr<T Create()
        {
        std::auto_ptr<T p( new T );
        p->PostInitialize ();
        return p;
        }
        };

        // A derived class
        class D : public B { /*...*/ };

        // Creating an initialized D object
        std::auto_ptr<D p = D::Create<D>();
        but that is not the goal:
        >
        UP_SQLPrepQuery ::StatementInte rnals::Statemen tInternals(bool & status)
        : nParams(0),
        capacity(0),
        tuple_num(0),
        alter_session_s tatement(false) ,
        select_statemen t(false)
        {sprintf(stmt_i nternals->stmt_name,"%ll x",embeddedConn ection.GetConne ctionInternals( __LINE__,
        __FILE__)->prep_cnt++);
        }
        >
        The error is in the line:
        >
        sprintf(stmt_in ternals->stmt_name,"%ll x",embeddedConn ection.GetConne ctionInternals( __LINE__,
        __FILE__)->prep_cnt++);
        }
        >
        Here , I try to get some value through a function.
        You have not followed the FAQ on how to post code that doesn't work
        (http://www.parashift.com/c++-faq-lit....html#faq-5.8). Not
        only is it helpful, in this case it is necessary because you don't
        provide enough information to divine what you are trying to do. Please
        post a *minimal* but *complete* program (i.e., one that we can cut and
        paste directly to our editors unchanged) that demonstrates your
        problem.

        Cheers! --M

        Comment

        • The|Godfather

          #5
          Re: error: invalid use of nonstatic data member

          Ok,
          I apologize for not posting working code , just did NOT have any time
          yesterday.
          Here is full report now:

          gcc --version: gcc (GCC) 3.4.2
          uname -rmo: 2.6.5-7.201-smp x86_64 GNU/Linux
          compile command:
          gcc -c -I/users/dstanche/problem test1.cpp
          Error Message:
          "test1.cpp: In constructor
          `test1::Stateme ntInternals::St atementInternal s()':
          test1.cpp:8: error: invalid use of nonstatic data member
          'test1::stmt_in ternals' "

          CODE :

          example.h:
          ------------
          class example {

          public:
          example() {;}
          inline int giveIt(){return 2;}
          };

          --------
          test1.h
          -------
          #include <example.h>

          class test1 :example{
          class StatementIntern als;
          public:

          test1();
          private:
          StatementIntern als * stmt_internals;


          };

          ---------
          test1I.h
          ---------
          class test1::Statemen tInternals
          {
          public:
          StatementIntern als();
          unsigned long *length;
          bool select_statemen t;
          int stmt_counter;

          };
          --------
          test1.cpp
          -------
          #include <test1.h>
          #include <test1I.h>

          test1::Statemen tInternals::Sta tementInternals ()
          : length(0), select_statemen t(0)

          {
          stmt_counter=st mt_internals->giveIt(); // THE PROBLEM LINE IS THIS
          ONE
          }

          test1::test1(): stmt_internals( new StatementIntern als){}


          int main() {

          return 0;
          }
          -------

          As you can see the code does not do anything special. I have NO idea
          why the problem occurs. Please advice.

          Dragomir Stanchev

          mlimber wrote:
          The|Godfather wrote:
          I read Scotte Meyer's "Effective C++" book twice and I know that
          he mentioned something specific about constructors and destructors that
          was related to the
          following error/warning: "error: invalid use of nonstatic data member "

          However, he did NOT mention this error in the book explicitly.
          >
          Huh? Scotte (or Scott, as most people call him) mentioned something
          specific related to that error but he did not mention that error
          explicitly, so how do you know he was referring to that error
          specifically?
          >
          It
          happens always in the constructor when you try to initialize some data
          members in the constructor and try to accsess other data members.
          >
          You can't *initialize* static data members in the ctor
          (http://www.parashift.com/c++-faq-lit...tml#faq-10.10), but you
          can *use* them there. Regarding the "other data members," see this FAQ:
          >

          >
          Of
          course,one can always move the initialization away from the
          constructor ,
          >
          Right, to enforce proper initialization, especially in the case that
          the constructor needs to call a virtual function. This is generally
          superior to forcing the user to call an Init() function, which can
          easily be forgotten, leaving the object uninitialized. This example is
          drawn from Sutter and Alexandrescu's _C++ Coding Standards_ (Item 49):
          >
          class B // Hierarchy root
          {
          protected:
          B() { /*...*/ }
          >
          // Called right after construction
          virtual void PostInitialize( ) { /*...*/ }
          >
          public:
          >
          // Interface for creating objects
          template<class T>
          static std::auto_ptr<T Create()
          {
          std::auto_ptr<T p( new T );
          p->PostInitialize ();
          return p;
          }
          };
          >
          // A derived class
          class D : public B { /*...*/ };
          >
          // Creating an initialized D object
          std::auto_ptr<D p = D::Create<D>();
          >
          but that is not the goal:

          UP_SQLPrepQuery ::StatementInte rnals::Statemen tInternals(bool & status)
          : nParams(0),
          capacity(0),
          tuple_num(0),
          alter_session_s tatement(false) ,
          select_statemen t(false)
          {sprintf(stmt_i nternals->stmt_name,"%ll x",embeddedConn ection.GetConne ctionInternals( __LINE__,
          __FILE__)->prep_cnt++);
          }

          The error is in the line:

          sprintf(stmt_in ternals->stmt_name,"%ll x",embeddedConn ection.GetConne ctionInternals( __LINE__,
          __FILE__)->prep_cnt++);
          }

          Here , I try to get some value through a function.
          >
          You have not followed the FAQ on how to post code that doesn't work
          (http://www.parashift.com/c++-faq-lit....html#faq-5.8). Not
          only is it helpful, in this case it is necessary because you don't
          provide enough information to divine what you are trying to do. Please
          post a *minimal* but *complete* program (i.e., one that we can cut and
          paste directly to our editors unchanged) that demonstrates your
          problem.
          >
          Cheers! --M

          Comment

          • Jan van Mastbergen

            #6
            Re: error: invalid use of nonstatic data member

            The|Godfather wrote:
            Ok,
            I apologize for not posting working code , just did NOT have any time
            yesterday.
            Here is full report now:
            >
            gcc --version: gcc (GCC) 3.4.2
            uname -rmo: 2.6.5-7.201-smp x86_64 GNU/Linux
            compile command:
            gcc -c -I/users/dstanche/problem test1.cpp
            Error Message:
            "test1.cpp: In constructor
            `test1::Stateme ntInternals::St atementInternal s()':
            test1.cpp:8: error: invalid use of nonstatic data member
            'test1::stmt_in ternals' "
            [...]
            If I compile this sample in MS-VC++ 8 the error message is simply that
            stmt_internals is an undeclared identifier, which makes a bit more sense
            to me than g++'s message. The 'forward' declaration in the definition of
            test1 merely *declares* StatementIntern als, it does not define it and so
            it is not a nested class in the classical sense.

            class test1 : example {
            class StatementIntern als; // declares class name
            public:
            test1();
            private:
            StatementIntern als * stmt_internals; // defines pointer
            };

            The definition of StatementIntern als is at the same lexical level as
            test1 and at that point the private attribute of test1 is unknown.
            Besides, C and C++ do not really support access to implicitly referenced
            outer variables from lexically nested functions. The question is not
            just whether to allow it (using public/private modifiers) but how to
            implement it when you do. A more complicated stack layout is needed to
            get at the proper variable instance. This is a feature that you will
            find in Algol-60, Pascal and the like but not C(++). Nobody seems to
            care enough to request it, though. I don't.

            Regards, Jan

            Comment

            • Victor Bazarov

              #7
              Re: error: invalid use of nonstatic data member

              Jan van Mastbergen wrote:
              The|Godfather wrote:
              >Ok,
              >I apologize for not posting working code , just did NOT have any time
              >yesterday.
              >Here is full report now:
              >>
              >gcc --version: gcc (GCC) 3.4.2
              >uname -rmo: 2.6.5-7.201-smp x86_64 GNU/Linux
              >compile command:
              >gcc -c -I/users/dstanche/problem test1.cpp
              >Error Message:
              >"test1.cpp: In constructor
              >`test1::Statem entInternals::S tatementInterna ls()':
              >test1.cpp:8: error: invalid use of nonstatic data member
              >'test1::stmt_i nternals' "
              >[...]
              If I compile this sample in MS-VC++ 8 the error message is simply that
              stmt_internals is an undeclared identifier, which makes a bit more
              sense to me than g++'s message. The 'forward' declaration in the
              definition of test1 merely *declares* StatementIntern als, it does not
              define it and so it is not a nested class in the classical sense.
              >
              class test1 : example {
              class StatementIntern als; // declares class name
              public:
              test1();
              private:
              StatementIntern als * stmt_internals; // defines pointer
              };
              I think it's all much simpler. You cannot use 'stmt_internals ' data
              member in the constructor of StatementIntern als [nested] class simply
              because 'stmt_internals ' is not a member of 'StatementInter nals' and
              needs an instance of 'test1' to be used.

              The confusion is common among Java programmers switching to C++. In
              Java an instance of an outer class _automatically_ contains an instance
              of a nested class. In C++ it does not.

              struct Outer {
              int data;
              struct Inner { // type defined inside another type
              Inner() { // c-tor
              int i = data; // what's "data"?
              }
              };
              };

              'Inner' does not have a member named "data". 'Outer' does. 'Outer'
              does not have a data member of type 'Inner'. Constructing an 'Outer'
              object does not automatically construct an 'Inner' object, nor does
              any instance of 'Inner' have any pre-defined "path" to 'data'.
              [..]
              V
              --
              Please remove capital 'A's when replying by e-mail
              I do not respond to top-posted replies, please don't ask


              Comment

              • Miles Bader

                #8
                Re: error: invalid use of nonstatic data member

                "The|Godfat her" <dragomir.stanc hev@gmail.comwr ites:
                class test1::Statemen tInternals
                {
                public:
                StatementIntern als();
                unsigned long *length;
                bool select_statemen t;
                int stmt_counter;
                };
                ....
                test1::Statemen tInternals::Sta tementInternals ()
                : length(0), select_statemen t(0)
                {
                stmt_counter=st mt_internals->giveIt(); // THE PROBLEM LINE IS THIS
                ONE
                ....
                As you can see the code does not do anything special. I have NO idea
                why the problem occurs. Please advice.
                Because the StatementIntern als class has no data member called
                "stmt_internals ", so there's no way the StatementIntern als constructor
                can use such a member.

                StatementIntern als has exactly the data members you declared above, no
                others.

                -Miles

                --
                Occam's razor split hairs so well, I bought the whole argument!

                Comment

                Working...