ภาพรวม
ใน C++11+ สามารถวัดเวลาทำงานของโค้ดได้แม่นยำด้วย std::chrono::high_resolution_clock ซึ่งให้ความละเอียดสูงสุดที่ระบบรองรับ (มักเป็น Nanoseconds)
Syntax พื้นฐาน
#include <chrono>
using namespace std::chrono;
auto start = high_resolution_clock::now();
// Code to measure
auto stop = high_resolution_clock::now();
auto duration = duration_cast(stop - start);
cout << "Time: " << duration.count() << " microseconds";
ตัวอย่างโค้ดครบถ้วน
#include <iostream>
#include <chrono>
#include <vector>
#include <algorithm>
#include <random>
using namespace std;
using namespace std::chrono;
void measureSort(const string& name, vector& data) {
auto start = high_resolution_clock::now();
sort(data.begin(), data.end());
auto stop = high_resolution_clock::now();
auto duration = duration_cast(stop - start);
cout << name << ": " << duration.count() << " µs\n";
}
int main() {
const int SIZE = 100000;
vector data(SIZE);
// Generate Random Data
random_device rd;
mt19937 gen(rd());
uniform_int_distribution<> dis(1, 1000000);
generate(data.begin(), data.end(), [&](){ return dis(gen); });
// Test Multiple Runs
for (int run = 1; run <= 3; run++) {
vector copy = data;
cout << "Run " << run << ": ";
measureSort("std::sort", copy);
}
// Measure Specific Function
auto start = high_resolution_clock::now();
int sum = 0;
for (int i = 0; i < 1000000; ++i) sum += i;
auto stop = high_resolution_clock::now();
auto ns = duration_cast(stop - start);
auto us = duration_cast(stop - start);
auto ms = duration_cast(stop - start);
cout << "\nLoop Sum: " << ns.count() << " ns ("
<< us.count() << " µs, " << ms.count() << " ms)\n";
return 0;
}
ผลลัพธ์ตัวอย่าง
Run 1: std::sort: 12450 µs
Run 2: std::sort: 11980 µs
Run 3: std::sort: 12120 µs
Loop Sum: 2450000 ns (2450 µs, 2 ms)
Duration Units และ Cast
| Unit | Type | Cast Function | Typical Use |
|---|---|---|---|
| Nanoseconds | nanoseconds | duration_cast<nanoseconds> | High Precision, Short Operations |
| Microseconds | microseconds | duration_cast<microseconds> | General Purpose (Recommended) |
| Milliseconds | milliseconds | duration_cast<milliseconds> | Longer Operations, Human Readable |
| Seconds | seconds | duration_cast<seconds> | Very Long Operations |
| Custom | duration<double, ratio<1,1000000>> | Custom | Floating Point Precision |
Best Practices สำหรับ Benchmarking
- Warm-up Runs: รัน 1-2 รอบก่อนวัดจริง (JIT, Cache, Branch Prediction)
- Multiple Iterations: วัดหลายรอบ หารด้วยจำนวนรอบ (Reduce Noise)
- Disable Optimizations สำหรับ Debug:
-O0แต่ Production Benchmark ควร-O2/-O3 - Prevent Dead Code Elimination: ใช้ Result (Print/Return) ไม่งั้น Compiler Optimize ทิ้ง
- Use
volatileหรือbenchmark::DoNotOptimize(Google Benchmark) - Pin CPU Core:
taskset -c 0 ./benchmark(Linux)
Google Benchmark Library (Production Grade)
// Install: sudo apt-get install libbenchmark-dev
#include <benchmark/benchmark.h>
static void BM_Sort(benchmark::State& state) {
vector data(state.range(0));
random_device rd;
mt19937 gen(rd());
uniform_int_distribution<> dis(1, 1000000);
for (auto _ : state) {
generate(data.begin(), data.end(), [&](){ return dis(gen); });
sort(data.begin(), data.end());
benchmark::DoNotOptimize(data.data());
}
}
BENCHMARK(BM_Sort)->Arg(100000);
BENCHMARK_MAIN();
Clocks Comparison
| Clock | Monotonic | Precision | Use Case |
|---|---|---|---|
high_resolution_clock | Usually | Highest | Benchmarking, Profiling |
steady_clock | ✅ Guaranteed | High | Timeouts, Intervals (Safe) |
system_clock | ❌ No (Wall Time) | Variable | Wall Clock Time, Time Points |
หมายเหตุ: high_resolution_clock อาจเป็น Alias ของ steady_clock หรือ system_clock ขึ้นกับ Implementation