none
перегрузка присваивания CLR C++ RRS feed

  • Вопрос

  • Здравствуйте.

    Перекопал весь локальный MSDN в поисках ответа на вопрос корректной перегрузки оператора присваивания для пользовательских управляемых классов, но безрезультатно.

    Следующая форма, не вызывая сомнений у компилятора, отчего-то игнорируется во время выполнения:

    public ref class CL {

    public:

    Int32 i;

    CL^ operator = (CL ^associate) ;

    CL();

    };

     

    Cl ^CL::operator = (CL ^associate) {

    this->i = associate->i;

    return this;

    }

    Спасибо за комментарии.

     

    9 февраля 2011 г. 19:55

Ответы

  • Когда вы пишите a = b (Cl ^a и Cl ^b) это означает, что теперь указатель A будет указывать на адрес памяти, на который указывает B. С теми объектами, на которые ссылаются указатели ничего не происходит, просто изменяются сами указатели. Поэтому это не приводит в вызову оператора присваивания для класса Cl.

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

    *a = *b;

    Или можно использовать конструктор, вместо оператора присваивания:

    a = gcnew Cl(b);

     


    Для связи [mail]
    • Помечено в качестве ответа _fizzy 12 февраля 2011 г. 12:50
    11 февраля 2011 г. 8:54
  • Возможность объявить в классе CL статические операторы, принимающие и возвращающие не CL, а именно CL^ - это расширение CLI. 

    Расширение не может противоречить стандарту C++, и в спецификации C++/CLI есть сноска в разделе 19.7 Static Operators:

    However, operators required by Standard C++ to be instance functions shall continue to be instance 

    functions. [Note: Standard C++ specifies that these operators are: assignment operators (§13.5.3), 

    operator() (§13.5.4), operator[] (§13.5.5), and operator-> (§13.5.6). end note]

    Объявить instance function в классе CL^ (а не CL) нельзя, и ответ на вопрос "можно ли переопределить = для CL^", скорее всего - нельзя.


    My blog
    • Помечено в качестве ответа _fizzy 12 февраля 2011 г. 12:49
    11 февраля 2011 г. 22:26
    Модератор
  • и ответ на вопрос "можно ли переопределить = для CL^", скорее всего - нельзя.

    Видимо, так оно и есть - у  меня ничего не получилось.

    Максимум, что возможно:

    public ref class CL {

    public:

    Int32 i;

    CL% operator = (CL ^associate) {

    *i=associate->i;

    return *this;

    }

    CL();

    };

     

    В этом случае отрабатывает присвоение:

    CL^ a =gcnew
     CL();
    CL^ b =gcnew CL();
    *а=b;

     

    • Помечено в качестве ответа _fizzy 12 февраля 2011 г. 12:49
    11 февраля 2011 г. 23:08

Все ответы

  • Когда Вы пишите

    CL^ a =gcnew CL();
    
    CL^ b =gcnew CL();
    
    b->i=100;
    
    a=b;
    
    чему равно  a->i ?

     

     

    9 февраля 2011 г. 21:31
  • я привел лишь схему, а не фрагмент реального кода.

    в действительности 'i' определено для обоих объектов.

    Вот что происходит, полагая Вашу запись продолжением моей схемы,: во время присваивания 'a=b' адрес 'b' копируется в 'а', в то время как перегруженному оператору управление не передается вовсе.

    10 февраля 2011 г. 18:15
  • Перегрузка оператора должна быть объявлена как статичекский метод класса.

    Вроде бы, так. :)

    10 февраля 2011 г. 22:06
  • Когда вы пишите a = b (Cl ^a и Cl ^b) это означает, что теперь указатель A будет указывать на адрес памяти, на который указывает B. С теми объектами, на которые ссылаются указатели ничего не происходит, просто изменяются сами указатели. Поэтому это не приводит в вызову оператора присваивания для класса Cl.

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

    *a = *b;

    Или можно использовать конструктор, вместо оператора присваивания:

    a = gcnew Cl(b);

     


    Для связи [mail]
    • Помечено в качестве ответа _fizzy 12 февраля 2011 г. 12:50
    11 февраля 2011 г. 8:54
  • Присваивание не может быть перегружено в виде статического метода. По крайней мере не получается еще на этапе компиляции.

     

    Дмитрий, но как быть с типом перегруженного оператора?

    CL^ operator = (CL ^associate)

     Принимает и возвращает дескрипторы, а не объекты.

    Можно ли все-таки как-нибудь реализовать перегрузку формы a=b, где оба операнда - дескрипторы?

     

    Хочу заметить, что перегрузка, например, сложения в виде

    static CL ^ operator + (CL ^leftApp, CL ^rightApp)

    {

    CL ^res = gcnew (CL);

    res->i = leftApp->i + rightApp->i;

    return res;

    }

    работает вполне корректно при

    CL ^a, ^b, ^c;

    ...

    a->assign(b+c);

    где функция assign в целом аналогична описанному выше оператору присваивания.

     

     

    11 февраля 2011 г. 20:00
  • Возможность объявить в классе CL статические операторы, принимающие и возвращающие не CL, а именно CL^ - это расширение CLI. 

    Расширение не может противоречить стандарту C++, и в спецификации C++/CLI есть сноска в разделе 19.7 Static Operators:

    However, operators required by Standard C++ to be instance functions shall continue to be instance 

    functions. [Note: Standard C++ specifies that these operators are: assignment operators (§13.5.3), 

    operator() (§13.5.4), operator[] (§13.5.5), and operator-> (§13.5.6). end note]

    Объявить instance function в классе CL^ (а не CL) нельзя, и ответ на вопрос "можно ли переопределить = для CL^", скорее всего - нельзя.


    My blog
    • Помечено в качестве ответа _fizzy 12 февраля 2011 г. 12:49
    11 февраля 2011 г. 22:26
    Модератор
  • и ответ на вопрос "можно ли переопределить = для CL^", скорее всего - нельзя.

    Видимо, так оно и есть - у  меня ничего не получилось.

    Максимум, что возможно:

    public ref class CL {

    public:

    Int32 i;

    CL% operator = (CL ^associate) {

    *i=associate->i;

    return *this;

    }

    CL();

    };

     

    В этом случае отрабатывает присвоение:

    CL^ a =gcnew
     CL();
    CL^ b =gcnew CL();
    *а=b;

     

    • Помечено в качестве ответа _fizzy 12 февраля 2011 г. 12:49
    11 февраля 2011 г. 23:08
  • //Вот такая   перезагрузка работает.

    public ref class CL {

    public:

    Int32 i;

    CL% operator = (CL% associate) {

    i=associate.i;

    return *this;

    }

    CL();

    };

     

     

    CL a;

    CL b;

    а=b;



    15 февраля 2011 г. 18:08