当前位置: 首页 > news >正文

使用Boost实现一个线程安全的map

肯定还是成熟的库更合适

# Thread-Safe Ordered Map in BoostUnfortunately, **Boost does not provide a built-in thread-safe ordered container** like `std::map`. Here's the breakdown:## What Boost Offers| Container | Thread-Safe | Ordered |
|-----------|-------------|---------|
| `boost::concurrent_flat_map` (1.83+) | ✅ | ❌ (hash-based) |
| `boost::container::flat_map` | ❌ | ✅ |
| `boost::multi_index_container` | ❌ | ✅ |## Recommended Solution: Wrap `std::map` with `boost::shared_mutex`For an order book where you need **ordering** (bids descending, asks ascending), the practical approach is to use a synchronized wrapper:```cpp
#include <boost/thread/shared_mutex.hpp>
#include <boost/thread/lock_types.hpp>
#include <map>
#include <functional>
#include <optional>template<typename Key, typename Value, typename Compare = std::less<Key>>
class ThreadSafeOrderedMap {
private:mutable boost::shared_mutex m_mutex;std::map<Key, Value, Compare> m_map;public:// Write operations - exclusive lockvoid insert(const Key& key, const Value& value) {boost::unique_lock<boost::shared_mutex> lock(m_mutex);m_map[key] = value;}bool erase(const Key& key) {boost::unique_lock<boost::shared_mutex> lock(m_mutex);return m_map.erase(key) > 0;}// Read operations - shared lockstd::optional<Value> find(const Key& key) const {boost::shared_lock<boost::shared_mutex> lock(m_mutex);auto it = m_map.find(key);if (it != m_map.end()) {return it->second;}return std::nullopt;}bool contains(const Key& key) const {boost::shared_lock<boost::shared_mutex> lock(m_mutex);return m_map.find(key) != m_map.end();}bool empty() const {boost::shared_lock<boost::shared_mutex> lock(m_mutex);return m_map.empty();}size_t size() const {boost::shared_lock<boost::shared_mutex> lock(m_mutex);return m_map.size();}// Get first element (best bid/ask)std::optional<std::pair<Key, Value>> front() const {boost::shared_lock<boost::shared_mutex> lock(m_mutex);if (m_map.empty()) return std::nullopt;return *m_map.begin();}// Atomic read-modify-write operationstemplate<typename Func>bool modify(const Key& key, Func&& func) {boost::unique_lock<boost::shared_mutex> lock(m_mutex);auto it = m_map.find(key);if (it != m_map.end()) {func(it->second);return true;}return false;}// Get or create entry atomicallytemplate<typename Func>void getOrInsertAndModify(const Key& key, Func&& func) {boost::unique_lock<boost::shared_mutex> lock(m_mutex);func(m_map[key]);}// Remove if condition is met (e.g., empty price level)template<typename Predicate>bool eraseIf(const Key& key, Predicate&& pred) {boost::unique_lock<boost::shared_mutex> lock(m_mutex);auto it = m_map.find(key);if (it != m_map.end() && pred(it->second)) {m_map.erase(it);return true;}return false;}// Iterate with shared lock (for snapshots)template<typename Func>void forEach(Func&& func) const {boost::shared_lock<boost::shared_mutex> lock(m_mutex);for (const auto& [key, value] : m_map) {func(key, value);}}// Get snapshot of top N levelsstd::vector<std::pair<Key, Value>> getTopN(size_t n) const {boost::shared_lock<boost::shared_mutex> lock(m_mutex);std::vector<std::pair<Key, Value>> result;result.reserve(std::min(n, m_map.size()));size_t count = 0;for (const auto& entry : m_map) {if (count++ >= n) break;result.push_back(entry);}return result;}
};

Updated Order Book Implementation

