集合订单拆单算法参考

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
#!/usr/bin/env python
# -*- coding: utf-8 -*-
# author: Nio.Ou time:2020/2/11
import pandas as pd
pd.set_option('expand_frame_repr', False)


def distribute(total, precision_digits):
def _dist(x):
rets = []
left = total
for w in x:
k = round(left * w, precision_digits)
left -= k
rets.append(k)
return rets # pd.Series(rets)

return _dist


def allocate_get_quantity_by_amount(order_df, confirm, quantity_precision_digits=5, cash_precision_digits=2):
alloc_df = order_df.copy()
# 先根据申请金额比例分配成本
alloc_df['rest_sum'] = alloc_df['amount'].sum() - alloc_df['amount'].cumsum() + alloc_df['amount']
alloc_df['rest_weight'] = alloc_df['amount'] / alloc_df['rest_sum']
alloc_df['final_amount'] = alloc_df['rest_weight'].agg(distribute(confirm['final_amount'], cash_precision_digits),
axis=0)
# 再根据成本比例分配份额
alloc_df['cost_rest_sum'] = alloc_df['final_amount'].sum() - alloc_df['final_amount'].cumsum() + alloc_df['final_amount']
alloc_df['cost_rest_weight'] = alloc_df['final_amount'] / alloc_df['cost_rest_sum']
alloc_df['final_quantity'] = alloc_df['cost_rest_weight'].agg(distribute(confirm['quantity'], quantity_precision_digits),
axis=0)
alloc_df['mktValue - final_amount'] = alloc_df['final_quantity'] * confirm['nav'] - alloc_df['final_amount']
alloc_df['mktValue - request_amount'] = alloc_df['final_quantity'] * confirm['nav'] - alloc_df['amount']

return alloc_df


def allocate_get_amount_by_quantity(order_df, confirm, quantity_precision_digits=5, cash_precision_digits=2):
alloc_df = order_df.copy()
# 先根据request quantity比例分配final quantity
alloc_df['rest_sum'] = alloc_df['quantity'].sum() - alloc_df['quantity'].cumsum() + alloc_df['quantity']
alloc_df['rest_weight'] = alloc_df['quantity'] / alloc_df['rest_sum']
alloc_df['final_quantity'] = alloc_df['rest_weight'].agg(
distribute(confirm['final_quantity'], quantity_precision_digits),
axis=0)
# 再根据final quantity 比例分配 final amount
alloc_df['cost_rest_sum'] = alloc_df['final_quantity'].sum() - alloc_df['final_quantity'].cumsum() + alloc_df[
'final_quantity']
alloc_df['cost_rest_weight'] = alloc_df['final_quantity'] / alloc_df['cost_rest_sum']
alloc_df['final_amount'] = alloc_df['cost_rest_weight'].agg(distribute(confirm['amount'], cash_precision_digits),
axis=0)
alloc_df['mktValue - final_amount'] = alloc_df['final_quantity'] * confirm['nav'] - alloc_df['final_amount']
alloc_df['mktValue - request_amount'] = alloc_df['quantity'] * confirm['nav'] - alloc_df['final_amount']
return alloc_df


def allocate_get_amount_by_amount(order_df, confirm, quantity_precision_digits=5, cash_precision_digits=2):
alloc_df = order_df.copy()
# 先根据request amount比例分配final amount
alloc_df['rest_sum'] = alloc_df['amount'].sum() - alloc_df['amount'].cumsum() + alloc_df['amount']
alloc_df['rest_weight'] = alloc_df['amount'] / alloc_df['rest_sum']
alloc_df['final_amount'] = alloc_df['rest_weight'].agg(distribute(confirm['amount'], cash_precision_digits),
axis=0)
# 再根据final amount 比例分配 final quantity
alloc_df['cost_rest_sum'] = alloc_df['final_amount'].sum() - alloc_df['final_amount'].cumsum() + alloc_df[
'final_amount']
alloc_df['cost_rest_weight'] = alloc_df['final_amount'] / alloc_df['cost_rest_sum']
alloc_df['final_quantity'] = alloc_df['cost_rest_weight'].agg(
distribute(confirm['final_quantity'], quantity_precision_digits),
axis=0)
alloc_df['mktValue - final_amount'] = alloc_df['final_quantity'] * confirm['nav'] - alloc_df['final_amount']
alloc_df['mktValue - request_amount'] = alloc_df['final_quantity'] * confirm['nav'] - alloc_df['amount']
return alloc_df


