Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • World
  • Users
  • Groups
Skins
  • Light
  • Cerulean
  • Cosmo
  • Flatly
  • Journal
  • Litera
  • Lumen
  • Lux
  • Materia
  • Minty
  • Morph
  • Pulse
  • Sandstone
  • Simplex
  • Sketchy
  • Spacelab
  • United
  • Yeti
  • Zephyr
  • Dark
  • Cyborg
  • Darkly
  • Quartz
  • Slate
  • Solar
  • Superhero
  • Vapor

  • Default (No Skin)
  • No Skin
Collapse
Code Project
  1. Home
  2. Other Discussions
  3. Clever Code
  4. Copy constructors and operator=

Copy constructors and operator=

Scheduled Pinned Locked Moved Clever Code
testingbeta-testingquestion
8 Posts 7 Posters 3 Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • L Offline
    L Offline
    Lost User
    wrote on last edited by
    #1

    Ack. Just got caught out by a classic and feel like a right fool. I'd written a unit test for testing object equality via a class's operator=. However, the test was succeeding, even though it should of failed, as I knew for sure that some class members were not being assigned. After some head scratching I looked at the test again:

    // Test operator=
    foo a;
    ...
    foo b = a;
    BOOST_CHECK(b == a);

    I knew that operator== was correct, so what was my schoolboy howler? I'd forgotten that foo b = a calls foo's copy constructor and not operator=. In this case I hadn't supplied a copy constructor, so the compiler obliged and created one for me, which, IIRC, does bitwise assignment, which meant the test succeeded. I changed the code to:

    // Test operator=
    foo a;
    ...
    foo b;
    b = a;
    BOOST_CHECK(b == a);

    And it worked as expected. D'oh. Moral: If you are going to override operator= you should probably add a copy constructor and make sure both are consistent!


    Kicking squealing Gucci little piggy.

    R R C 3 Replies Last reply
    0
    • L Lost User

      Ack. Just got caught out by a classic and feel like a right fool. I'd written a unit test for testing object equality via a class's operator=. However, the test was succeeding, even though it should of failed, as I knew for sure that some class members were not being assigned. After some head scratching I looked at the test again:

      // Test operator=
      foo a;
      ...
      foo b = a;
      BOOST_CHECK(b == a);

      I knew that operator== was correct, so what was my schoolboy howler? I'd forgotten that foo b = a calls foo's copy constructor and not operator=. In this case I hadn't supplied a copy constructor, so the compiler obliged and created one for me, which, IIRC, does bitwise assignment, which meant the test succeeded. I changed the code to:

      // Test operator=
      foo a;
      ...
      foo b;
      b = a;
      BOOST_CHECK(b == a);

      And it worked as expected. D'oh. Moral: If you are going to override operator= you should probably add a copy constructor and make sure both are consistent!


      Kicking squealing Gucci little piggy.

      R Offline
      R Offline
      Rama Krishna Vavilala
      wrote on last edited by
      #2

      I also faced similar problem many times. I learnt it the hard way toalways start my C++ class with private copy constructors and assignment operators with no implementations and make them public and add implementation later only when I need them.


      Debugging is twice as hard as writing the code in the first place. Therefore, if you write the code as cleverly as possible, you are, by definition, not smart enough to debug it. -Brian Kernighan

      1 Reply Last reply
      0
      • L Lost User

        Ack. Just got caught out by a classic and feel like a right fool. I'd written a unit test for testing object equality via a class's operator=. However, the test was succeeding, even though it should of failed, as I knew for sure that some class members were not being assigned. After some head scratching I looked at the test again:

        // Test operator=
        foo a;
        ...
        foo b = a;
        BOOST_CHECK(b == a);

        I knew that operator== was correct, so what was my schoolboy howler? I'd forgotten that foo b = a calls foo's copy constructor and not operator=. In this case I hadn't supplied a copy constructor, so the compiler obliged and created one for me, which, IIRC, does bitwise assignment, which meant the test succeeded. I changed the code to:

        // Test operator=
        foo a;
        ...
        foo b;
        b = a;
        BOOST_CHECK(b == a);

        And it worked as expected. D'oh. Moral: If you are going to override operator= you should probably add a copy constructor and make sure both are consistent!


        Kicking squealing Gucci little piggy.

        R Offline
        R Offline
        ricecake
        wrote on last edited by
        #3

        Rob Caldecott wrote:

        In this case I hadn't supplied a copy constructor, so the compiler obliged and created one for me, which, IIRC, does bitwise assignment

        IIRC, I think it does memberwise copy construction, recursively calling each member's copy constructor.

        Rob Caldecott wrote:

        Moral: If you are going to override operator= you should probably add a copy constructor and make sure both are consistent!

        Even better is the "Rule of Three": If you need any one out of {destructor, assignment operator, copy constructor} then you probably need all three!

        -- Marcus Kwok

        N 1 Reply Last reply
        0
        • L Lost User

          Ack. Just got caught out by a classic and feel like a right fool. I'd written a unit test for testing object equality via a class's operator=. However, the test was succeeding, even though it should of failed, as I knew for sure that some class members were not being assigned. After some head scratching I looked at the test again:

          // Test operator=
          foo a;
          ...
          foo b = a;
          BOOST_CHECK(b == a);

          I knew that operator== was correct, so what was my schoolboy howler? I'd forgotten that foo b = a calls foo's copy constructor and not operator=. In this case I hadn't supplied a copy constructor, so the compiler obliged and created one for me, which, IIRC, does bitwise assignment, which meant the test succeeded. I changed the code to:

          // Test operator=
          foo a;
          ...
          foo b;
          b = a;
          BOOST_CHECK(b == a);

          And it worked as expected. D'oh. Moral: If you are going to override operator= you should probably add a copy constructor and make sure both are consistent!


          Kicking squealing Gucci little piggy.

          C Offline
          C Offline
          Chris Meech
          wrote on last edited by
          #4

          I'm not sure why, but the statement

          foo b = a;

          is referred to as an initializer or initialization statement instead of an assignment statement. I'm sure there is a specific need that this difference addresses, but it's lost on me. :-O

          Chris Meech I am Canadian. [heard in a local bar] Nobody likes jerks. [espeir] The zen of the soapbox is hard to attain...[Jörgen Sigvardsson] I wish I could remember what it was like to only have a short term memory.[David Kentley]

          Z M 2 Replies Last reply
          0
          • C Chris Meech

            I'm not sure why, but the statement

            foo b = a;

            is referred to as an initializer or initialization statement instead of an assignment statement. I'm sure there is a specific need that this difference addresses, but it's lost on me. :-O

            Chris Meech I am Canadian. [heard in a local bar] Nobody likes jerks. [espeir] The zen of the soapbox is hard to attain...[Jörgen Sigvardsson] I wish I could remember what it was like to only have a short term memory.[David Kentley]

            Z Offline
            Z Offline
            Zac Howland
            wrote on last edited by
            #5

            Chris Meech wrote:

            I'm sure there is a specific need that this difference addresses, but it's lost on me.

            Efficiency. If it was to use the assignment operation, it would first have to create and initialize b (using the default constructor) and then call the assignment operator (basically, doing the assignments twice). By using the copy-constructor, it avoids initialization in the default constructor.

            If you decide to become a software engineer, you are signing up to have a 1/2" piece of silicon tell you exactly how stupid you really are for 8 hours a day, 5 days a week Zac

            1 Reply Last reply
            0
            • R ricecake

              Rob Caldecott wrote:

              In this case I hadn't supplied a copy constructor, so the compiler obliged and created one for me, which, IIRC, does bitwise assignment

              IIRC, I think it does memberwise copy construction, recursively calling each member's copy constructor.

              Rob Caldecott wrote:

              Moral: If you are going to override operator= you should probably add a copy constructor and make sure both are consistent!

              Even better is the "Rule of Three": If you need any one out of {destructor, assignment operator, copy constructor} then you probably need all three!

              -- Marcus Kwok

              N Offline
              N Offline
              Nemanja Trifunovic
              wrote on last edited by
              #6

              ricecake wrote:

              Even better is the "Rule of Three": If you need any one out of {destructor, assignment operator, copy constructor} then you probably need all three!

              True. Although modern C++ techniques tend to reduce it to The rule of two[^]


              Programming Blog utf8-cpp

              R 1 Reply Last reply
              0
              • N Nemanja Trifunovic

                ricecake wrote:

                Even better is the "Rule of Three": If you need any one out of {destructor, assignment operator, copy constructor} then you probably need all three!

                True. Although modern C++ techniques tend to reduce it to The rule of two[^]


                Programming Blog utf8-cpp

                R Offline
                R Offline
                ricecake
                wrote on last edited by
                #7

                Nemanja Trifunovic wrote:

                The rule of two[^]

                Interesting, thanks for the nice article.

                -- Marcus Kwok

                1 Reply Last reply
                0
                • C Chris Meech

                  I'm not sure why, but the statement

                  foo b = a;

                  is referred to as an initializer or initialization statement instead of an assignment statement. I'm sure there is a specific need that this difference addresses, but it's lost on me. :-O

                  Chris Meech I am Canadian. [heard in a local bar] Nobody likes jerks. [espeir] The zen of the soapbox is hard to attain...[Jörgen Sigvardsson] I wish I could remember what it was like to only have a short term memory.[David Kentley]

                  M Offline
                  M Offline
                  Michael Dunn
                  wrote on last edited by
                  #8

                  In:

                  foo a;
                  foo b = a;

                  the second line is equivalent to:

                  foo b(a);

                  That is, construct b as a copy of a. That's why the copy ctor is called.

                  --Mike-- Visual C++ MVP :cool: LINKS~! Ericahist | PimpFish | CP SearchBar v3.0 | C++ Forum FAQ

                  1 Reply Last reply
                  0
                  Reply
                  • Reply as topic
                  Log in to reply
                  • Oldest to Newest
                  • Newest to Oldest
                  • Most Votes


                  • Login

                  • Don't have an account? Register

                  • Login or register to search.
                  • First post
                    Last post
                  0
                  • Categories
                  • Recent
                  • Tags
                  • Popular
                  • World
                  • Users
                  • Groups