构造函数与“=”运算符做同样的事情吗?

问题描述 投票:0回答:1
  1. 当我们没有定义任何
    =
    运算符时,编译器如何知道 使用构造函数?
  2. 构造函数不是只在定义变量时调用吗?
#include <string>

class Person
{
public:
    std::string name;
    Person(const char* fullName) : name(fullName) {}
};

int main()
{
    Person p1("Jibel Sadeghi"); // This is ok because we declared the constructor with a const char*
    /* When we didn't overload the '=' operator for 'const char*',
       how the next lines don't have any errors? */
    p1 = "Ben Sadeghi";
}
c++ oop constructor operator-overloading assignment-operator
1个回答
7
投票

构造函数不是只在定义变量时调用吗?

不。创建对象(类的实例)时使用构造函数。

该对象可以保存在变量中,或数组的元素中,或动态分配的,或(如果您在这里有)临时对象中。

当我们没有定义任何 = 运算符时,编译器如何知道使用构造函数?

你的类有默认的复制赋值运算符,带有签名

Person& Person::operator=(const Person& assign_from);

和默认的移动赋值运算符,带签名

Person& Person::operator=(Person&& move_assign_from);

当编译器尝试编译时

p1 = "Ben Sadeghi";

它发现它需要

Person::operator=()
,查看所有候选者(有默认的两个,因为你没有提供任何),并且对于每个候选者,它尝试将实际参数转换为形式参数的类型。

对于复制赋值,形式参数的类型为

const Person&
,实际参数的类型为
const char[12]
,并且有一个隐式构造函数能够执行转换。所以可以调用
Person::Person(const char*)
,然后调用
Person& Person::operator=(const Person&)

对于移动赋值,形式参数的类型为

Person&&
,实际参数的类型为
const char[12]
,并且有一个隐式构造函数能够执行转换。所以可以调用
Person::Person(const char*)
,然后调用
Person& Person::operator=(Person&&)

Person&&
参数比
const Person&
更适合临时人员,因此最终选择了
Person::Person(const char*)
后跟
Person& Person::operator=(Person&&)
的序列。

© www.soinside.com 2019 - 2024. All rights reserved.