def allocate_get_quantity_by_quantity(order_df, confirm, quantity_precision_digits=5):
alloc_df = order_df.copy()
# 根据份额占比获取分配的份额
alloc_df['rest_sum'] = alloc_df['quantity'].sum() - alloc_df['quantity'].cumsum() + alloc_df['quantity']
alloc_df['rest_weight'] = alloc_df['quantity'] / alloc_df['rest_sum']
alloc_df['final_quantity'] = alloc_df['rest_weight'].agg(distribute(confirm['quantity'], quantity_precision_digits),
axis=0)
return alloc_df

def allocate_get_amount_by_weight(order_df, confirm, cash_precision_digits=2):
alloc_df = order_df.copy()
# 根据份额占比获取分配的份额
alloc_df['rest_sum'] = alloc_df['weight'].sum() - alloc_df['weight'].cumsum() + alloc_df['weight']
alloc_df['rest_weight'] = alloc_df['weight'] / alloc_df['rest_sum']
alloc_df['final_amount'] = alloc_df['rest_weight'].agg(distribute(confirm['amount'], cash_precision_digits),
axis=0)
return alloc_df


if __name__ == '__main__':
orders = [
{"amount": 209.83},
{"amount": 215.11},
{"amount": 213.70},
{"amount": 448.85},
]
confirm = {
"nav": 105.380000,
"request_amount": 1087.49,
"final_amount": 1087.42,
"quantity": 10.319000
}
df = allocate_get_quantity_by_amount(pd.DataFrame(orders), confirm, 4)
print(df)

orders2 = [
{"quantity": 1.991},
{"quantity": 2.041},
{"quantity": 2.028},
{"quantity": 4.259},
]
confirm2 = {
"nav": 105.380000,
"request_quantity": 10.319,
"final_quantity": 10.319,
"amount": 1087.43
}
df2 = allocate_get_amount_by_quantity(pd.DataFrame(orders2), confirm2, 4)
print(df2)

orders3 = [
{"amount": 209.83},
{"amount": 215.11},
{"amount": 213.70},
{"amount": 448.85},
]
confirm3 = {
"nav": 105.380000,
"request_amount": 1087.49,
"final_quantity": 10.319,
"amount": 1087.42
}
df3 = allocate_get_amount_by_amount(pd.DataFrame(orders3), confirm3, 4)
print(df3)

orders4 = [
{"quantity": 209.8311},
{"quantity": 215.1123},
{"quantity": 213.7059},
{"quantity": 448.8538},
]
confirm4 = {
"quantity": (209.8311+215.1123+213.7059+448.8538) * 1.25
}
df = allocate_get_quantity_by_quantity(pd.DataFrame(orders4), confirm4, 4)
print(df)
print(df['quantity'].sum())
print(df['final_quantity'].sum())

orders5 = [
{"weight": 0.11},
{"weight": 0.23},
{"weight": 0.29},
{"weight": 0.37},
]
confirm5 = {
"amount": 123456.78
}
df = allocate_get_amount_by_weight(pd.DataFrame(orders5), confirm5, 2)
print(df)
print(df['final_amount'].sum())

集合订单拆单算法参考

https://blog.jiejaitt.top/posts/f6d6fc90.html

作者

JIeJaitt

发布于

2025-01-24

更新于

2025-01-24

许可协议

Your browser is out-of-date!

Update your browser to view this website correctly.&npsb;Update my browser now

×