我现在有两个c++单元
第一个是A单元
#include <iostream>
#include <string>
#include <cmath>
#include <chrono>
// 注意!!!不同C++单元中的相同类名不同实现方法:当它们被编译和链接时编译器不会发生警告而是选择其中的一个去使用
// 如果这里和其他单元一样叫Timer那么析构方法就不一定用的是哪个单元类中的析构方法了(至少是析构方法会发生混乱,其他的估计也会)
// 解决方法:可以使用命名空间
class Timer {
public:
Timer(const char* name)
:m_Name(name),m_Stopped(false)
{
m_StartTimePoint = std::chrono::high_resolution_clock::now();
}
~Timer() {
Stop();
}
void Stop() {
auto endTimePoint = std::chrono::high_resolution_clock::now();
auto start = std::chrono::time_point_cast<std::chrono::microseconds>(m_StartTimePoint).time_since_epoch().count();
auto end = std::chrono::time_point_cast<std::chrono::microseconds>(endTimePoint).time_since_epoch().count();
auto duration = end - start;
double ms = duration * 0.001;
std::cout << m_Name << ":" << duration << "us(" << ms << "ms)\n";
m_Stopped = true;
}
private:
std::chrono::time_point<std::chrono::high_resolution_clock> m_StartTimePoint;
const char* m_Name;
bool m_Stopped;
};
void function1() {
Timer timer("Function1");
for (int i = 0; i < 10; i++) {
std::cout << "Hello" << i << std::endl;
}
}
void function2() {
Timer timer("Function2");
for (int i = 0; i < 10; i++) {
std::cout << "Hello"<< sqrt(i) << std::endl;
}
}
int main() {
function1();
function2();
std::cin.get();
}
第二个是B单元
#include <iostream>
#include <chrono> // 时钟相关
#include <thread>
// 注意!!!不同C++单元中的相同类名不同实现方法:当它们被编译和链接时编译器不会发生警告而是选择其中的一个去使用
// 如果这里和其他单元一样叫Timer那么析构方法就不一定用的是哪个单元类中的析构方法了(至少是析构方法会发生混乱,其他的估计也会)
// 解决方法:可以使用命名空间
class Timer // 创建这么一个结构/类 在构造析构方法搞事情
{
public:
std::chrono::time_point<std::chrono::steady_clock> start, end; // 两个时间点类型变量
std::chrono::duration<float> dur; // 一个时间段类型变脸
Timer() {
start = std::chrono::high_resolution_clock::now();
}
~Timer() {
end = std::chrono::high_resolution_clock::now();
dur = end - start;
std::cout << "花费时间:" << dur.count() * 1000.0f<< "ms" << std::endl;
}
};
void Function() {
Timer t; // 现在只需要在想要测量耗时的方法开头实例一个Timer类就好了,类结束回收自动打印耗时,真tm方便
for (int i = 0; i < 10; i++) {
std::cout << "count\n";
}
}
当我运行时会发现我确实使用了A单元中Timer的构造方法,但是在栈生命周期回收后调用的构造方法确实B单元中Timer的构造方法。
不同C++单元中的相同类名不同实现方法:当它们被编译和链接时编译器不会发生警告而是选择其中的一个去使用,为了避免这种情况可以使用命名空间。
问题产生过程及原理:
编译器一次只能在一个编译单元上工作;这将是源文件和它包含的任何内容。由于您的课程位于不同的档案中,因此不存在冲突。
链接器将所有内容放在一起,但它不知道类定义,因此它也不会看到冲突,导致问题发生。
解决问题时参考了:不同C++文件中的相同类名 | 经验摘录