C++实现获取指定代码段的cpu占用

 更新时间:2023年12月28日 10:24:52   作者:BuffaloX_X  
这篇文章主要为大家详细介绍了C++实现获取指定代码段的cpu占用的相关知识,文中的示例代码讲解详细,具有一定的借鉴价值,有需要的小伙伴可以参考一下

windows

#include <iostream>
#include <windows.h>
#include <vector>
 
class CodeSegmentCPUMonitor {
public:
    static CodeSegmentCPUMonitor& getInstance() {
        static CodeSegmentCPUMonitor instance;
        return instance;
    }
 
    ~CodeSegmentCPUMonitor() {
        // 获取结束性能计数器值
        QueryPerformanceCounter(&endCounter);
 
        // 计算运行时间(秒)
        double elapsedTime = static_cast<double>(endCounter.QuadPart - startCounter.QuadPart) / frequency.QuadPart;
 
        // 计算 CPU 平均占用
        double averageCPUUsage = (totalCycles / elapsedTime) * 100.0 / processorSpeed;
 
        std::cout << "Total Average CPU Usage: " << averageCPUUsage << "%\n";
    }
 
    void enterCodeSegment() {
        // 进入代码段时记录开始时间
        QueryPerformanceCounter(&codeSegmentStartCounter);
    }
 
    void exitCodeSegment() {
        // 退出代码段时记录结束时间
        QueryPerformanceCounter(&codeSegmentEndCounter);
 
        // 计算代码段的 CPU 占用
        ULONGLONG codeSegmentCycles = codeSegmentEndCounter.QuadPart - codeSegmentStartCounter.QuadPart;
        totalCycles += codeSegmentCycles;
    }
 
private:
    LARGE_INTEGER frequency;
    LARGE_INTEGER startCounter;
    LARGE_INTEGER endCounter;
 
    LARGE_INTEGER codeSegmentStartCounter;
    LARGE_INTEGER codeSegmentEndCounter;
 
    ULONGLONG totalCycles = 0;
 
    // 假设处理器速度为 2.5 GHz,你需要根据实际情况调整这个值
    const double processorSpeed = 2.5e9;
 
    CodeSegmentCPUMonitor() {
        // 获取性能计数器频率
        if (QueryPerformanceFrequency(&frequency)) {
            // 获取初始性能计数器值
            QueryPerformanceCounter(&startCounter);
        } else {
            std::cerr << "Failed to get performance counter frequency.\n";
        }
    }
 
    // 禁用拷贝构造函数和赋值运算符
    CodeSegmentCPUMonitor(const CodeSegmentCPUMonitor&) = delete;
    CodeSegmentCPUMonitor& operator=(const CodeSegmentCPUMonitor&) = delete;
};
 
int main() {
    // Example: Measure CPU usage for code segment 1
    {
        CodeSegmentCPUMonitor::getInstance().enterCodeSegment();
 
        // Your code segment 1 here
 
        CodeSegmentCPUMonitor::getInstance().exitCodeSegment();
    }
 
    // Example: Measure CPU usage for code segment 2
    {
        CodeSegmentCPUMonitor::getInstance().enterCodeSegment();
 
        // Your code segment 2 here
 
        CodeSegmentCPUMonitor::getInstance().exitCodeSegment();
    }
 
    // ... Add more code segments as needed ...
 
    return 0;
}

linux

#include <iostream>
#include <vector>
#include <ctime>
 
class CodeSegmentCPUMonitor {
public:
    static CodeSegmentCPUMonitor& getInstance() {
        static CodeSegmentCPUMonitor instance;
        return instance;
    }
 
    ~CodeSegmentCPUMonitor() {
        // 获取结束时间
        struct timespec endTime;
        clock_gettime(CLOCK_MONOTONIC, &endTime);
 
        // 计算运行时间(秒)
        double elapsedTime = static_cast<double>(endTime.tv_sec - startTime.tv_sec) +
                             static_cast<double>(endTime.tv_nsec - startTime.tv_nsec) / 1e9;
 
        // 计算 CPU 平均占用
        double averageCPUUsage = (totalCycles / elapsedTime) * 100.0 / processorSpeed;
 
        std::cout << "Total Average CPU Usage: " << averageCPUUsage << "%\n";
    }
 
    void enterCodeSegment() {
        // 进入代码段时记录开始时间
        clock_gettime(CLOCK_MONOTONIC, &codeSegmentStartTime);
    }
 