#include <cstdint>// Your existing structs (unchanged)
struct SpecificOrder {uint64_t orderId;uint64_t price;uint64_t volume;int side;int updateTime;bool isValid;SpecificOrder() : orderId(0), price(0), volume(0), side(0), updateTime(0), isValid(false) {}SpecificOrder(uint64_t id, uint64_t p, uint64_t vol, int s, int time): orderId(id), price(p), volume(vol), side(s), updateTime(time), isValid(true) {}
};struct PriceLevel {uint64_t price;uint64_t totalVolume;std::map<uint64_t, SpecificOrder> orders;PriceLevel() : price(0), totalVolume(0) {}void AddOrder(const SpecificOrder& order) {orders[order.orderId] = order;totalVolume += order.volume;}bool RemoveOrder(uint64_t orderId, uint64_t& removedVolume) {auto it = orders.find(orderId);if (it != orders.end()) {removedVolume = it->second.volume;totalVolume -= removedVolume;orders.erase(it);return true;}return false;}bool UpdateOrder(uint64_t orderId, uint64_t newVolume) {auto it = orders.find(orderId);if (it != orders.end()) {uint64_t oldVolume = it->second.volume;it->second.volume = newVolume;totalVolume = totalVolume - oldVolume + newVolume;return true;}return false;}bool Empty() const { return orders.empty(); }
};// Thread-safe order book
class OrderBook {
private:// Bids: descending order (highest price first)ThreadSafeOrderedMap<uint64_t, PriceLevel, std::greater<uint64_t>> m_bids;// Asks: ascending order (lowest price first)ThreadSafeOrderedMap<uint64_t, PriceLevel, std::less<uint64_t>> m_asks;public:void AddOrder(const SpecificOrder& order) {auto& book = (order.side == 0) ? m_bids : m_asks;  // 0 = buy, 1 = sellbook.getOrInsertAndModify(order.price, [&](PriceLevel& level) {level.price = order.price;level.AddOrder(order);});}bool RemoveOrder(uint64_t price, uint64_t orderId, int side) {auto& book = (side == 0) ? m_bids : m_asks;uint64_t removedVolume = 0;bool removed = book.modify(price, [&](PriceLevel& level) {level.RemoveOrder(orderId, removedVolume);});// Clean up empty price levelsif (removed) {book.eraseIf(price, [](const PriceLevel& level) {return level.Empty();});}return removed;}bool UpdateOrder(uint64_t price, uint64_t orderId, uint64_t newVolume, int side) {auto& book = (side == 0) ? m_bids : m_asks;return book.modify(price, [&](PriceLevel& level) {level.UpdateOrder(orderId, newVolume);});}// Get best bid (highest buy price)std::optional<PriceLevel> GetBestBid() const {auto result = m_bids.front();return result ? std::optional<PriceLevel>(result->second) : std::nullopt;}// Get best ask (lowest sell price)std::optional<PriceLevel> GetBestAsk() const {auto result = m_asks.front();return result ? std::optional<PriceLevel>(result->second) : std::nullopt;}// Get market depth snapshotstd::pair<std::vector<std::pair<uint64_t, PriceLevel>>,std::vector<std::pair<uint64_t, PriceLevel>>> GetDepth(size_t levels) const {return {m_bids.getTopN(levels), m_asks.getTopN(levels)};}
};

Alternative: High-Performance Options

If you need higher performance for HFT-style order books:

Library Container Notes
Intel TBB tbb::concurrent_map Ordered, concurrent, skip-list based
libcds cds::container::SkipListMap Lock-free ordered map
folly folly::ConcurrentSkipList Facebook's high-perf skip list
// Example with Intel TBB (if you're open to non-Boost)
#include <tbb/concurrent_map.h>tbb::concurrent_map<uint64_t, PriceLevel, std::greater<uint64_t>> m_bids;
tbb::concurrent_map<uint64_t, PriceLevel> m_asks;

Summary

Bottom line: For a thread-safe ordered map from Boost, use std::map + boost::shared_mutex as shown above. This provides:

  • ✅ Maintained ordering (ascending/descending)
  • ✅ Thread-safe concurrent access
  • ✅ Reader-writer lock efficiency (multiple readers, single writer)
  • ✅ Atomic compound operations via lambdas
http://www.jsqmd.com/news/59467/

相关文章:

  • 2025年湖南景区卖票软件公司权威推荐榜单:景点票务软件‌/智慧旅游软件‌/景区软件‌源头公司精选
  • AI数据标注平台获资,详解其技术架构与功能
  • 2025深圳英国留学中介机构
  • 2025去英国哪个留学中介好
  • 2025 年 12 月卷包机厂家推荐排行榜:全自动床垫/棉被/枕头压缩卷包机,高效便捷的家居包装解决方案!
  • linux查看cpu核心数的命令,方便人类查看
  • 2025年自行走升降机价格源头厂家权威推荐榜单:自行走四桅柱升降机‌/自行走升降机室内‌/自行走升降机‌源头厂家精选
  • 2025 年 12 月面巾纸折叠机/擦手纸折叠机/棉柔巾折叠机厂家推荐排行榜,高效稳定与智能设计的行业首选!
  • 2025年梵尼诗留声机品牌权威推荐榜单:万元音响/万元音箱品牌/万元级礼物品牌精选
  • 三环级联控制的理想采样率
  • 2025年蜂窝斜管填料品牌制造商TOP5榜单,专业解析与选购
  • 2025年国内营销咨询公司排名推荐:营销咨询公司哪家合适?
  • 2025 费用管理系统选型:核心维度对比,避开流程繁琐 的坑
  • Avalonia MenuItem:pointerover setting foreground color
  • 洛谷 P1922:女仆咖啡厅桌游吧 ← 树形DP
  • VNA专用高频测试电缆定制方案与技术应用指南
  • 2025年本地的风机盘管出风箱/风机盘管分风箱厂家最新权威推荐排行榜
  • PbootCMS网站获取指定栏目下面所有单页内容办法(PbootCMS 获取栏目下所有单页内容的方法与代码示例)
  • 2025去英国留学哪个中介好
  • 2025年五大生物绳填料供应商排行榜,生物绳填料定制品牌商新
  • 2025宁波英国留学中介有哪些
  • 2025宁波英国留学中介哪个好
  • 2025年重庆AI搜索排名品牌企业推荐:看看哪家服务性价比高
  • 2025南京英国留学中介排名
  • 完整教程:Mamba YOLO: 基于状态空间模型的目标检测简单基线
  • linux三剑客-awk实战组合用法
  • 口碑不错的吐司连续切片机生产厂家推荐
  • 开放式厨房绝配!2025年油烟吸力表现卓越的十大集成灶品牌权威推荐
  • 题解:Kuangyeyes Random Number
  • LightRAG:图增强检索框架,索引速度提升10倍