我正在建立一个市场,我想为市场参与者订单建立一个匹配机制。
例如我收到这些订单:
A buys 50
B buys 100
C sells 50
D sells 20
可以表示为List<Orders>
,其中Order
是包含Participant
,BuySell
和Amount
我想创建一个Match
函数,它输出两件事:
List<Order>
)List<MatchedOrder>
其中MatchOrder
有Buyer
,Seller
,Amount
约束是最小化订单数量(不匹配和匹配),同时不会撤消任何可能的匹配(即最终只能购买或卖出无与伦比的订单)
所以在上面的例子中,结果将是:
A buys 50 from C
B buys 20 from D
B buys 80 (outstanding)
这似乎是一个相当复杂的编写算法,但在实践中很常见。有什么指针可以看哪儿?
答案 0 :(得分:0)
您可以将其建模为二分图中的流问题。每个销售节点都在左侧,每个购买节点都在右侧。像这样:
然后,您必须找到可以从source
传递到sink
的最大流量。
您可以使用所需的任何最大流量算法,例如Ford Fulkerson。要最小化订单数,您可以使用最大流量/最小成本算法。有许多技术可以做到这一点,包括在找到正常的MaxFlow解决方案后应用循环取消。
运行算法后,您可能会有以下残留网络:
答案 1 :(得分:0)
WithRemainingQuantity
结构:订单的pointeur o
和存储不匹配数量的整数List<WithRemainingQuantity>
,1个用于购买Bq,1个用于销售Sq,均按包含订单的降序排序。Algo(meta和c ++的混合):
struct WithRemainingQuantity
{
Order * o;
int remainingQty; // initialised with o->getQty
}
struct MatchedOrder
{
Order * orderBuy;
Order * orderSell;
int matchedQty=0;
}
List<WithRemainingQuantity> Bq;
List<WithRemainingQuantity> Sq;
/*
populate Bq and Sq and sort by quantities descending,
this is what guarantees the minimum of matched.
*/
List<MatchedOrder> l;
while( ! Bq.empty && !Sq.empty)
{
int matchedQty = std::min(Bq.front().remainingQty, Sq.front().remainingQty)
l.push_back( MatchedOrder(orderBuy=Bq.front(), sellOrder=Sq.front(), qtyMatched=matchedQty) )
Bq.remainingQty -= matchedQty
Sq.remainingQty -= matchedQty
if(Bq.remainingQty==0)
Bq.pop_front()
if(Sq.remainingQty==0)
Sq.pop_front()
}
不匹配的订单是Bq或Sq中的剩余订单(根据while
条款,其中一个订单是致命空的。)