    void exitCodeSegment() {
        // 退出代码段时记录结束时间
        struct timespec codeSegmentEndTime;
        clock_gettime(CLOCK_MONOTONIC, &codeSegmentEndTime);
 
        // 计算代码段的 CPU 占用
        double codeSegmentElapsedTime = static_cast<double>(codeSegmentEndTime.tv_sec - codeSegmentStartTime.tv_sec) +
                                        static_cast<double>(codeSegmentEndTime.tv_nsec - codeSegmentStartTime.tv_nsec) / 1e9;
        totalCycles += codeSegmentElapsedTime;
    }
 
private:
    struct timespec startTime;
    struct timespec codeSegmentStartTime;
 
    double totalCycles = 0;
 
    // 假设处理器速度为 2.5 GHz,你需要根据实际情况调整这个值
    const double processorSpeed = 2.5e9;
 
    CodeSegmentCPUMonitor() {
        // 获取初始时间
        clock_gettime(CLOCK_MONOTONIC, &startTime);
    }
 
    // 禁用拷贝构造函数和赋值运算符
    CodeSegmentCPUMonitor(const CodeSegmentCPUMonitor&) = delete;
    CodeSegmentCPUMonitor& operator=(const CodeSegmentCPUMonitor&) = delete;
};
 
int main() {
    // Example: Measure CPU usage for code segment 1
    {
        CodeSegmentCPUMonitor::getInstance().enterCodeSegment();
 
        // Your code segment 1 here
 
        CodeSegmentCPUMonitor::getInstance().exitCodeSegment();
    }
 
    // Example: Measure CPU usage for code segment 2
    {
        CodeSegmentCPUMonitor::getInstance().enterCodeSegment();
 
        // Your code segment 2 here
 
        CodeSegmentCPUMonitor::getInstance().exitCodeSegment();
    }
 
    // ... Add more code segments as needed ...
 
    return 0;
}

linux和windows条件编译

#include <iostream>
 
#ifdef _WIN32
#include <windows.h>
#else
#include <ctime>
#endif
 
class CodeSegmentCPUMonitor {
public:
    static CodeSegmentCPUMonitor& getInstance() {
        static CodeSegmentCPUMonitor instance;
        return instance;
    }
 
    ~CodeSegmentCPUMonitor() {
#ifdef _WIN32
        FILETIME endTime;
        GetSystemTimeAsFileTime(&endTime);
        ULARGE_INTEGER endTime64;
        endTime64.LowPart = endTime.dwLowDateTime;
        endTime64.HighPart = endTime.dwHighDateTime;
        double elapsedTime = static_cast<double>(endTime64.QuadPart - startTime.QuadPart) / frequency.QuadPart;
#else
        struct timespec endTime;
        clock_gettime(CLOCK_MONOTONIC, &endTime);
        double elapsedTime = static_cast<double>(endTime.tv_sec - startTime.tv_sec) +
                             static_cast<double>(endTime.tv_nsec - startTime.tv_nsec) / 1e9;
#endif
 
        double averageCPUUsage = (totalCycles / elapsedTime) * 100.0 / processorSpeed;
 
        std::cout << "Total Average CPU Usage: " << averageCPUUsage << "%\n";
    }
 
    void enterCodeSegment() {
#ifdef _WIN32
        GetSystemTimeAsFileTime(&codeSegmentStartTime);
#else
        clock_gettime(CLOCK_MONOTONIC, &codeSegmentStartTime);
#endif
    }
 
    void exitCodeSegment() {
#ifdef _WIN32
        FILETIME codeSegmentEndTime;
        GetSystemTimeAsFileTime(&codeSegmentEndTime);
        ULARGE_INTEGER codeSegmentEndTime64;
        codeSegmentEndTime64.LowPart = codeSegmentEndTime.dwLowDateTime;
        codeSegmentEndTime64.HighPart = codeSegmentEndTime.dwHighDateTime;
        double codeSegmentElapsedTime = static_cast<double>(codeSegmentEndTime64.QuadPart - codeSegmentStartTime.QuadPart) / frequency.QuadPart;
#else
        struct timespec codeSegmentEndTime;
        clock_gettime(CLOCK_MONOTONIC, &codeSegmentEndTime);
        double codeSegmentElapsedTime = static_cast<double>(codeSegmentEndTime.tv_sec - codeSegmentStartTime.tv_sec) +
                                        static_cast<double>(codeSegmentEndTime.tv_nsec - codeSegmentStartTime.tv_nsec) / 1e9;
#endif
 
        totalCycles += codeSegmentElapsedTime;
    }
 
private:
#ifdef _WIN32
    LARGE_INTEGER frequency;
    LARGE_INTEGER startTime;
    FILETIME codeSegmentStartTime;
#else
    struct timespec startTime;
    struct timespec codeSegmentStartTime;
#endif
 
