0

Build and run of Move constructors example from Microsoft, and the output was:

default
copy
int,int,int
b2 contents: Toupee Megaphone Suit 

However I was expecting it to print move at some point. Is the move constructor actually being called? Why there is no print?

Following is the code from the referenced link:

#include <iostream>
#include <vector>
#include <string>
#include <algorithm>
using namespace std;

class Box {
public:
    Box() { std::cout << "default" << std::endl; }
    Box(int width, int height, int length)
       : m_width(width), m_height(height), m_length(length)
    {
        std::cout << "int,int,int" << std::endl;
    }
    Box(Box& other)
       : m_width(other.m_width), m_height(other.m_height), m_length(other.m_length)
    {
        std::cout << "copy" << std::endl;
    }
    Box(Box&& other) : m_width(other.m_width), m_height(other.m_height), m_length(other.m_length)
    {
        m_contents = std::move(other.m_contents);
        std::cout << "move" << std::endl;
    }
    int Volume() { return m_width * m_height * m_length; }
    void Add_Item(string item) { m_contents.push_back(item); }
    void Print_Contents()
    {
        for (const auto& item : m_contents)
        {
            cout << item << " ";
        }
    }
private:
    int m_width{ 0 };
    int m_height{ 0 };
    int m_length{ 0 };
    vector<string> m_contents;
};

Box get_Box()
{
    Box b(5, 10, 18); // "int,int,int"
    b.Add_Item("Toupee");
    b.Add_Item("Megaphone");
    b.Add_Item("Suit");

    return b;
}

int main()
{
    Box b; // "default"
    Box b1(b); // "copy"
    Box b2(get_Box()); // "move"
    cout << "b2 contents: ";
    b2.Print_Contents(); // Prove that we have all the values

    char ch;
    cin >> ch; // keep window open
    return 0;
}
KcFnMi
  • 5,516
  • 10
  • 62
  • 136
  • 3
    Like all free introductions, MIcrosoft's "learn C++" material is not very good. A lot of it seems written by people who don't use C++ at all (and some of it is just plain wrong). Get a [good book](https://stackoverflow.com/questions/388242/the-definitive-c-book-guide-and-list) instead. – molbdnilo Oct 06 '22 at 05:03
  • 1
    You may find [this](https://en.cppreference.com/w/cpp/language/copy_elision) interesting. Basically both copy and move are elided in the case you're asking about. – WhozCraig Oct 06 '22 at 05:04
  • This elided thing is kinda new to me. May I thing that, on `Box b2(get_Box());`, a move and then a copy was supposed to happen, but due to this elided thing they are actually skipped? – KcFnMi Oct 06 '22 at 05:27
  • *"due to this elided thing they are actually skipped?"* Yes, exactly that. – BoP Oct 06 '22 at 09:20
  • 1
    Also note the "13 contributors" mentioned at the top of the page. This makes the material kind of random noice. – BoP Oct 06 '22 at 09:22
  • You mean random noiSe? – KcFnMi Oct 06 '22 at 09:29
  • Can I toggle the elided behavior off? To observe what was actually intended. – KcFnMi Oct 06 '22 at 09:30

1 Answers1

2

If you want to see the Move constructor add Box b3(std::move(b)); somewhere below and it will call the move constructor. I would just google "The rule of five cpp" because there also is the copy and move assignment operator.

  • Well, `std::move` is being explicitly called, so yes, I can understand the consequeces. – KcFnMi Oct 06 '22 at 10:05
  • In which cases is the move constructor implicitly called? – KcFnMi Oct 06 '22 at 14:12
  • Basically only when you make std::move. There are exeptions like if it is the only constructor existing. Edit: [doc for Move](https://en.cppreference.com/w/cpp/language/move_constructor) under Explanation and then initialization @KcFnMi Found also this [stackOverflow](https://stackoverflow.com/a/13125851) – Crafty-Codes Oct 07 '22 at 13:05