commit
7cdca9d255
@ -0,0 +1,22 @@
|
||||
|
||||
#ifndef CPP_START_NON_COPY_ABLE_H
|
||||
#define CPP_START_NON_COPY_ABLE_H
|
||||
|
||||
|
||||
class NonCopyAble {
|
||||
|
||||
protected:
|
||||
NonCopyAble() = default;
|
||||
|
||||
~NonCopyAble() = default;
|
||||
|
||||
public:
|
||||
// 禁用复制构造
|
||||
NonCopyAble(const NonCopyAble &) = delete;
|
||||
|
||||
// 禁用赋值构造
|
||||
NonCopyAble &operator=(const NonCopyAble &) = delete;
|
||||
};
|
||||
|
||||
|
||||
#endif //CPP_START_NON_COPY_ABLE_H
|
@ -0,0 +1,292 @@
|
||||
#include <iostream>
|
||||
#include <map>
|
||||
#include <thread>
|
||||
|
||||
template<typename T>
|
||||
class iterator {
|
||||
public:
|
||||
using value_type = T;
|
||||
using size_type = size_t;
|
||||
|
||||
private:
|
||||
size_type cursor_;
|
||||
const value_type step_;
|
||||
value_type value_;
|
||||
|
||||
public:
|
||||
|
||||
iterator(size_type cur_satrt, value_type begin_val, value_type step_val)
|
||||
:
|
||||
cursor_(cur_satrt),
|
||||
step_(step_val),
|
||||
value_(begin_val) {
|
||||
|
||||
};
|
||||
|
||||
value_type operator*() const {
|
||||
return value_;
|
||||
};
|
||||
|
||||
bool operator!=(const iterator &rhs) const {
|
||||
return (cursor_ != rhs.cursor_);
|
||||
};
|
||||
|
||||
iterator *operator++() {
|
||||
value_ += step_;
|
||||
++cursor_;
|
||||
return (*this);
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
void foreach() {
|
||||
std::map<std::string, int> mm = {
|
||||
{"a", 1},
|
||||
{"b", 2},
|
||||
{"c", 3}
|
||||
};
|
||||
|
||||
for (const auto &m: mm) {
|
||||
std::cout << m.first << " -> " << m.second << std::endl;
|
||||
}
|
||||
}
|
||||
|
||||
int g_constructCount = 0;
|
||||
int g_copy_constructCount = 0;
|
||||
int g_destructCount = 0;
|
||||
|
||||
class A {
|
||||
|
||||
public:
|
||||
A() {
|
||||
std::cout << "construct: " << ++g_constructCount << std::endl;
|
||||
}
|
||||
|
||||
A(const A &a) {
|
||||
std::cout << "copy construct: " << ++g_copy_constructCount << std::endl;
|
||||
}
|
||||
|
||||
~A() {
|
||||
std::cout << "destruct: " << ++g_destructCount << std::endl;
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
A getA() {
|
||||
return A{};
|
||||
}
|
||||
|
||||
|
||||
template<typename T>
|
||||
struct GetLeftSize : std::integral_constant<int, 10> {
|
||||
|
||||
};
|
||||
|
||||
template<typename ... T>
|
||||
void f(T ... args) {
|
||||
std::cout << sizeof...(args) << std::endl;
|
||||
}
|
||||
|
||||
|
||||
template<typename ... T>
|
||||
void expand(T ... args) {
|
||||
std::initializer_list<int>{(std::cout << args << std::endl, 0)...};
|
||||
}
|
||||
|
||||
template<typename F, typename Arg>
|
||||
auto Func(F f, Arg arg) -> decltype(f(arg)) {
|
||||
return f(arg);
|
||||
}
|
||||
|
||||
|
||||
template<typename Fn, typename Arg>
|
||||
auto GroupBy(const std::vector<Arg> &vt, Fn &&keySelector)
|
||||
-> std::multimap<decltype(keySelector((Arg & )
|
||||
|
||||
nullptr)), Arg>
|
||||
{
|
||||
typedef decltype(keySelector(*(Arg * ) nullptr))
|
||||
key_type;
|
||||
std::multimap<key_type, Arg> map;
|
||||
std::for_each(vt
|
||||
.
|
||||
|
||||
begin(), vt
|
||||
|
||||
.
|
||||
|
||||
end(),
|
||||
|
||||
[&](
|
||||
const Arg &arg
|
||||
){
|
||||
map.
|
||||
insert(make_pair(keySelector(arg), arg)
|
||||
);
|
||||
});
|
||||
return
|
||||
map;
|
||||
}
|
||||
|
||||
std::mutex g_lock;
|
||||
|
||||
void func() {
|
||||
std::lock_guard<std::mutex> locker(g_lock);
|
||||
std::this_thread::sleep_for(std::chrono::seconds(2));
|
||||
}
|
||||
|
||||
#include "sync_queue.h"
|
||||
void sync_test(){
|
||||
// 同步队列
|
||||
auto queue = new SyncQueue<int>(3);
|
||||
|
||||
// 每2秒取出进行消费
|
||||
std::thread producer([&](){
|
||||
int i = 0;
|
||||
while (i < 9){
|
||||
queue->dequeue(i);
|
||||
std::this_thread::sleep_for(std::chrono::seconds(2));
|
||||
std::cout << "dequeue: " << i << std::endl;
|
||||
}
|
||||
});
|
||||
|
||||
// 持续写入
|
||||
std::thread consumer([&](){
|
||||
for (int i = 0; i < 10; ++i) {
|
||||
queue->enqueue(i);
|
||||
std::cout << "enqueue: " << i << std::endl;
|
||||
}
|
||||
});
|
||||
|
||||
producer.join();
|
||||
consumer.join();
|
||||
}
|
||||
|
||||
|
||||
#include <chrono>
|
||||
#include <iomanip>
|
||||
#include "stop_watch.h"
|
||||
|
||||
void chrono_test(){
|
||||
|
||||
StopWatch stopWatch;
|
||||
|
||||
std::chrono::minutes t1(10);
|
||||
std::chrono::seconds t2(60);
|
||||
std::chrono::seconds t3 = t1 - t2;
|
||||
std::cout << "duration time: " << t3.count() << std::endl;
|
||||
|
||||
std::cout << "\ncost time: " << stopWatch.elapsed<std::chrono::microseconds>() << " us\n" << std::endl;
|
||||
|
||||
std::chrono::system_clock::time_point now = std::chrono::system_clock::now();
|
||||
// 将 time_point 转为 ctime
|
||||
std::time_t last = std::chrono::system_clock::to_time_t(now - std::chrono::hours(24));
|
||||
std::time_t next = std::chrono::system_clock::to_time_t(now + std::chrono::hours (24));
|
||||
|
||||
// 使用put_time格式化时间
|
||||
std::cout
|
||||
<< "One day ago, the time was "
|
||||
<< std::put_time(std::localtime(&last), "%F %T")
|
||||
<< "\n"
|
||||
<< "NExt day ago, the time is "
|
||||
<< std::put_time(std::localtime(&next), "%F %T")
|
||||
|
||||
<< std::endl;
|
||||
|
||||
std::cout << "\ncost time: " << stopWatch.elapsed() << " ms\n" << std::endl;
|
||||
|
||||
}
|
||||
|
||||
#include "thread_pool.h"
|
||||
void thread_test(){
|
||||
ThreadPool pool(3,10);
|
||||
|
||||
std::thread t0([&pool]{
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
auto thdId = std::this_thread::get_id();
|
||||
pool.add([thdId]{
|
||||
std::cout << "thread 1 id:" << thdId << std::endl;
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
std::thread t1([&pool]{
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
auto thdId = std::this_thread::get_id();
|
||||
pool.add([thdId]{
|
||||
std::cout << "thread 2 id:" << thdId << std::endl;
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
std::this_thread::sleep_for(std::chrono::seconds(2));
|
||||
// getchar();
|
||||
|
||||
pool.stop();
|
||||
t0.join();
|
||||
t1.join();
|
||||
}
|
||||
|
||||
|
||||
#include "aspect/aspect.h"
|
||||
#include "test/time_elapsed_aspect.h"
|
||||
#include "test/log_aspect.h"
|
||||
void HT(int a)
|
||||
{
|
||||
std::cout << "real HT function " << a << std::endl;
|
||||
}
|
||||
void aop_test(){
|
||||
using namespace std;
|
||||
|
||||
aop<LogAspect, TimeElapsedAspect>([](int a){
|
||||
std::thread t([a](){
|
||||
std::this_thread::sleep_for(std::chrono::seconds(1));
|
||||
std::cout << "run function, arg is " << a << std::endl;
|
||||
});
|
||||
t.join();
|
||||
}, 1);
|
||||
|
||||
cout << endl;
|
||||
|
||||
std::function<void(int)> f = std::bind(&HT, std::placeholders::_1);
|
||||
aop<LogAspect>(f, 100);
|
||||
}
|
||||
|
||||
int main() {
|
||||
// 同步队列测试
|
||||
// sync_test();
|
||||
// 时间工具测试
|
||||
// chrono_test();
|
||||
// 线程池测试
|
||||
// thread_test();
|
||||
// AOP测试
|
||||
aop_test();
|
||||
|
||||
|
||||
// auto start = std::chrono::duration_cast<std::chrono::milliseconds>(
|
||||
// std::chrono::system_clock::now().time_since_epoch()).count();
|
||||
// std::cout << "start time: " << start / 1000 << std::endl;
|
||||
// std::thread t0(func);
|
||||
// std::thread t1(func);
|
||||
// std::thread t2(func);
|
||||
// t0.join(); // 阻塞执行
|
||||
// t1.detach(); // 分离线程何对象,之后就无法何线程发送联系
|
||||
// t2.join();
|
||||
// auto end = std::chrono::duration_cast<std::chrono::milliseconds>(
|
||||
// std::chrono::system_clock::now().time_since_epoch()).count();
|
||||
// std::cout << " end time: " << end / 1000 << std::endl;
|
||||
|
||||
// A&& a = getA();
|
||||
//
|
||||
// expand(1,2,3,4);
|
||||
//
|
||||
// std::cout << GetLeftSize<int>::value << std::endl;
|
||||
//
|
||||
// f();
|
||||
// f(1);
|
||||
// f(1,2.5,"");
|
||||
//
|
||||
// foreach();
|
||||
|
||||
return 0;
|
||||
}
|
@ -0,0 +1,32 @@
|
||||
|
||||
#ifndef CPP_START_STOP_WATCH_H
|
||||
#define CPP_START_STOP_WATCH_H
|
||||
|
||||
#include <chrono>
|
||||
|
||||
|
||||
class StopWatch {
|
||||
|
||||
private:
|
||||
|
||||
std::chrono::time_point<std::chrono::high_resolution_clock> mBegin;
|
||||
|
||||
public:
|
||||
StopWatch() : mBegin(std::chrono::high_resolution_clock::now()) {
|
||||
|
||||
}
|
||||
|
||||
void reset() {
|
||||
mBegin = std::chrono::high_resolution_clock::now();
|
||||
}
|
||||
|
||||
template<typename Duration=std::chrono::milliseconds>
|
||||
int64_t elapsed() const {
|
||||
return std::chrono::duration_cast<Duration>(std::chrono::high_resolution_clock::now() - mBegin)
|
||||
.count();
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
|
||||
#endif //CPP_START_STOP_WATCH_H
|
@ -0,0 +1,20 @@
|
||||
|
||||
#ifndef CPP_START_LOG_ASPECT_H
|
||||
#define CPP_START_LOG_ASPECT_H
|
||||
|
||||
#include <iostream>
|
||||
|
||||
class LogAspect {
|
||||
|
||||
public:
|
||||
void before(int i) {
|
||||
std::cout << "log info: before: " << i << std::endl;
|
||||
}
|
||||
|
||||
void after(int i) {
|
||||
std::cout << "log info: after: " << i << std::endl;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
#endif //CPP_START_LOG_ASPECT_H
|
@ -0,0 +1,23 @@
|
||||
|
||||
#ifndef CPP_START_TIME_ELAPSED_ASPECT_H
|
||||
#define CPP_START_TIME_ELAPSED_ASPECT_H
|
||||
|
||||
#include <iostream>
|
||||
#include "../stop_watch.h"
|
||||
|
||||
class TimeElapsedAspect {
|
||||
private:
|
||||
StopWatch mStopWatch;
|
||||
public:
|
||||
|
||||
void before(int a) {
|
||||
mStopWatch.reset();
|
||||
}
|
||||
|
||||
void after(int a) {
|
||||
std::cout << "cost time : " << mStopWatch.elapsed() << " ms" << std::endl;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
#endif //CPP_START_TIME_ELAPSED_ASPECT_H
|
@ -0,0 +1,88 @@
|
||||
|
||||
#ifndef CPP_START_THREAD_POOL_H
|
||||
#define CPP_START_THREAD_POOL_H
|
||||
|
||||
#include <list>
|
||||
#include <thread>
|
||||
#include <memory>
|
||||
#include <atomic>
|
||||
#include <functional>
|
||||
#include "sync_queue.h"
|
||||
|
||||
class ThreadPool {
|
||||
|
||||
using Task = std::function<void()>;
|
||||
|
||||
private:
|
||||
|
||||
// 线程组
|
||||
std::list<std::shared_ptr<std::thread>> mThreadGroup;
|
||||
|
||||
// 任务队列
|
||||
SyncQueue<Task> mQueue;
|
||||
|
||||
// 运行状态
|
||||
std::atomic_bool mRunning;
|
||||
|
||||
// 标识
|
||||
std::once_flag mFlag;
|
||||
|
||||
private:
|
||||
|
||||
void init(int numThreads) {
|
||||
mRunning = true;
|
||||
for (int i = 0; i < numThreads; ++i) {
|
||||
mThreadGroup.push_back(std::make_shared<std::thread>(&ThreadPool::run, this));
|
||||
}
|
||||
}
|
||||
|
||||
void run() {
|
||||
while (mRunning) {
|
||||
std::list<Task> tasks;
|
||||
mQueue.dequeue(tasks);
|
||||
|
||||
for (auto &task: tasks) {
|
||||
if (!mRunning) {
|
||||
return;
|
||||
}
|
||||
task();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void stopThreadGroup() {
|
||||
mQueue.stop();
|
||||
mRunning = false;
|
||||
for (const auto &thread: mThreadGroup) {
|
||||
if (thread) {
|
||||
thread->join();
|
||||
}
|
||||
}
|
||||
mThreadGroup.clear();
|
||||
}
|
||||
|
||||
public:
|
||||
ThreadPool(int numThreads = std::thread::hardware_concurrency(), int maxTask = 1000) :
|
||||
mQueue(maxTask) {
|
||||
init(numThreads);
|
||||
}
|
||||
|
||||
~ThreadPool() {
|
||||
stop();
|
||||
}
|
||||
|
||||
void stop() {
|
||||
std::call_once(mFlag, [this] { stopThreadGroup(); });
|
||||
}
|
||||
|
||||
void add(Task &&task) {
|
||||
mQueue.enqueue(std::forward<Task>(task));
|
||||
}
|
||||
|
||||
void add(const Task &task) {
|
||||
mQueue.enqueue(task);
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
#endif //CPP_START_THREAD_POOL_H
|
Loading…
Reference in new issue