    double totalCycles = 0;
    const double processorSpeed = 2.5e9;
 
    CodeSegmentCPUMonitor() {
#ifdef _WIN32
        QueryPerformanceFrequency(&frequency);
        QueryPerformanceCounter(&startTime);
#else
        clock_gettime(CLOCK_MONOTONIC, &startTime);
#endif
    }
 
    CodeSegmentCPUMonitor(const CodeSegmentCPUMonitor&) = delete;
    CodeSegmentCPUMonitor& operator=(const CodeSegmentCPUMonitor&) = delete;
};
 
int main() {
    // Example: Measure CPU usage for code segment 1
    {
        CodeSegmentCPUMonitor::getInstance().enterCodeSegment();
 
        // Your code segment 1 here
 
        CodeSegmentCPUMonitor::getInstance().exitCodeSegment();
    }
 
    // Example: Measure CPU usage for code segment 2
    {
        CodeSegmentCPUMonitor::getInstance().enterCodeSegment();
 
        // Your code segment 2 here
 
        CodeSegmentCPUMonitor::getInstance().exitCodeSegment();
    }
 
    // ... Add more code segments as needed ...
 
    return 0;
}

解耦log接口的形式1

#include <iostream>
#include <string>
 
// CPU Monitor Output Interface
class CPUMonitorOutputInterface {
public:
    virtual ~CPUMonitorOutputInterface() {}
    virtual void log(const std::string& message) = 0;
};
 
// ConsoleLogger: 实现CPUMonitorOutputInterface的一个Logger类示例
class ConsoleLogger : public CPUMonitorOutputInterface {
public:
    void log(const std::string& message) override {
        std::cout << "Logger: " << message << std::endl;
    }
};
 
class CodeSegmentCPUMonitor {
public:
    CodeSegmentCPUMonitor(CPUMonitorOutputInterface& logger) : logger(logger) {
#ifdef _WIN32
        QueryPerformanceFrequency(&frequency);
        QueryPerformanceCounter(&startTime);
#else
        clock_gettime(CLOCK_MONOTONIC, &startTime);
#endif
    }
 
    ~CodeSegmentCPUMonitor() {
#ifdef _WIN32
        FILETIME endTime;
        GetSystemTimeAsFileTime(&endTime);
        ULARGE_INTEGER endTime64;
        endTime64.LowPart = endTime.dwLowDateTime;
        endTime64.HighPart = endTime.dwHighDateTime;
        double elapsedTime = static_cast<double>(endTime64.QuadPart - startTime.QuadPart) / frequency.QuadPart;
#else
        struct timespec endTime;
        clock_gettime(CLOCK_MONOTONIC, &endTime);
        double elapsedTime = static_cast<double>(endTime.tv_sec - startTime.tv_sec) +
                             static_cast<double>(endTime.tv_nsec - startTime.tv_nsec) / 1e9;
#endif
 
        double averageCPUUsage = (totalCycles / elapsedTime) * 100.0 / processorSpeed;
        logger.log("Total Average CPU Usage: " + std::to_string(averageCPUUsage) + "%");
    }
 
    void enterCodeSegment() {
#ifdef _WIN32
        GetSystemTimeAsFileTime(&codeSegmentStartTime);
#else
        clock_gettime(CLOCK_MONOTONIC, &codeSegmentStartTime);
#endif
    }
 
    void exitCodeSegment() {
#ifdef _WIN32
        FILETIME codeSegmentEndTime;
        GetSystemTimeAsFileTime(&codeSegmentEndTime);
        ULARGE_INTEGER codeSegmentEndTime64;
        codeSegmentEndTime64.LowPart = codeSegmentEndTime.dwLowDateTime;
        codeSegmentEndTime64.HighPart = codeSegmentEndTime.dwHighDateTime;
        double codeSegmentElapsedTime = static_cast<double>(codeSegmentEndTime64.QuadPart - codeSegmentStartTime.QuadPart) / frequency.QuadPart;
#else
        struct timespec codeSegmentEndTime;
        clock_gettime(CLOCK_MONOTONIC, &codeSegmentEndTime);
        double codeSegmentElapsedTime = static_cast<double>(codeSegmentEndTime.tv_sec - codeSegmentStartTime.tv_sec) +
                                        static_cast<double>(codeSegmentEndTime.tv_nsec - codeSegmentStartTime.tv_nsec) / 1e9;
#endif
 
        totalCycles += codeSegmentElapsedTime;
    }
 
private:
    CPUMonitorOutputInterface& logger;
 
#ifdef _WIN32
    LARGE_INTEGER frequency;
    LARGE_INTEGER startTime;
    FILETIME codeSegmentStartTime;
#else
    struct timespec startTime;
    struct timespec codeSegmentStartTime;
#endif
 
