如果类B
有一个构造函数接受对类A
的对象的引用存储引用,并且使用该类的临时函数调用,则引用似乎在构造函数后变为无效完成(见example run)。但是,我尝试过的静态代码分析工具都没有检测到这种情况:
g++ -Wall -Wextra -pedantic
clang++ -Wall -Wextra -pedantic
cppcheck
clang-tidy
我想我明白编译器的行为符合标准。如何在现有代码库中检测此类代码?哪些编程约定可以帮助避免这种难以捕获的错误?
完整性下面的完整示例代码和带注释的输出。
#include <iostream>
class A {
public:
explicit A(int i) : i_(i) { std::cerr << this << " A\n"; }
~A() { std::cerr << this << " ~A\n"; }
void do_() const { std::cerr << this << " " << i_ << "\n"; }
private:
int i_;
};
class B {
public:
explicit B(const A& a) : a_(a) { std::cerr << this << " B\n"; }
~B() { std::cerr << this << " ~B\n"; }
void do_() const { std::cerr << this << " "; a_.do_(); }
const A& a_;
};
int main(int, char**) {
B b(A(42));
int i = 0;
b.do_();
std::cerr << i << " main\n";
}
输出:
# Construction of b
0xffa66138 A
0xffa66134 B
0xffa66138 ~A
# Calling b.do_()
0xffa66134 0xffa66138 42
# Printing i in main()
0 main
# End of main()
0xffa66134 ~B
答案 0 :(得分:2)
您可以禁止使用已删除的构造函数临时
class B {
public:
explicit B(const A& a) : a_(a) { std::cerr << this << " B\n"; }
B(A&&) = delete;
// ...
};
保证A
的有效期超过B
的方法是shared_ptr
。