#include <benchmark/benchmark.h>
namespace bench = benchmark;
#include <chrono>
#include <ctime>
#include <iostream>
#include <iomanip>
#include <sstream>
#include <thread>
#include <windows.h>
#include <tchar.h>
#define BENCH(x) BENCHMARK(x)->Iterations(100'000)->Unit(bench::kMicrosecond)
void BackgroundWork()
{
auto now = std::chrono::system_clock::now();
std::vector<std::string> result;
constexpr size_t size = 60;
result.resize(size + 1);
for (int i = 0; i < size + 1; ++i) {
auto timePoint = std::chrono::system_clock::to_time_t(now - std::chrono::minutes(i * 1));
std::stringstream ss;
ss << std::put_time(std::localtime(&timePoint), "%I:%M");
result[size - i] = ss.str();
}
}
//
// THREAD_PRIORITY_LOWEST & THREAD_MODE_BACKGROUND_BEGIN & THREAD_MODE_BACKGROUND_END
//
void ThreadPriorityTestV1()
{
::SetThreadPriority(::GetCurrentThread(), THREAD_PRIORITY_LOWEST);
if (!SetThreadPriority(GetCurrentThread(), THREAD_MODE_BACKGROUND_BEGIN)) {
DWORD dwError = GetLastError();
if (ERROR_THREAD_MODE_ALREADY_BACKGROUND == dwError) {
_tprintf(TEXT("Already in background mode\n"));
} else {
_tprintf(TEXT("Failed to enter background mode (%d)\n"), dwError);
}
return;
}
BackgroundWork();
if (!SetThreadPriority(GetCurrentThread(), THREAD_MODE_BACKGROUND_END)) {
_tprintf(TEXT("Failed to end background mode (%d)\n"), GetLastError());
}
}
//
// THREAD_MODE_BACKGROUND_BEGIN & THREAD_MODE_BACKGROUND_END
//
void ThreadPriorityTestV2()
{
if (!SetThreadPriority(GetCurrentThread(), THREAD_MODE_BACKGROUND_BEGIN)) {
DWORD dwError = GetLastError();
if (ERROR_THREAD_MODE_ALREADY_BACKGROUND == dwError) {
_tprintf(TEXT("Already in background mode\n"));
}
else {
_tprintf(TEXT("Failed to enter background mode (%d)\n"), dwError);
}
return;
}
BackgroundWork();
if (!SetThreadPriority(GetCurrentThread(), THREAD_MODE_BACKGROUND_END)) {
_tprintf(TEXT("Failed to end background mode (%d)\n"), GetLastError());
}
}
//
// THREAD_PRIORITY_LOWEST
//
void ThreadPriorityTestV3()
{
::SetThreadPriority(::GetCurrentThread(), THREAD_PRIORITY_LOWEST);
BackgroundWork();
}
//
// NONE
//
void ThreadPriorityTestV4()
{
BackgroundWork();
}
void TestV1(benchmark::State& state)
{
for (auto _ : state) {
std::thread t1{ ThreadPriorityTestV1 };
std::thread t2{ ThreadPriorityTestV1 };
t1.join();
t2.join();
}
}
BENCH(TestV1);
void TestV2(benchmark::State& state)
{
for (auto _ : state) {
std::thread t1{ ThreadPriorityTestV2 };
std::thread t2{ ThreadPriorityTestV2 };
t1.join();
t2.join();
}
}
BENCH(TestV2);
void TestV3(benchmark::State& state)
{
for (auto _ : state) {
std::thread t1{ ThreadPriorityTestV3 };
std::thread t2{ ThreadPriorityTestV3 };
t1.join();
t2.join();
}
}
BENCH(TestV3);
void TestV4(benchmark::State& state)
{
for (auto _ : state) {
std::thread t1{ ThreadPriorityTestV4 };
std::thread t2{ ThreadPriorityTestV4 };
t1.join();
t2.join();
}
}
BENCH(TestV4);
BENCHMARK_MAIN();
- THREAD_PRIORITY_LOWEST & THREAD_MODE_BACKGROUND_BEGIN & THREAD_MODE_BACKGROUND_END
TestV1/iterations:100000 1996 us 215 us 100000
- THREAD_MODE_BACKGROUND_BEGIN & THREAD_MODE_BACKGROUND_END
TestV2/iterations:100000 1964 us 206 us 100000
- THREAD_PRIORITY_LOWEST
TestV3/iterations:100000 2010 us 211 us 100000
- NONE
TestV4/iterations:100000 2018 us 207 us 100000