First Defined here in g++ from class to namespace
===

I have read many questions like this and I am not 100% sure if mine's any different. I have searched quite a lot for the right answer but most of the answers were around macro gaurds. I had a custom string class that I derived from `std::string`, and later on since I was using that project in real world so I did not want to derive std::string just for the sake of extending functionality. So I moved the functions from customString.h into utils_string.h. Here is the definition:


    #ifndef OPS_TOOLKIT_UTILS_STRING_H
    #define OPS_TOOLKIT_UTILS_STRING_H
    #include <string>
    #include <algorithm>
    #include <vector>
    
    namespace utils{
      namespace string{
    
    const std::string kilikeDelimiter = "%";
    
    void tolower(std::string& str){
        //CODE
    }
    
    bool iequals(const std::string& str1,const std::string& str2){
        //CODE
    }
    bool ilike(const std::string& str,const std::string& pattern){
        //CODE
    }
    std::string prependAndAppendILikeDelimiter(const std::string& str) {
        //CODE
    }
    } //namespace string
    } //namespace utils
    
    #endif


and I get complains about `...first defined here` and here is exact output from compiler. Note: no class here

> /tmp/ccCFVTXP.o: In function `utils::string::tolower(std::basic_string<char, std::char_traits<char>, std::allocator<char> >&)':
listings.cpp:(.text+0x0): multiple definition of `utils::string::tolower(std::basic_string<char, std::char_traits<char>, std::allocator<char> >&)'
/tmp/cczDtRdT.o:listing.cpp:(.text+0x0): first defined here
/tmp/ccCFVTXP.o: In function `utils::string::iequals(std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&, std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)':
listings.cpp:(.text+0x55): multiple definition of `utils::string::iequals(std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&, std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)'
/tmp/cczDtRdT.o:listing.cpp:(.text+0x55): first defined here
/tmp/ccCFVTXP.o: In function `utils::string::ilike(std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&, std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)':
listings.cpp:(.text+0x118): multiple definition of `utils::string::ilike(std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&, std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)'
/tmp/cczDtRdT.o:listing.cpp:(.text+0x118): first defined here
/tmp/ccCFVTXP.o: In function `utils::string::prependAndAppendILikeDelimiter(std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)':
listings.cpp:(.text+0x484): multiple definition of `utils::string::prependAndAppendILikeDelimiter(std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)'
/tmp/cczDtRdT.o:listing.cpp:(.text+0x484): first defined here
/tmp/ccifZISK.o: In function `utils::string::tolower(std::basic_string<char, std::char_traits<char>, std::allocator<char> >&)':
match_count.cpp:(.text+0x0): multiple definition of `utils::string::tolower(std::basic_string<char, std::char_traits<char>, std::allocator<char> >&)'
/tmp/cczDtRdT.o:listing.cpp:(.text+0x0): first defined here
/tmp/ccifZISK.o: In function `utils::string::iequals(std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&, std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)':
match_count.cpp:(.text+0x55): multiple definition of `utils::string::iequals(std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&, std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)'
/tmp/cczDtRdT.o:listing.cpp:(.text+0x55): first defined here
/tmp/ccifZISK.o: In function `utils::string::ilike(std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&, std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)':
match_count.cpp:(.text+0x118): multiple definition of `utils::string::ilike(std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&, std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)'
/tmp/cczDtRdT.o:listing.cpp:(.text+0x118): first defined here
/tmp/ccifZISK.o: In function `utils::string::prependAndAppendILikeDelimiter(std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)':
match_count.cpp:(.text+0x484): multiple definition of `utils::string::prependAndAppendILikeDelimiter(std::basic_string<char, std::char_traits<char>, std::allocator<char> > const&)'
/tmp/cczDtRdT.o:listing.cpp:(.text+0x484): first defined here
collect2: ld returned 1 exit status


I am sorry for whole mess but I didn't want to miss anything for anyone who has come across similar problem.

One more thing; where it says **match_count.cpp** **listing.cpp** and **listings.cpp** it's just using the functions defined in ::utils::string::function()
