the operator "="error in class "String"

This is a discussion on the operator "="error in class "String" within the C++ Programming forums, part of the General Programming Boards category; Code: #include <iostream> using namespace std; class String { public: String(const char *str = NULL); // 通用构造函数 String(const String &another); ...

  1. #1
    Registered User
    Join Date
    May 2011
    Posts
    19

    the operator "="error in class "String"

    Code:
    #include <iostream>
    using namespace std;
    class String
    {
    public:
    	String(const char *str = NULL); // 通用构造函数
    	String(const String &another); // 拷贝构造函数
    	~ String(); // 析构函数
    	String& operator =(const String&);// 赋值函数
    	friend ostream& operator << (ostream&, const String& s);
    	friend istream& operator>>(istream& in, String& s);
    	friend String& operator+(const String&,const String&);
    private:
    	char *m_data; // 用于保存字符串
    };
    String::String(const char *str)
    {
       if (str == NULL)
          m_data = NULL;
       else
       {
    	   m_data = new char[strlen(str)+1];
           strcpy(m_data,str);
       }
    
    }
    String::String(const String &another)
    {
       m_data = new char[strlen(another.m_data)+1];
       strcpy(m_data,another.m_data);
    }
    String::~String()
    {
    	if(m_data != NULL)
    	{
    		delete m_data;
    		m_data = NULL;
    	}
    }
    String & String::operator=(const String &rhs)
    {
      if (*(this->m_data) == *rhs.m_data)
          return *this/*rhs*/;
      if(this->m_data!=NULL)
      this->~String();
      m_data = new char[strlen(rhs.m_data)+1];
      strcpy(m_data,rhs.m_data); 
      return *this;
    }
    ostream& operator << (ostream& out, const String& s)
    {
      if(s.m_data)
       out << s.m_data << endl;
      return out;
    }
    istream& operator>>(istream& in, String& s)
    {
    	char *s1 = new char[1000];
       in >> s1;
       s.m_data = new char[strlen(s1)+1];
       strcpy(s.m_data,s1); 
       return in;
    }
    String& operator+(const String& lhs,const String&rhs)
    {
      String ret(lhs);
      strcat(ret.m_data,rhs.m_data);
      return ret;
    }
    int main()
    {
       String s ;
       cin >> s;
       String s1;
       cin >> s1;
       String s2= s+s1;//this sentence has question , but i don't know why
       cout << s2;
    }
    who can explain it to me ?thanks!

  2. #2
    The Dragon Reborn
    Join Date
    Nov 2009
    Location
    Dublin, Ireland
    Posts
    629
    On running the program, the error is trying to return a local variable in the overload + function...what I got here
    You are returning a local object..which is wrong
    Last edited by Eman; 07-27-2011 at 09:01 AM.
    You ended that sentence with a preposition...Bastard!

  3. #3
    C++まいる!Cをこわせ! Elysia's Avatar
    Join Date
    Oct 2007
    Posts
    22,170
    >> if(m_data != NULL)
    Deleting NULL is perfectly defined. You can remove that.

    >> if (*(this->m_data) == *rhs.m_data)
    Very bad. Checks if the first character in the strings are equal. You should check for self-assignment, which is usually

    if (this == &rhs) or
    if (*this == rhs)

    >> char *s1 = new char[1000];
    >> in >> s1;
    Never do this. You can get a buffer overrun.
    Read into a std::string with std::getline or use I/O manipulators to limit the length of data to read.
    Example:

    std::string s;
    std::getline(std::cin, s);

    Or

    std::string s;
    std::cin >> s;

    operator >> is broken; it leaks memory.
    Suggested approach:

    std::string s;
    stream >> s;
    m_data = new char[s.size() + 1];
    strcpy(m_data, s.c_str());

    operator + is broken in design. It should return a temporary, not a reference. Furthermore, it doesn't check for enough room in the buffer, so buffer overflows can occur.

    You also failed to mention what the problem was.
    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.
    For information on how to enable C++11 on your compiler, look here.
    よく聞くがいい!私は天才だからね! ^_^

  4. #4
    Registered User manasij7479's Avatar
    Join Date
    Feb 2011
    Location
    Kolkata@India
    Posts
    2,490
    Quote Originally Posted by Elysia View Post

    >> char *s1 = new char[1000];
    >> in >> s1;
    Never do this. You can get a buffer overrun.
    Read into a std::string with std::getline or use I/O manipulators to limit the length of data to read.
    .
    Wouldn't using std::string defeat the purpose of making a string class in the first place? ....
    If it is an exercise; he won't probably be allowed to use std::string ..
    Manasij Mukherjee | gcc-4.8.2 @Arch Linux
    Slow and Steady wins the race... if and only if :
    1.None of the other participants are fast and steady.
    2.The fast and unsteady suddenly falls asleep while running !



  5. #5
    C++まいる!Cをこわせ! Elysia's Avatar
    Join Date
    Oct 2007
    Posts
    22,170
    It is a solution; I didn't mention it was the only solution.
    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.
    For information on how to enable C++11 on your compiler, look here.
    よく聞くがいい!私は天才だからね! ^_^

  6. #6
    Algorithm Dissector iMalc's Avatar
    Join Date
    Dec 2005
    Location
    New Zealand
    Posts
    6,261
    Don't implement your operator= that way. It is not exception safe.
    Instead use the "copy and swap" idiom. It is much easier, is exception safe, and may solve whatever error you were getting. Speaking of which, how about posting the actual error huh?!
    My homepage
    Advice: Take only as directed - If symptoms persist, please see your debugger

    Linus Torvalds: "But it clearly is the only right way. The fact that everybody else does it some other way only means that they are wrong"

  7. #7
    Registered User whiteflags's Avatar
    Join Date
    Apr 2006
    Location
    United States
    Posts
    7,525
    Quote Originally Posted by Elysia View Post
    operator >> is broken; it leaks memory.
    Suggested approach:

    std::string s;
    stream >> s;
    m_data = new char[s.size() + 1];
    strcpy(m_data, s.c_str());
    Seems like you fixed the buffer overrun but did nothing about the leak. To be clear, the memory that m_data held before using operator>> would be leaked, because m_data was not released before assigning new memory.

    Quote Originally Posted by Elysia View Post
    Read into a std::string with std::getline or use I/O manipulators to limit the length of data to read.
    Just to be clear, the IO manipulator that works for this is called std::setw.
    Last edited by whiteflags; 07-27-2011 at 07:04 PM.

  8. #8
    Registered User
    Join Date
    May 2011
    Posts
    19
    Quote Originally Posted by manasij7479 View Post
    Wouldn't using std::string defeat the purpose of making a string class in the first place? ....
    If it is an exercise; he won't probably be allowed to use std::string ..
    if don't use std::string ,how to write ?

  9. #9
    Registered User whiteflags's Avatar
    Join Date
    Apr 2006
    Location
    United States
    Posts
    7,525
    I explained in my post so you probably want to read the thread. All you need to do to know about std::setw and see examples is look it up. If you cannot use manipulators, and cannot use std::string, then the best you could do is not use operator>> for this, and instead use the istream::get() function.
    Last edited by whiteflags; 07-27-2011 at 08:37 PM.

  10. #10
    Registered User
    Join Date
    May 2011
    Posts
    19
    Quote Originally Posted by whiteflags View Post
    I explained in my post so you probably want to read the thread. All you need to do to know about std::setw and see examples is look it up. If you cannot use manipulators, and cannot use std::string, then the best you could do is not use operator>> for this, and instead use the istream::get() function.
    ok!thank you!

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Replies: 9
    Last Post: 03-31-2009, 04:23 PM
  2. Replies: 46
    Last Post: 08-24-2007, 04:52 PM
  3. "itoa"-"_itoa" , "inp"-"_inp", Why some functions have "
    By L.O.K. in forum Windows Programming
    Replies: 5
    Last Post: 12-08-2002, 07:25 AM
  4. "CWnd"-"HWnd","CBitmap"-"HBitmap"...., What is mean by "
    By L.O.K. in forum Windows Programming
    Replies: 2
    Last Post: 12-04-2002, 06:59 AM

Tags for this Thread


1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21