    double totalCycles = 0;
    const double processorSpeed = 2.5e9;
};
 
int main() {
    // Example: Measure CPU usage for code segment 1 with ConsoleLogger
    {
        ConsoleLogger consoleLogger;
        CodeSegmentCPUMonitor monitor(consoleLogger);
        monitor.enterCodeSegment();
 
        // Your code segment 1 here
 
        monitor.exitCodeSegment();
    }
 
    // Example: Measure CPU usage for code segment 2 with ConsoleLogger
    {
        ConsoleLogger consoleLogger;
        CodeSegmentCPUMonitor monitor(consoleLogger);
        monitor.enterCodeSegment();
 
        // Your code segment 2 here
 
        monitor.exitCodeSegment();
    }
 
    // ... Add more code segments as needed ...
 
    return 0;
}

到此这篇关于C++实现获取指定代码段的cpu占用的文章就介绍到这了,更多相关C++获取cpu占用内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • C++控制台循环链表实现贪吃蛇

    C++控制台循环链表实现贪吃蛇

    这篇文章主要为大家详细介绍了C++控制台循环链表实现贪吃蛇,文中示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2020-04-04
  • C++实现LeetCode(39.组合之和)

    C++实现LeetCode(39.组合之和)

    这篇文章主要介绍了C++实现LeetCode(39.组合之和),本篇文章通过简要的案例,讲解了该项技术的了解与使用,以下就是详细内容,需要的朋友可以参考下
    2021-07-07
  • 教你用Matlab制作立体动态相册

    教你用Matlab制作立体动态相册

    没想到吧,MATLAB竟也能制作3D相册!本文将为大家详细介绍Matlab制作立体动态相册的方法步骤,感兴趣的小伙伴可以跟随小编一起动手试一试
    2022-03-03
  • Qt QString的使用实现

    Qt QString的使用实现

    本文主要介绍了Qt QString的使用实现,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2022-05-05
  • Qt利用DOM类实现读取xml文件

    Qt利用DOM类实现读取xml文件

    Dom(Document Object Model,即文档对象模型)能把XML文档转换成应用程序可遍历的树形结构,这样便可以随机访问其中的节点。本文将详细讲讲实现的方法,需要的可以参考一下
    2022-06-06
  • FFRPC应用 Client/Server使用及原理解析

    FFRPC应用 Client/Server使用及原理解析

    这篇文章主要介绍了FFRPC应用 Client/Server使用及原理解析,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下
    2019-08-08
  • C++实现线程同步的四种方式总结

    C++实现线程同步的四种方式总结

    这篇文章主要为大家详细介绍了C++实现线程同步的四种方式,文中的示例代码讲解详细,对我们学习C++有一定的帮助,需要的可以参考一下
    2022-11-11
  • C++中的explicit关键字实例浅析

    C++中的explicit关键字实例浅析

    在C++程序中很少有人去使用explicit关键字,不可否认,在平时的实践中确实很少能用的上,再说C++的功能强大,往往一个问题可以利用好几种C++特性去解决。接下来给大家介绍 C++中的explicit关键字,需要的朋友可以参考下
    2017-03-03
  • C++操作MySQL大量数据插入效率低下的解决方法

    C++操作MySQL大量数据插入效率低下的解决方法

    这篇文章主要介绍了C++操作MySQL大量数据插入效率低下的解决方法,需要的朋友可以参考下
    2014-07-07
  • C语言中break与continue的用法和区别详解

    C语言中break与continue的用法和区别详解

    当我们使用while或for循环时,如果想提前结束循环(在不满足结束条件的情况下结束循环),可以使用break或continue关键字,这篇文章主要给大家介绍了关于C语言中break与continue的用法和区别的相关资料,需要的朋友可以参考下
    2021-10-10

最新评论