Linking error

Discussion in 'C++' started by Kevin Grigorenko, Sep 12, 2003.

  1. Okay, everything seems simple enough but I get the following Link error:

    TeXt.obj : error LNK2001: unresolved external symbol "private: static char *
    TextDB::TextDB::myVersion" (?myVersion@TextDB@1@0PADA)

    My environment is Visual Studio .NET, I think it's C++ 7 from the microsoft
    visual studio versioning point of view.

    Here is TeXt.h:

    // Annoying MSVC++ warning:
    #pragma warning( disable : 4290 )

    // TeXt - Standalone Pure Text Database Management System

    #ifndef TEXT_DB
    #define TEXT_DB

    #define TEXT_MAJOR_REVISION 1
    #define TEXT_MINOR_REVISION 0
    #define TEXT_BUILD 0

    /*
    Revision History:
    -----------------
    > 1.0.1

    ---------
    - Created. I've run into too many situations
    where something like this would have been
    useful.
    */

    //#include <bool.h>
    #include <string>
    #include <stdexcept>
    /*

    // If no bool.h, uncomment:
    typedef short int bool;
    #ifndef false
    #define false 0
    #endif
    #ifndef true
    #define true 1
    #endif
    */

    namespace TextDB
    {
    class TextDB
    {
    public:
    // Constructors/Destructor:
    TextDB(const std::string filename) throw(std::invalid_argument);
    ~TextDB();
    TextDB(const TextDB &copy) throw(std::invalid_argument);

    static const char *getVersion();
    private:
    // Private because it is illogical to instantiate a
    // TextDB object without a filename
    TextDB();

    void initialize(std::string in_filename)
    throw(std::invalid_argument);

    std::string filename;
    static char myVersion[20];
    }; // class TextDB
    } // namespace TextDB

    #endif // #ifndef TEXT_DB

    AND then here is TeXt.cpp:

    //#include <bool>
    #include <string>
    #include <fstream>
    #include "TeXt.h"
    namespace TextDB
    {
    TextDB::TextDB(const std::string filename)
    {
    initialize(filename);
    }

    TextDB::~TextDB()
    {
    }

    TextDB::TextDB(const TextDB &copy)
    {
    initialize(copy.filename);
    }

    const char *TextDB::getVersion()
    {
    return myVersion;
    }

    void TextDB::initialize(std::string in_filename)
    {
    sprintf(myVersion, "%d.%d.%d", TEXT_MAJOR_REVISION,
    TEXT_MINOR_REVISION, TEXT_BUILD);
    std::ifstream infile(filename.c_str(), std::ios_base::in);
    if(!infile.is_open())
    {
    throw std::invalid_argument("Could not open database file <" +
    filename + ">");
    }
    this->filename = in_filename;
    infile.close();
    } // initialize()
    } // namespace TextDB

    I'm sure the answer is simple, but I can't see it obviously.

    Thank you very much!

    Kevin Grigorenko
     
    Kevin Grigorenko, Sep 12, 2003
    #1
    1. Advertising

  2. Kevin Grigorenko

    Ron Natalie Guest

    "Kevin Grigorenko" <> wrote in message news:bjt6i4$1hk0$...

    > static char myVersion[20];


    This is only a declaration.

    You must also define it. Put

    char TextDB::myVersion[20];

    inside the namespace TextDB in your cpp file.
     
    Ron Natalie, Sep 12, 2003
    #2
    1. Advertising

  3. Kevin Grigorenko

    Mike Wahler Guest

    Kevin Grigorenko <> wrote in message
    news:bjt6i4$1hk0$...
    > Okay, everything seems simple enough but I get the following Link error:
    >
    > TeXt.obj : error LNK2001: unresolved external symbol "private: static char

    *
    > TextDB::TextDB::myVersion" (?myVersion@TextDB@1@0PADA)
    >
    > My environment is Visual Studio .NET, I think it's C++ 7 from the

    microsoft
    > visual studio versioning point of view.
    >
    > Here is TeXt.h:


    > [snip]


    > namespace TextDB
    > {
    > class TextDB
    > {
    > public:
    > // Constructors/Destructor:
    > TextDB(const std::string filename) throw(std::invalid_argument);
    > ~TextDB();
    > TextDB(const TextDB &copy) throw(std::invalid_argument);
    >
    > static const char *getVersion();
    > private:
    > // Private because it is illogical to instantiate a
    > // TextDB object without a filename
    > TextDB();
    >
    > void initialize(std::string in_filename)
    > throw(std::invalid_argument);
    >
    > std::string filename;
    > static char myVersion[20];


    This is only a declaration, it's not a defintion.
    No storage is reserved. Do this in your implementation
    file (inside your namespace 'TextDB':

    char TextDB::myVersion[20];

    I'd recommend replacing that char array with a std::string.

    -Mike
     
    Mike Wahler, Sep 12, 2003
    #3
  4. "Ron Natalie" <> wrote in message
    news:3f621f5b$0$51850$...
    >
    > "Kevin Grigorenko" <> wrote in message

    news:bjt6i4$1hk0$...
    >
    > > static char myVersion[20];

    >
    > This is only a declaration.
    >
    > You must also define it. Put
    >
    > char TextDB::myVersion[20];
    >
    > inside the namespace TextDB in your cpp file.
    >
    >


    Thanks, that did it. So any variables declared static must explicitly be
    defined? Can this be done inline?

    Kevin Grigorenko
     
    Kevin Grigorenko, Sep 12, 2003
    #4
  5. Kevin Grigorenko

    Ron Natalie Guest

    "Kevin Grigorenko" <> wrote in message news:bjt7aq$1ja0$...

    > Thanks, that did it. So any variables declared static must explicitly be
    > defined?


    Yes

    > Can this be done inline?


    No, with the exception of static integral constants. The implementations need
    the definition to figure out which module actually allocates the storage for the
    variable. This all harps back to an age old issue as to whether C (or C++)
    could define the same data in multiple object files and have the linker fold
    them all into the same object. The early C linkers did support this, but the
    powers that were decided to not require this (although any linker that could
    do seperate compilation of Fortran (common blocks) had to have the capability).
     
    Ron Natalie, Sep 12, 2003
    #5
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. RU
    Replies:
    2
    Views:
    7,991
  2. pradeep

    linking error

    pradeep, Sep 6, 2003, in forum: C++
    Replies:
    2
    Views:
    347
    Janusz Szpilewski
    Sep 7, 2003
  3. Jeff Schwab

    Newbie Linking Error

    Jeff Schwab, Dec 29, 2003, in forum: C++
    Replies:
    5
    Views:
    734
  4. Yoon-Soo Lee
    Replies:
    5
    Views:
    4,232
    Chris \( Val \)
    Jan 2, 2004
  5. manish
    Replies:
    1
    Views:
    1,980
    Christopher Benson-Manica
    Apr 2, 2004
Loading...

Share This Page