Реализация C ++ оператора строки - PullRequest
0 голосов
/ 05 декабря 2011

У меня проблема с char *, строка сложена вместе такой как это:

enter code here
s2 = s3 + "," + s1; 

и у меня три оператора ниже

friend Mystring operator+( const Mystring &lhs, const Mystring &rhs);  -- 1
friend Mystring operator+( const Mystring &mystr, const char *ch ); -- 2
friend Mystring operator+( const char *ch, const Mystring &mystr ); -- 3

но я использую 1 и 3, он рухнет, но я использую 1 и 3 может принести пользу.

Моя проблема в том, что порядок не s3 + "," сначала, поэтому сначала используйте оператор w и результат использует оператор 3, но факт не такой, как я думал.

Может кто-нибудь объяснить, почему это происходит?

Mystring operator+( const Mystring &mystr,const char *ch )
{
  Mystring tmp;
  tmp.str_ = new char[ strlen(mystr.str_)+2 ];
  strcpy( tmp.str_, mystr.str_ );
  strcat( tmp.str_, ch );
  return tmp;
}


Mystring operator+( const char *ch, const Mystring &mystr )
{
  Mystring tmp;
  tmp.str_ = new char[ strlen(mystr.str_)+strlen(mystr.str_)+1 ];
  strcpy( tmp.str_, mystr.str_ );
  strcat( tmp.str_, mystr.str_ );
  return tmp;
}

Mystring operator+( const Mystring &lhs, const Mystring &rhs )
{
  Mystring tmp;
  tmp.str_ = new char[ strlen(lhs.str_)+strlen(rhs.str_)+1 ];
  strcpy( tmp.str_, lhs.str_ );
  strcat( tmp.str_, rhs.str_ );
  return tmp;
}

Ответы [ 3 ]

2 голосов
/ 05 декабря 2011

Попробуйте сначала протестировать более простые вещи:

s2 = s3 + ",";
s2 = "," + s3;
s3 = s1 + s2;

перед переходом к цепочке:

s2 = s3 + ","  + s1;

таким образом, вы можете понять, в чем проблема.

1 голос
/ 05 декабря 2011

В

Mystring operator+( const Mystring &mystr,const char *ch )
{
  Mystring tmp;
  tmp.str_ = new char[ strlen(mystr.str_)+2 ];

вы должны написать:

  tmp.str_ = new char[ strlen(mystr.str_) + strlen(ch) + 1 ];

А здесь:

Mystring operator+( const char *ch, const Mystring &mystr )
{
  Mystring tmp;
  tmp.str_ = new char[ strlen(mystr.str_)+strlen(mystr.str_)+1 ];

вы должны написать:

  tmp.str_ = new char [ strlen(ch) + strlen(mystr.str_) + 1 ];
0 голосов
/ 05 декабря 2011

Вы читали это? Что такое правило трех?

Основываясь на том, как вы вручную управляете памятью в этих функциях, я думаю, можно с уверенностью предположить, что вы этого не сделали.В любом случае, как только вы правильно реализуете большую тройку, вот что вы должны сделать.Сначала у вас должно быть два неотъемлемых члена.Один для хранения размера строки, а другой для хранения емкости динамического массива.Затем вы хотите иметь приватную функцию, назовем ее increase_capacity, которая увеличивает емкость , если необходимо .Все ваше распределение памяти будет происходить там, в одном месте.Это сильно упростит вещи.Это может выглядеть примерно так:

void increase_capacity(int cap)
{
    if (cap <= capacity_) return;
    char * temp = new char[cap];
    capacity_ = cap;
    memcpy(temp, str_, size_); // Or size_ + 1 if your string is null terminated.
                               // It doesn't have to be.
    delete [] str_;
    str_ = temp;
}

Теперь у вас также должна быть функция изменения размера, которая при необходимости корректирует размер.

void resize(int size)
{
    if (size > capacity_)
    {
        int cap = capacity_ * 2;
        cap = cap > size ? cap : size;
        increase_capacity(cap);
    }

    size_ = size;
    // Fill in new elements with some default value, or don't.
}

Лучше, чем все вышеперечисленное, выследует просто использовать vector<char>, но, возможно, вы пытаетесь понять ручное управление памятью, это нормально.

Теперь вы должны реализовать operator + = в качестве члена:

Mystring & operator+=(const Mystring & rhs)
{
    int old_size = size_;
    resize(size_ + rhs.size_);
    memcpy(str_ + old_size, rhs.str_, rhs.size_);
    return *this;
}

Еслиесли хотите, вы также можете реализовать тот, который принимает const char *, который сохранит выделение, которое произойдет, если вы полагаетесь на неявное преобразование.

Наконец, вы можете реализовать свой operator+:

Mystring operator+(Mystring lhs, const Mystring & rhs)
{
    return lhs += rhs;
}

Если у вас есть неявное преобразование из const char *, оно должно охватывать все из них.Но если вы написали дополнительный operator+=, который занимает const char *, чтобы сделать меньше выделений, вам, вероятно, также следует написать тот, который занимает const char * с правой стороны.Он выглядит так же, как и выше, только тип второго параметра изменяется.Вам не нужно писать один для обратной операции, так как в любом случае lhs нужно будет выделять как Mystring.

...