Explorar el Código

测试版优化

JiahengHe hace 2 años
padre
commit
f2e525fc87
Se han modificado 3 ficheros con 83 adiciones y 46 borrados
  1. 5 0
      global/src/params.rs
  2. 65 39
      strategy/src/predictor_new.rs
  3. 13 7
      strategy/src/quant.rs

+ 5 - 0
global/src/params.rs

@@ -49,6 +49,11 @@ pub struct Params {
     pub log_level: String,
     // 中控端口
     pub port: u32,
+
+    pub max_spread: Decimal,
+    pub min_spread: Decimal,
+    pub rl_num: Decimal,
+    pub max_position_value: Decimal
 }
 
 impl Params {

+ 65 - 39
strategy/src/predictor_new.rs

@@ -15,12 +15,15 @@ pub struct PredictorNew {
     pub alpha: Vec<Decimal>,                                            // 价格系数
     pub gamma: Decimal,                                                 // 定价系数
     pub avg_spread_list: Vec<Decimal>,                                  // 平均价差
-
-    pub transaction_prices: Vec<Decimal>,                               // 成交价记录
-    pub max_spread: f64,                                                // 最大点差
-    pub min_spread: f64,                                                // 最小点差
-    pub variance: f64,                                                  // 波动率
-    pub balance_value: f64                                              // 持仓价值
+//
+    pub transaction_prices: Vec<Decimal>,                                   // 中间价记录
+    pub variance: Decimal,                                                  // 波动率
+    pub balance_value: Decimal,                                             // 持仓价值
+// 手动输入
+    pub max_spread: Decimal,                                                // 最大点差
+    pub min_spread: Decimal,                                                // 最小点差
+    pub rl_num: Decimal,                                                    // 取价坐标
+    pub max_position_value: Decimal                                         // 最大持仓(u)
 }
 
 /*
@@ -28,7 +31,7 @@ pub struct PredictorNew {
     下面的单元测试有使用示例
 */
 impl PredictorNew {
-    pub fn new(ref_exchange_length: usize) -> Self {
+    pub fn new(ref_exchange_length: usize, max_spread: Decimal, min_spread: Decimal, rl_num: Decimal, max_position_value: Decimal) -> Self {
         Self {
             loop_count: 0,
             market_info_list: vec![],
@@ -40,10 +43,12 @@ impl PredictorNew {
             gamma: Decimal::from_f64(0.999).unwrap(),
             avg_spread_list: vec![dec!(0); ref_exchange_length],
             transaction_prices: Vec::new(),
-            max_spread: Default::default(),
-            min_spread: Default::default(),
-            variance: 0.0,
-            balance_value: 0.0,
+            max_spread,
+            min_spread,
+            variance: Decimal::ZERO,
+            balance_value: Decimal::ZERO,
+            rl_num,
+            max_position_value
         }
     }
 
@@ -91,46 +96,63 @@ impl PredictorNew {
     }
 
     /**
-        波动率计算(根据最近成交价)
+        波动率计算(根据最近成交价,EWMA波动率算法
     **/
     pub fn update_std(&mut self) {
+        let gamma = self.gamma.to_f64().unwrap();
+        // 如果程序刚刚启动,gamma值不能太大
+        // if self.loop_count < 100 {
+        //     gamma = 0.9f64;
+        // }
         let len = self.transaction_prices.len();
         let rtn:f64 = (self.transaction_prices[len - 1].to_f64().unwrap() / self.transaction_prices[len - 2].to_f64().unwrap()).ln();
-        let result: f64 = self.gamma.to_f64().unwrap() * rtn.powf(2.0) + (1f64 - self.gamma.to_f64().unwrap()) * self.variance.to_f64().unwrap();
-        self.variance = result.sqrt();
+        let result: f64 = gamma * rtn.powf(2.0) + (1f64 - gamma) * self.variance.to_f64().unwrap();
+        self.variance = Decimal::from_f64(result.sqrt()).unwrap();
     }
 
     /**
        计算gamma值
     **/
-    pub fn calc_gamma(&mut self) -> f64 {
-        self.max_spread / 2f64 * self.balance_value * self.variance * self.variance
+    pub fn calc_gamma(&mut self, ira: Decimal) -> Decimal {
+        self.max_spread / Decimal::TWO * self.balance_value * self.variance * self.variance * ira
+    }
+
+    /**
+       计算价格偏差范围
+    **/
+    pub fn calc_deviation_range(&mut self, ira: Decimal) -> Decimal {
+        return (self.rl_num - ira) * self.max_spread + ira * self.min_spread;
     }
 
     /**
        计算预定价格
     **/
-    pub fn calc_rp(&mut self, gamma: &f64) -> f64{
+    pub fn calc_rp(&mut self, gamma: &Decimal) -> Decimal{
         let last_market_info = self.market_info_list.last().unwrap();
         let ref_bid_price = last_market_info[public_params::LENGTH+public_params::BID_PRICE_INDEX];
         let ref_ask_price = last_market_info[public_params::LENGTH+public_params::ASK_PRICE_INDEX];
         let ref_mid_price = (ref_bid_price + ref_ask_price) * dec!(0.5);
-
-        ref_mid_price.to_f64().unwrap() - self.balance_value * gamma * self.variance * self.variance
+        println!("mid_price: {}", ref_mid_price);
+        ref_mid_price - self.balance_value * gamma * self.variance * self.variance
     }
 
-    pub fn calc_dk(&mut self, gamma: &f64) -> f64 {
-        return ((self.max_spread + self.min_spread)/2f64 * gamma - self.variance.powf(2f64) * gamma.powf(2f64)) / 2f64;
+    pub fn calc_dk(&mut self, gamma: &Decimal) -> Decimal {
+        return ((self.max_spread + self.min_spread)/Decimal::TWO * gamma - self.variance * self.variance * gamma * gamma) / Decimal::TWO;
     }
 
-    pub fn calc_kappa(&mut self, gamma: &f64, dk: f64) -> f64 {
-        return gamma / ( std::f64::consts::E.powf(dk) - 1f64);
+    pub fn calc_kappa(&mut self, gamma: &Decimal, dk: Decimal, deviation_range: Decimal) -> Decimal {
+        let e = std::f64::consts::E.powf(dk.to_f64().unwrap()) - 1f64;
+        gamma / Decimal::from_f64(e).unwrap() / deviation_range
     }
 
-    pub fn calc_theta(&mut self, gamma: f64, kappa: f64) -> f64 {
-        let a = gamma * self.variance.powf(2f64);
-        let b = 2f64 / gamma * (1f64 + gamma / kappa).ln();
-        (a + b) / 2f64
+    /**
+        计算价差
+    **/
+    pub fn calc_theta(&mut self, gamma: Decimal, kappa: Decimal) -> Decimal {
+        let a = gamma * self.variance * self.variance;
+        let ln = (Decimal::ONE + gamma / kappa).to_f64().unwrap().ln();
+        let b = Decimal::TWO / gamma * Decimal::from_f64(ln).unwrap();
+        (a + b) / Decimal::TWO
     }
 
     // 更新平均价差,_update_avg_spread
@@ -214,12 +236,15 @@ impl PredictorNew {
     // }
     pub fn get_ref_price(&mut self) -> Vec<Vec<Decimal>>{
         let mut ref_price_list = vec![];
-        let gamma = self.calc_gamma();
+        let ira = Decimal::from_str("5").unwrap();
+        let dd = self.calc_deviation_range(ira.clone());
+        let gamma = self.calc_gamma(ira);
         let rp = self.calc_rp(&gamma);
         let dk = self.calc_dk(&gamma);
-        let kappa = self.calc_kappa(&gamma, dk);
+        let kappa = self.calc_kappa(&gamma, dk, dd);
         let theta = self.calc_theta(gamma, kappa);
-        ref_price_list.push(vec![Decimal::from_f64(rp + theta).unwrap() , Decimal::from_f64(rp - theta).unwrap()]);
+        println!("gamma: {}, rp: {}, dk: {}, kappa: {}, theta: {}, std: {}", gamma, rp, dk, kappa, theta, self.variance);
+        ref_price_list.push(vec![rp + theta , rp - theta]);
         ref_price_list
     }
 }
@@ -230,6 +255,8 @@ mod tests {
     use std::collections::BTreeMap;
     use std::io;
     use std::io::Write;
+    use std::str::FromStr;
+    use rust_decimal::Decimal;
     use rust_decimal_macros::dec;
     use standard::Ticker;
     use crate::predictor_new::PredictorNew;
@@ -238,14 +265,14 @@ mod tests {
     fn predictor_build_test() {
         let mut stdout = io::stdout();
 
-        let predictor1 = PredictorNew::new(2)
+        let predictor1 = PredictorNew::new(2, Default::default(), Default::default(), Default::default())
             .alpha(vec![dec!(0.99); 100])
             .gamma(dec!(0.8));
         writeln!(stdout, "predictor1:").unwrap();
         writeln!(stdout, "{:?}", predictor1).unwrap();
         writeln!(stdout, "").unwrap();
 
-        let predictor2 = PredictorNew::new(2);
+        let predictor2 = PredictorNew::new(2, Default::default(), Default::default(), Default::default());
         writeln!(stdout, "predictor2:").unwrap();
         writeln!(stdout, "{:?}", predictor2).unwrap();
         writeln!(stdout, "").unwrap();
@@ -253,7 +280,7 @@ mod tests {
 
     #[test]
     fn market_info_handler_test() {
-        let mut predictor = PredictorNew::new(1);
+        let mut predictor = PredictorNew::new(1, Default::default(), Default::default(), Default::default());
         let market_info_0 = vec![dec!(0.99), dec!(1.0), dec!(0.89), dec!(0.79), dec!(0.99), dec!(1.0), dec!(0.89), dec!(0.79), dec!(0.89), dec!(0.79), dec!(0.99), dec!(1.0), dec!(0.89), dec!(0.79)];
         predictor.market_info_handler(&market_info_0);
         let market_info_1 = vec![dec!(0.98), dec!(0.99), dec!(0.56), dec!(0.49), dec!(0.99), dec!(1.0), dec!(0.89), dec!(0.79), dec!(0.89), dec!(0.79), dec!(0.99), dec!(1.0), dec!(0.89), dec!(0.79)];
@@ -262,12 +289,12 @@ mod tests {
 
     #[test]
     fn get_ref_price_test() {
-        let mut predictor = PredictorNew::new(1)
+        let mut predictor = PredictorNew::new(1, Default::default(), Default::default(), Default::default())
             .alpha(vec![dec!(0.99); 100])
             .gamma(dec!(0.8));
-        predictor.balance_value = 1f64;
-        predictor.max_spread = 0.1f64;
-        predictor.min_spread = 0.01f64;
+        predictor.balance_value = Decimal::from_str("0.5").unwrap();
+        predictor.max_spread = Decimal::from_str("0.5").unwrap();
+        predictor.min_spread = Decimal::from_str("0.01").unwrap();
         //
         let mut ref_ticker_map: BTreeMap<String, Ticker> = BTreeMap::new();
         ref_ticker_map.insert("binance".to_string(), Ticker{
@@ -281,8 +308,7 @@ mod tests {
         });
         // println!("before market info: {:?}", predictor.get_ref_price());
 
-        let mut market_info = vec![];
-        market_info = vec![dec!(0.99), dec!(1.0), dec!(0.991), dec!(0.79), dec!(0.99), dec!(1.0), dec!(0.89), dec!(0.79), dec!(0.89), dec!(0.79), dec!(0.99), dec!(1.0), dec!(0.89), dec!(0.79)];
+        let mut market_info= vec![dec!(0.99), dec!(1.0), dec!(0.991), dec!(0.79), dec!(0.99), dec!(1.0), dec!(0.89), dec!(0.79), dec!(0.89), dec!(0.79), dec!(0.99), dec!(1.0), dec!(0.89), dec!(0.79)];
         predictor.market_info_handler(&market_info);
         println!("market info 0: {:?}", predictor.get_ref_price());
         market_info = vec![dec!(0.98), dec!(0.99), dec!(0.981), dec!(0.49), dec!(0.99), dec!(1.0), dec!(0.89), dec!(0.79), dec!(0.89)];

+ 13 - 7
strategy/src/quant.rs

@@ -175,9 +175,11 @@ impl Quant {
                 avg_spread_list: vec![],
                 transaction_prices: vec![],
                 variance: Default::default(),
-                max_spread: Default::default(),
-                min_spread: 0.0,
-                balance_value: 0.0,
+                max_spread: Decimal::ZERO,
+                min_spread: Decimal::ZERO,
+                balance_value: Decimal::ZERO,
+                rl_num: Decimal::ZERO,
+                max_position_value: Decimal::ZERO
             },
             market: Market {
                 symbol: symbol.clone(),
@@ -272,7 +274,7 @@ impl Quant {
             }
         }
         info!("价格系数:{:?}", price_alpha);
-        quant_obj.predictor = PredictorNew::new(quant_obj.ref_name.len())
+        quant_obj.predictor = PredictorNew::new(quant_obj.ref_name.len(), params.max_spread, params.min_spread, params.rl_num, params.max_position_value)
             .alpha(price_alpha)
             .gamma(params.gamma);
 
@@ -684,11 +686,11 @@ impl Quant {
     }
 
     pub fn _update_ticker(&mut self, data: SpecialTicker, name: String) {
-        let spread = (data.buy - data.sell).to_f64().unwrap();
-        if spread > self.predictor.max_spread || self.predictor.max_spread == 0f64{
+        let spread = data.buy - data.sell;
+        if spread > self.predictor.max_spread || self.predictor.max_spread == Decimal::ZERO{
             self.predictor.max_spread = spread;
         }
-        if spread < self.predictor.min_spread || self.predictor.min_spread == 0f64{
+        if spread < self.predictor.min_spread || self.predictor.min_spread == Decimal::ZERO{
             self.predictor.min_spread = spread;
         }
         self.tickers.insert(name, data);
@@ -732,6 +734,10 @@ impl Quant {
                 volume: Default::default(),
             });
         }
+        let bp = self.trade_msg.market[BID_PRICE_INDEX];
+        let ap = self.trade_msg.market[ASK_PRICE_INDEX];
+        let mp = (bp + ap) * dec!(0.5);
+        self.predictor.balance_value = self.trade_msg.cash * mp;
         let ref_price: Vec<Vec<Decimal>> = self.predictor.get_ref_price();
         self.trade_msg.ref_price = ref_price;
     }