You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

关于用户提供的显式默认函数被隐式删除时程序非法的疑问

关于C++用户提供函数与显式删除函数的疑问解答

根据C++标准定义:用户声明且首次声明未显式默认或删除的函数为用户提供函数;用户提供的显式默认函数(即首次声明后显式默认的函数)在显式默认点定义,若被隐式定义为删除则程序非法。

比如下面的结构体中,所有特殊成员函数都采用了显式默认:

struct trivial
{
    trivial() = default;
    trivial(const trivial&) = default;
    trivial(trivial&&) = default;
    trivial& operator=(const trivial&) = default;
    trivial& operator=(trivial&&) = default;
    ~trivial() = default;
};

疑问点

我写出了下面这段显式删除所有特殊成员函数的代码,它能正常运行,这和上面的定义表述有冲突吗?

struct trivial
{
    trivial() = delete;
    trivial(int){};
    trivial(const trivial&) = delete;
    trivial(trivial&&) = delete;
    trivial& operator=(const trivial&) = delete;
    trivial& operator=(trivial&&) = delete;
    ~trivial() = delete;
};

核心区别解释

那段定义只针对**显式默认(= default)**的函数,和显式删除的函数是完全不同的两种情况:

  • 显式默认的函数,是你要求编译器帮你生成符合规则的默认实现。但如果因为类的某些特性(比如包含无法默认构造的成员),编译器没法生成有效实现,这个函数会被隐式删除,此时程序就会非法——毕竟你要求生成,但编译器做不到。
  • 显式删除(= delete)的函数,是你主动告诉编译器“这个函数不能被调用,也不需要存在实现”。编译器不会尝试生成它的代码,只要你在程序里没有调用这些被删除的函数(比如你的代码只用到了自定义的trivial(int)构造函数),程序就能正常编译运行。

简单说,显式删除是你主动禁用函数,显式默认是你请求编译器生成函数但可能失败——这就是为什么你的删除版代码能正常运行,和那段定义完全不冲突。

内容的提问来源于stack exchange,提问作者John

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.22 16:04:51