Ejemplo n.º 1
0
        public ConfigInfo Double2Int(ConfigInfoView config)
        {
            if (config == null)
                return null;

            ConfigInfo field = new ConfigInfo();

            field.Version = config.Version;
            field.TickSize = config.TickSize;
            field.TickSizeMultiplier = config.TickSizeMultiplier;
            field.SettlementPriceMultiplier = config.SettlementPriceMultiplier;
            field.AveragePriceMultiplier = config.AveragePriceMultiplier;
            field.ContractMultiplier = config.ContractMultiplier;
            field.Time_ssf_Diff = config.Time_ssf_Diff;

            return field;
        }
Ejemplo n.º 2
0
        public ConfigInfo Double2Int(ConfigInfoView config)
        {
            if (config == null)
            {
                return(null);
            }

            var field = new ConfigInfo();

            field.Version                   = config.Version;
            field.TickSize                  = config.TickSize;
            field.TickSizeMultiplier        = config.TickSizeMultiplier;
            field.SettlementPriceMultiplier = config.SettlementPriceMultiplier;
            field.AveragePriceMultiplier    = config.AveragePriceMultiplier;
            field.ContractMultiplier        = config.ContractMultiplier;
            field.Time_ssf_Diff             = config.Time_ssf_Diff;

            return(field);
        }
Ejemplo n.º 3
0
        /// <summary>
        /// 传入两个tick得到tick的差分
        /// </summary>
        /// <param name="prev"></param>
        /// <param name="current"></param>
        /// <returns></returns>
        public PbTick Diff(PbTick prev, PbTick current)
        {
            if (prev == null)
            {
                if (current.Config == null)
                {
                    throw new Exception("快照的配置不能为空");
                }
                // 是快照,直接返回
                return(current);
            }

            PbTick tick = new PbTick();

            #region 配置数据
            // 当前数据为空或前后相同,表示
            if (current.Config == null || prev.Config.IsSame(current.Config))
            {
                tick.Config = null;
                // 可以继续下去
            }
            else
            {
                // 是新数据,返回快照
                _config  = current.Config;
                TickSize = _config.GetTickSize();

                return(current);
            }
            #endregion

            // 先取最关键的数据,因为前一条的config总会补成有效
            _config  = prev.Config;
            TickSize = _config.GetTickSize();

            tick.LastPrice = current.LastPrice - prev.LastPrice;

            DepthTick from_last = null;
            DepthTick from_next = null;
            DepthTick to_last   = null;
            DepthTick to_next   = null;

            DepthTick last_last = null;
            DepthTick last_next = null;

            #region 买1到买N
            from_last = null;
            from_next = current.Depth1_3;
            to_last   = null;
            to_next   = tick.Depth1_3;

            last_last = null;
            last_next = prev.Depth1_3;

            while (true)
            {
                // 如果下一步没有数据,直接跳过
                if (from_next == null)
                {
                    break;
                }

                // 每节的循环
                if (from_next.BidSize1 == 0)
                {
                    break;
                }

                // 如果没有上一笔,这个地方就比较特殊
                if (from_last == null)
                {
                    // 需要考察目标是否有数据
                    if (to_next == null)
                    {
                        to_next       = new DepthTick();
                        tick.Depth1_3 = to_next;
                    }
                    to_next.BidPrice1 = current.LastPrice - from_next.BidPrice1;
                }
                else
                {
                    // 需要考察目标是否有数据
                    if (to_next == null)
                    {
                        to_next      = new DepthTick();
                        to_last.Next = to_next;
                    }
                    to_next.BidPrice1 = from_last.BidPrice3 - from_next.BidPrice1 - 1;
                }
                if (last_next == null)
                {
                    to_next.BidSize1  = from_next.BidSize1;
                    to_next.BidCount1 = from_next.BidCount1;
                }
                else
                {
                    to_next.BidSize1  = from_next.BidSize1 - last_next.BidSize1;
                    to_next.BidCount1 = from_next.BidCount1 - last_next.BidCount1;
                }


                if (from_next.BidSize2 == 0)
                {
                    break;
                }
                to_next.BidPrice2 = from_next.BidPrice1 - from_next.BidPrice2 - 1;
                if (last_next == null)
                {
                    to_next.BidSize2  = from_next.BidSize2;
                    to_next.BidCount2 = from_next.BidCount2;
                }
                else
                {
                    to_next.BidSize2  = from_next.BidSize2 - last_next.BidSize2;
                    to_next.BidCount2 = from_next.BidCount2 - last_next.BidCount2;
                }


                if (from_next.BidSize3 == 0)
                {
                    break;
                }

                to_next.BidPrice3 = from_next.BidPrice2 - from_next.BidPrice3 - 1;
                if (last_next == null)
                {
                    to_next.BidSize3  = from_next.BidSize3;
                    to_next.BidCount3 = from_next.BidCount3;
                }
                else
                {
                    to_next.BidSize3  = from_next.BidSize3 - last_next.BidSize3;
                    to_next.BidCount3 = from_next.BidCount3 - last_next.BidCount3;
                }

                // 移动到下一个数据块
                from_last = from_next;
                from_next = from_next.Next;

                to_last = to_next;
                to_next = to_next.Next;

                last_last = last_next;
                if (last_next != null)
                {
                    last_next = last_next.Next;
                }
            }
            #endregion

            #region 卖1到卖N
            from_last = null;
            from_next = current.Depth1_3;
            to_last   = null;
            to_next   = tick.Depth1_3;

            last_last = null;
            last_next = prev.Depth1_3;

            while (true)
            {
                // 如果下一步没有数据,直接跳过
                if (from_next == null)
                {
                    break;
                }

                // 每节的循环
                if (from_next.AskSize1 == 0)
                {
                    break;
                }

                // 如果没有上一笔,这个地方就比较特殊
                if (from_last == null)
                {
                    // 需要考察目标是否有数据
                    if (to_next == null)
                    {
                        to_next       = new DepthTick();
                        tick.Depth1_3 = to_next;
                    }
                    to_next.AskPrice1 = from_next.AskPrice1 - current.LastPrice;
                }
                else
                {
                    // 需要考察目标是否有数据
                    if (to_next == null)
                    {
                        to_next      = new DepthTick();
                        to_last.Next = to_next;
                    }
                    to_next.AskPrice1 = from_next.AskPrice1 - from_last.AskPrice3 - 1;
                }
                if (last_next == null)
                {
                    to_next.AskSize1  = from_next.AskSize1;
                    to_next.AskCount1 = from_next.AskCount1;
                }
                else
                {
                    to_next.AskSize1  = from_next.AskSize1 - last_next.AskSize1;
                    to_next.AskCount1 = from_next.AskCount1 - last_next.AskCount1;
                }

                if (from_next.AskSize2 == 0)
                {
                    break;
                }
                to_next.AskPrice2 = from_next.AskPrice2 - from_next.AskPrice1 - 1;
                if (last_next == null)
                {
                    to_next.AskSize2  = from_next.AskSize2;
                    to_next.AskCount2 = from_next.AskCount2;
                }
                else
                {
                    to_next.AskSize2  = from_next.AskSize2 - last_next.AskSize2;
                    to_next.AskCount2 = from_next.AskCount2 - last_next.AskCount2;
                }


                if (from_next.AskSize3 == 0)
                {
                    break;
                }
                to_next.AskPrice3 = from_next.AskPrice3 - from_next.AskPrice2 - 1;
                if (last_next == null)
                {
                    to_next.AskSize3  = from_next.AskSize3;
                    to_next.AskCount3 = from_next.AskCount3;
                }
                else
                {
                    to_next.AskSize3  = from_next.AskSize3 - last_next.AskSize3;
                    to_next.AskCount3 = from_next.AskCount3 - last_next.AskCount3;
                }

                // 移动到下一个数据块
                from_last = from_next;
                from_next = from_next.Next;

                to_last = to_next;
                to_next = to_next.Next;

                last_last = last_next;
                if (last_next != null)
                {
                    last_next = last_next.Next;
                }
            }
            #endregion

            #region 常用行情信息
            tick.Volume       = current.Volume - prev.Volume;
            tick.OpenInterest = current.OpenInterest - prev.OpenInterest;
            tick.Turnover     = current.Turnover - prev.Turnover;
            tick.AveragePrice = current.AveragePrice - prev.AveragePrice;
            tick.TradingDay   = current.TradingDay - prev.TradingDay;
            tick.ActionDay    = current.ActionDay - prev.ActionDay;

            tick.Time_HHmm      = current.Time_HHmm - prev.Time_HHmm;
            tick.Time________ff = current.Time________ff - prev.Time________ff;
            // 这个地方有区别要减去一个差,将时间再缩小
            tick.Time_____ssf__ = current.Time_____ssf__ - prev.Time_____ssf__ - _config.Time_ssf_Diff;
            #endregion

            #region Bar数据
            // Bar数据要进行差分计算
            if (current.Bar != null || prev.Bar != null)
            {
                tick.Bar = new BarInfo();
                if (current.Bar == null)
                {
                    current.Bar = new BarInfo();
                }
                if (prev.Bar == null)
                {
                    prev.Bar = new BarInfo();
                }

                tick.Bar.Open    = current.Bar.Open - prev.Bar.Open;
                tick.Bar.High    = current.Bar.High - prev.Bar.High;
                tick.Bar.Low     = current.Bar.Low - prev.Bar.Low;
                tick.Bar.Close   = current.Bar.Close - prev.Bar.Close;
                tick.Bar.BarSize = current.Bar.BarSize - prev.Bar.BarSize;

                if (tick.Bar.IsZero)
                {
                    tick.Bar = null;
                }
            }
            #endregion

            #region 静态数据
            if (current.Static != null || prev.Static != null)
            {
                tick.Static = new StaticInfo();
                if (current.Static == null)
                {
                    current.Static = new StaticInfo();
                }
                if (prev.Static == null)
                {
                    prev.Static = new StaticInfo();
                }

                tick.Static.LowerLimitPrice = current.Static.LowerLimitPrice - prev.Static.LowerLimitPrice;
                tick.Static.UpperLimitPrice = current.Static.UpperLimitPrice - prev.Static.UpperLimitPrice;
                tick.Static.SettlementPrice = current.Static.SettlementPrice - prev.Static.SettlementPrice;

                if (!string.Equals(current.Static.Exchange, prev.Static.Exchange))
                {
                    tick.Static.Exchange = current.Static.Exchange;
                }

                if (!string.Equals(current.Static.Symbol, prev.Static.Symbol))
                {
                    tick.Static.Symbol = current.Static.Symbol;
                }


                if (tick.Static.IsZero)
                {
                    tick.Static = null;
                }
            }
            #endregion

            #region 除权除息数据
            // 除权除息数据本来就是稀疏矩阵,不需要做差分
            if (current.Split != null)
            {
                tick.Split = current.Split;

                if (tick.Split.IsZero)
                {
                    tick.Split = null;
                }
            }
            #endregion

            return(tick);
        }
Ejemplo n.º 4
0
 public PbTickCodec()
 {
     Config = new ConfigInfo().Default();
 }
Ejemplo n.º 5
0
        public PbTick Restore(PbTick prev, PbTick diff)
        {
            if (prev == null)
            {
                if (diff.Config == null)
                {
                    throw new Exception("快照的配置不能为空");
                }
                // 记下配置,要用到
                _config  = diff.Config;
                TickSize = _config.GetTickSize();
                // 是快照,直接返回
                return(diff);
            }

            var tick = new PbTick();

            #region 配置数据
            if (diff.Config == null)
            {
                // 使用上条的配置
                tick.Config = prev.Config;
            }
            else
            {
                // 新配置
                _config  = diff.Config;
                TickSize = _config.GetTickSize();
                // 是快照,直接返回
                return(diff);
            }
            #endregion

            _config  = tick.Config;
            TickSize = _config.GetTickSize();

            tick.LastPrice = prev.LastPrice + diff.LastPrice;

            DepthTick from_last = null;
            DepthTick from_next = null;
            DepthTick to_last   = null;
            DepthTick to_next   = null;

            DepthTick last_last = null;
            DepthTick last_next = null;

            #region 买1到买N
            from_last = null;
            from_next = diff.Depth1_3;
            to_last   = null;
            to_next   = tick.Depth1_3;

            last_last = null;
            last_next = prev.Depth1_3;

            while (true)
            {
                // 如果下一步没有数据,直接跳过
                if (from_next == null)
                {
                    break;
                }

                // 如果没有上一笔,这个地方就比较特殊
                if (from_last == null)
                {
                    // 需要考察目标是否有数据
                    if (to_next == null)
                    {
                        to_next       = new DepthTick();
                        tick.Depth1_3 = to_next;
                    }
                    to_next.BidPrice1 = tick.LastPrice - from_next.BidPrice1;
                }
                else
                {
                    // 需要考察目标是否有数据
                    if (to_next == null)
                    {
                        to_next      = new DepthTick();
                        to_last.Next = to_next;
                    }
                    to_next.BidPrice1 = to_last.BidPrice3 - from_next.BidPrice1 - 1;
                }

                to_next.BidPrice2 = to_next.BidPrice1 - from_next.BidPrice2 - 1;
                to_next.BidPrice3 = to_next.BidPrice2 - from_next.BidPrice3 - 1;

                if (last_next == null)
                {
                    to_next.BidSize1  = from_next.BidSize1;
                    to_next.BidSize2  = from_next.BidSize2;
                    to_next.BidSize3  = from_next.BidSize3;
                    to_next.BidCount1 = from_next.BidCount1;
                    to_next.BidCount2 = from_next.BidCount2;
                    to_next.BidCount3 = from_next.BidCount3;
                }
                else
                {
                    to_next.BidSize1  = from_next.BidSize1 + last_next.BidSize1;
                    to_next.BidSize2  = from_next.BidSize2 + last_next.BidSize2;
                    to_next.BidSize3  = from_next.BidSize3 + last_next.BidSize3;
                    to_next.BidCount1 = from_next.BidCount1 + last_next.BidCount1;
                    to_next.BidCount2 = from_next.BidCount2 + last_next.BidCount2;
                    to_next.BidCount3 = from_next.BidCount3 + last_next.BidCount3;
                }

                // 太复杂了,简化为发现Size=0就设Price等为0
                if (to_next.BidSize3 == 0)
                {
                    to_next.BidCount3 = 0;
                    to_next.BidPrice3 = 0;
                }
                if (to_next.BidSize2 == 0)
                {
                    to_next.BidCount2 = 0;
                    to_next.BidPrice2 = 0;
                }
                if (to_next.BidSize1 == 0)
                {
                    to_next.BidCount1 = 0;
                    to_next.BidPrice1 = 0;
                }

                // 移动到下一个数据块
                from_last = from_next;
                from_next = from_next.Next;

                to_last = to_next;
                to_next = to_next.Next;

                last_last = last_next;
                if (last_next != null)
                {
                    last_next = last_next.Next;
                }
            }
            #endregion

            #region 卖1到卖N
            from_last = null;
            from_next = diff.Depth1_3;
            to_last   = null;
            to_next   = tick.Depth1_3;

            last_last = null;
            last_next = prev.Depth1_3;

            while (true)
            {
                // 如果下一步没有数据,直接跳过
                if (from_next == null)
                {
                    break;
                }

                // 如果没有上一笔,这个地方就比较特殊
                if (from_last == null)
                {
                    // 需要考察目标是否有数据
                    if (to_next == null)
                    {
                        to_next       = new DepthTick();
                        tick.Depth1_3 = to_next;
                    }
                    to_next.AskPrice1 = tick.LastPrice + from_next.AskPrice1;
                }
                else
                {
                    // 需要考察目标是否有数据
                    if (to_next == null)
                    {
                        to_next      = new DepthTick();
                        to_last.Next = to_next;
                    }
                    to_next.AskPrice1 = to_last.AskPrice3 + from_next.AskPrice1 + 1;
                }

                to_next.AskPrice2 = to_next.AskPrice1 + from_next.AskPrice2 + 1;
                to_next.AskPrice3 = to_next.AskPrice2 + from_next.AskPrice3 + 1;

                if (last_next == null)
                {
                    to_next.AskSize1  = from_next.AskSize1;
                    to_next.AskSize2  = from_next.AskSize2;
                    to_next.AskSize3  = from_next.AskSize3;
                    to_next.AskCount1 = from_next.AskCount1;
                    to_next.AskCount2 = from_next.AskCount2;
                    to_next.AskCount3 = from_next.AskCount3;
                }
                else
                {
                    to_next.AskSize1  = from_next.AskSize1 + last_next.AskSize1;
                    to_next.AskSize2  = from_next.AskSize2 + last_next.AskSize2;
                    to_next.AskSize3  = from_next.AskSize3 + last_next.AskSize3;
                    to_next.AskCount1 = from_next.AskCount1 + last_next.AskCount1;
                    to_next.AskCount2 = from_next.AskCount2 + last_next.AskCount2;
                    to_next.AskCount3 = from_next.AskCount3 + last_next.AskCount3;
                }

                // 太复杂了,简化为发现Size=0就设Price等为0
                if (to_next.AskSize3 == 0)
                {
                    to_next.AskCount3 = 0;
                    to_next.AskPrice3 = 0;
                }
                if (to_next.AskSize2 == 0)
                {
                    to_next.AskCount2 = 0;
                    to_next.AskPrice2 = 0;
                }
                if (to_next.AskSize1 == 0)
                {
                    to_next.AskCount1 = 0;
                    to_next.AskPrice1 = 0;
                }


                // 移动到下一个数据块
                from_last = from_next;
                from_next = from_next.Next;

                to_last = to_next;
                to_next = to_next.Next;

                last_last = last_next;
                if (last_next != null)
                {
                    last_next = last_next.Next;
                }
            }
            #endregion

            #region 常用行情信息
            tick.Volume       = prev.Volume + diff.Volume;
            tick.OpenInterest = prev.OpenInterest + diff.OpenInterest;
            tick.Turnover     = prev.Turnover + diff.Turnover;
            tick.AveragePrice = prev.AveragePrice + diff.AveragePrice;
            tick.TradingDay   = prev.TradingDay + diff.TradingDay;
            tick.ActionDay    = prev.ActionDay + diff.ActionDay;

            tick.Time_HHmm      = prev.Time_HHmm + diff.Time_HHmm;
            tick.Time________ff = prev.Time________ff + diff.Time________ff;
            // 还原时间
            tick.Time_____ssf__ = prev.Time_____ssf__ + diff.Time_____ssf__ + _config.Time_ssf_Diff;
            #endregion

            #region Bar数据
            if (prev.Bar != null || diff.Bar != null)
            {
                tick.Bar = new BarInfo();
                if (prev.Bar == null)
                {
                    prev.Bar = new BarInfo();
                }
                if (diff.Bar == null)
                {
                    diff.Bar = new BarInfo();
                }

                tick.Bar.Open    = prev.Bar.Open + diff.Bar.Open;
                tick.Bar.High    = prev.Bar.High + diff.Bar.High;
                tick.Bar.Low     = prev.Bar.Low + diff.Bar.Low;
                tick.Bar.Close   = prev.Bar.Close + diff.Bar.Close;
                tick.Bar.BarSize = prev.Bar.BarSize + diff.Bar.BarSize;
            }
            #endregion

            #region 静态数据
            if (prev.Static != null || diff.Static != null)
            {
                tick.Static = new StaticInfo();
                if (prev.Static == null)
                {
                    prev.Static = new StaticInfo();
                }
                if (diff.Static == null)
                {
                    diff.Static = new StaticInfo();
                }

                tick.Static.LowerLimitPrice = prev.Static.LowerLimitPrice + diff.Static.LowerLimitPrice;
                tick.Static.UpperLimitPrice = prev.Static.UpperLimitPrice + diff.Static.UpperLimitPrice;
                tick.Static.SettlementPrice = prev.Static.SettlementPrice + diff.Static.SettlementPrice;

                tick.Static.Symbol   = string.IsNullOrWhiteSpace(diff.Static.Symbol) ? prev.Static.Symbol : diff.Static.Symbol;
                tick.Static.Exchange = string.IsNullOrWhiteSpace(diff.Static.Exchange) ? prev.Static.Exchange : diff.Static.Exchange;
            }
            #endregion

            #region 除权除息数据
            // 没有做过差分,所以直接返回
            if (diff.Split != null)
            {
                tick.Split = diff.Split;
            }
            #endregion

            return(tick);
        }
Ejemplo n.º 6
0
        /// <summary>
        /// 传入两个tick得到tick的差分
        /// </summary>
        /// <param name="prev"></param>
        /// <param name="current"></param>
        /// <returns></returns>
        public PbTick Diff(PbTick prev, PbTick current)
        {
            if (prev == null)
            {
                if (current.Config == null)
                    throw new Exception("快照的配置不能为空");
                // 是快照,直接返回
                return current;
            }

            PbTick tick = new PbTick();

            #region 配置数据
            // 当前数据为空或前后相同,表示
            if(current.Config == null || prev.Config.IsSame(current.Config))
            {
                tick.Config = null;
                // 可以继续下去
            }
            else
            {
                // 是新数据,返回快照
                _config = current.Config;
                TickSize = _config.GetTickSize();

                return current;
            }
            #endregion

            // 先取最关键的数据,因为前一条的config总会补成有效
            _config = prev.Config;
            TickSize = _config.GetTickSize();

            tick.LastPrice = current.LastPrice - prev.LastPrice;

            DepthTick from_last = null;
            DepthTick from_next = null;
            DepthTick to_last = null;
            DepthTick to_next = null;

            DepthTick last_last = null;
            DepthTick last_next = null;

            #region 买1到买N
            from_last = null;
            from_next = current.Depth1_3;
            to_last = null;
            to_next = tick.Depth1_3;

            last_last = null;
            last_next = prev.Depth1_3;

            while (true)
            {
                // 如果下一步没有数据,直接跳过
                if (from_next == null)
                    break;

                // 每节的循环
                if (from_next.BidSize1 == 0)
                    break;

                // 如果没有上一笔,这个地方就比较特殊
                if (from_last == null)
                {
                    // 需要考察目标是否有数据
                    if (to_next == null)
                    {
                        to_next = new DepthTick();
                        tick.Depth1_3 = to_next;
                    }
                    to_next.BidPrice1 = current.LastPrice - from_next.BidPrice1;
                }
                else
                {
                    // 需要考察目标是否有数据
                    if (to_next == null)
                    {
                        to_next = new DepthTick();
                        to_last.Next = to_next;
                    }
                    to_next.BidPrice1 = from_last.BidPrice3 - from_next.BidPrice1 - 1;
                }
                if (last_next == null)
                {
                    to_next.BidSize1 = from_next.BidSize1;
                    to_next.BidCount1 = from_next.BidCount1;
                }
                else
                {
                    to_next.BidSize1 = from_next.BidSize1 - last_next.BidSize1;
                    to_next.BidCount1 = from_next.BidCount1 - last_next.BidCount1;
                }


                if (from_next.BidSize2 == 0)
                    break;
                to_next.BidPrice2 = from_next.BidPrice1 - from_next.BidPrice2 - 1;
                if (last_next == null)
                {
                    to_next.BidSize2 = from_next.BidSize2;
                    to_next.BidCount2 = from_next.BidCount2;
                }
                else
                {
                    to_next.BidSize2 = from_next.BidSize2 - last_next.BidSize2;
                    to_next.BidCount2 = from_next.BidCount2 - last_next.BidCount2;
                }


                if (from_next.BidSize3 == 0)
                    break;

                to_next.BidPrice3 = from_next.BidPrice2 - from_next.BidPrice3 - 1;
                if (last_next == null)
                {
                    to_next.BidSize3 = from_next.BidSize3;
                    to_next.BidCount3 = from_next.BidCount3;
                }
                else
                {
                    to_next.BidSize3 = from_next.BidSize3 - last_next.BidSize3;
                    to_next.BidCount3 = from_next.BidCount3 - last_next.BidCount3;
                }

                // 移动到下一个数据块
                from_last = from_next;
                from_next = from_next.Next;

                to_last = to_next;
                to_next = to_next.Next;

                last_last = last_next;
                if (last_next != null)
                    last_next = last_next.Next;
            }
            #endregion

            #region 卖1到卖N
            from_last = null;
            from_next = current.Depth1_3;
            to_last = null;
            to_next = tick.Depth1_3;

            last_last = null;
            last_next = prev.Depth1_3;

            while (true)
            {
                // 如果下一步没有数据,直接跳过
                if (from_next == null)
                    break;

                // 每节的循环
                if (from_next.AskSize1 == 0)
                    break;

                // 如果没有上一笔,这个地方就比较特殊
                if (from_last == null)
                {
                    // 需要考察目标是否有数据
                    if (to_next == null)
                    {
                        to_next = new DepthTick();
                        tick.Depth1_3 = to_next;
                    }
                    to_next.AskPrice1 = from_next.AskPrice1 - current.LastPrice;
                }
                else
                {
                    // 需要考察目标是否有数据
                    if (to_next == null)
                    {
                        to_next = new DepthTick();
                        to_last.Next = to_next;
                    }
                    to_next.AskPrice1 = from_next.AskPrice1 - from_last.AskPrice3 - 1;
                }
                if (last_next == null)
                {
                    to_next.AskSize1 = from_next.AskSize1;
                    to_next.AskCount1 = from_next.AskCount1;
                }
                else
                {
                    to_next.AskSize1 = from_next.AskSize1 - last_next.AskSize1;
                    to_next.AskCount1 = from_next.AskCount1 - last_next.AskCount1;
                }

                if (from_next.AskSize2 == 0)
                    break;
                to_next.AskPrice2 = from_next.AskPrice2 - from_next.AskPrice1 - 1;
                if (last_next == null)
                {
                    to_next.AskSize2 = from_next.AskSize2;
                    to_next.AskCount2 = from_next.AskCount2;
                }
                else
                {
                    to_next.AskSize2 = from_next.AskSize2 - last_next.AskSize2;
                    to_next.AskCount2 = from_next.AskCount2 - last_next.AskCount2;
                }


                if (from_next.AskSize3 == 0)
                    break;
                to_next.AskPrice3 = from_next.AskPrice3 - from_next.AskPrice2 - 1;
                if (last_next == null)
                {
                    to_next.AskSize3 = from_next.AskSize3;
                    to_next.AskCount3 = from_next.AskCount3;
                }
                else
                {
                    to_next.AskSize3 = from_next.AskSize3 - last_next.AskSize3;
                    to_next.AskCount3 = from_next.AskCount3 - last_next.AskCount3;
                }

                // 移动到下一个数据块
                from_last = from_next;
                from_next = from_next.Next;

                to_last = to_next;
                to_next = to_next.Next;

                last_last = last_next;
                if (last_next != null)
                    last_next = last_next.Next;
            }
            #endregion

            #region 常用行情信息
            tick.Volume = current.Volume - prev.Volume;
            tick.OpenInterest = current.OpenInterest - prev.OpenInterest;
            tick.Turnover = current.Turnover - prev.Turnover;
            tick.AveragePrice = current.AveragePrice - prev.AveragePrice;
            tick.TradingDay = current.TradingDay - prev.TradingDay;
            tick.ActionDay = current.ActionDay - prev.ActionDay;

            tick.Time_HHmm = current.Time_HHmm - prev.Time_HHmm;
            tick.Time________ff = current.Time________ff - prev.Time________ff;
            // 这个地方有区别要减去一个差,将时间再缩小
            tick.Time_____ssf__ = current.Time_____ssf__ - prev.Time_____ssf__ - _config.Time_ssf_Diff;
            #endregion

            #region Bar数据
            // Bar数据要进行差分计算
            if (current.Bar != null || prev.Bar != null)
            {
                tick.Bar = new BarInfo();
                if (current.Bar == null)
                    current.Bar = new BarInfo();
                if (prev.Bar == null)
                    prev.Bar = new BarInfo();

                tick.Bar.Open = current.Bar.Open - prev.Bar.Open;
                tick.Bar.High = current.Bar.High - prev.Bar.High;
                tick.Bar.Low = current.Bar.Low - prev.Bar.Low;
                tick.Bar.Close = current.Bar.Close - prev.Bar.Close;
                tick.Bar.BarSize = current.Bar.BarSize - prev.Bar.BarSize;

                if (tick.Bar.IsZero)
                    tick.Bar = null;
            }
            #endregion

            #region 静态数据
            if (current.Static != null || prev.Static != null)
            {
                tick.Static = new StaticInfo();
                if (current.Static == null)
                    current.Static = new StaticInfo();
                if (prev.Static == null)
                    prev.Static = new StaticInfo();

                tick.Static.LowerLimitPrice = current.Static.LowerLimitPrice - prev.Static.LowerLimitPrice;
                tick.Static.UpperLimitPrice = current.Static.UpperLimitPrice - prev.Static.UpperLimitPrice;
                tick.Static.SettlementPrice = current.Static.SettlementPrice - prev.Static.SettlementPrice;

                if (!string.Equals(current.Static.Exchange,prev.Static.Exchange))
                    tick.Static.Exchange = current.Static.Exchange;

                if (!string.Equals(current.Static.Symbol, prev.Static.Symbol))
                    tick.Static.Symbol = current.Static.Symbol;
                

                if (tick.Static.IsZero)
                    tick.Static = null;
            }
            #endregion

            #region 除权除息数据
            // 除权除息数据本来就是稀疏矩阵,不需要做差分
            if (current.Split != null)
            {
                tick.Split = current.Split;

                if (tick.Split.IsZero)
                    tick.Split = null;
            }
            #endregion

            return tick;
        }
Ejemplo n.º 7
0
 public PbTickCodec()
 {
     Config = new ConfigInfo().Default();
 }
Ejemplo n.º 8
0
        public PbTick Restore(PbTick prev, PbTick diff)
        {
            if (prev == null)
            {
                if (diff.Config == null)
                    throw new Exception("快照的配置不能为空");
                // 记下配置,要用到
                _config = diff.Config;
                TickSize = _config.GetTickSize();
                // 是快照,直接返回
                return diff;
            }

            var tick = new PbTick();

            #region 配置数据
            if (diff.Config == null)
            {
                // 使用上条的配置
                tick.Config = prev.Config;
            }
            else
            {
                // 新配置
                _config = diff.Config;
                TickSize = _config.GetTickSize();
                // 是快照,直接返回
                return diff;
            }
            #endregion

            _config = tick.Config;
            TickSize = _config.GetTickSize();

            tick.LastPrice = prev.LastPrice + diff.LastPrice;

            DepthTick from_last = null;
            DepthTick from_next = null;
            DepthTick to_last = null;
            DepthTick to_next = null;

            DepthTick last_last = null;
            DepthTick last_next = null;

            #region 买1到买N
            from_last = null;
            from_next = diff.Depth1_3;
            to_last = null;
            to_next = tick.Depth1_3;

            last_last = null;
            last_next = prev.Depth1_3;

            while (true)
            {
                // 如果下一步没有数据,直接跳过
                if (from_next == null)
                    break;

                // 如果没有上一笔,这个地方就比较特殊
                if (from_last == null)
                {
                    // 需要考察目标是否有数据
                    if (to_next == null)
                    {
                        to_next = new DepthTick();
                        tick.Depth1_3 = to_next;
                    }
                    to_next.BidPrice1 = tick.LastPrice - from_next.BidPrice1;
                }
                else
                {
                    // 需要考察目标是否有数据
                    if (to_next == null)
                    {
                        to_next = new DepthTick();
                        to_last.Next = to_next;
                    }
                    to_next.BidPrice1 = to_last.BidPrice3 - from_next.BidPrice1 - 1;
                }

                to_next.BidPrice2 = to_next.BidPrice1 - from_next.BidPrice2 - 1;
                to_next.BidPrice3 = to_next.BidPrice2 - from_next.BidPrice3 - 1;

                if (last_next == null)
                {
                    to_next.BidSize1 = from_next.BidSize1;
                    to_next.BidSize2 = from_next.BidSize2;
                    to_next.BidSize3 = from_next.BidSize3;
                    to_next.BidCount1 = from_next.BidCount1;
                    to_next.BidCount2 = from_next.BidCount2;
                    to_next.BidCount3 = from_next.BidCount3;
                }
                else
                {
                    to_next.BidSize1 = from_next.BidSize1 + last_next.BidSize1;
                    to_next.BidSize2 = from_next.BidSize2 + last_next.BidSize2;
                    to_next.BidSize3 = from_next.BidSize3 + last_next.BidSize3;
                    to_next.BidCount1 = from_next.BidCount1 + last_next.BidCount1;
                    to_next.BidCount2 = from_next.BidCount2 + last_next.BidCount2;
                    to_next.BidCount3 = from_next.BidCount3 + last_next.BidCount3;
                }

                // 太复杂了,简化为发现Size=0就设Price等为0
                if (to_next.BidSize3 == 0)
                {
                    to_next.BidCount3 = 0;
                    to_next.BidPrice3 = 0;
                }
                if (to_next.BidSize2 == 0)
                {
                    to_next.BidCount2 = 0;
                    to_next.BidPrice2 = 0;
                }
                if (to_next.BidSize1 == 0)
                {
                    to_next.BidCount1 = 0;
                    to_next.BidPrice1 = 0;
                }

                // 移动到下一个数据块
                from_last = from_next;
                from_next = from_next.Next;

                to_last = to_next;
                to_next = to_next.Next;

                last_last = last_next;
                if (last_next != null)
                    last_next = last_next.Next;
            }
            #endregion

            #region 卖1到卖N
            from_last = null;
            from_next = diff.Depth1_3;
            to_last = null;
            to_next = tick.Depth1_3;

            last_last = null;
            last_next = prev.Depth1_3;

            while (true)
            {
                // 如果下一步没有数据,直接跳过
                if (from_next == null)
                    break;

                // 如果没有上一笔,这个地方就比较特殊
                if (from_last == null)
                {
                    // 需要考察目标是否有数据
                    if (to_next == null)
                    {
                        to_next = new DepthTick();
                        tick.Depth1_3 = to_next;
                    }
                    to_next.AskPrice1 = tick.LastPrice + from_next.AskPrice1;
                }
                else
                {
                    // 需要考察目标是否有数据
                    if (to_next == null)
                    {
                        to_next = new DepthTick();
                        to_last.Next = to_next;
                    }
                    to_next.AskPrice1 = to_last.AskPrice3 + from_next.AskPrice1 + 1;
                }

                to_next.AskPrice2 = to_next.AskPrice1 + from_next.AskPrice2 + 1;
                to_next.AskPrice3 = to_next.AskPrice2 + from_next.AskPrice3 + 1;

                if (last_next == null)
                {
                    to_next.AskSize1 = from_next.AskSize1;
                    to_next.AskSize2 = from_next.AskSize2;
                    to_next.AskSize3 = from_next.AskSize3;
                    to_next.AskCount1 = from_next.AskCount1;
                    to_next.AskCount2 = from_next.AskCount2;
                    to_next.AskCount3 = from_next.AskCount3;
                }
                else
                {
                    to_next.AskSize1 = from_next.AskSize1 + last_next.AskSize1;
                    to_next.AskSize2 = from_next.AskSize2 + last_next.AskSize2;
                    to_next.AskSize3 = from_next.AskSize3 + last_next.AskSize3;
                    to_next.AskCount1 = from_next.AskCount1 + last_next.AskCount1;
                    to_next.AskCount2 = from_next.AskCount2 + last_next.AskCount2;
                    to_next.AskCount3 = from_next.AskCount3 + last_next.AskCount3;
                }

                // 太复杂了,简化为发现Size=0就设Price等为0
                if (to_next.AskSize3 == 0)
                {
                    to_next.AskCount3 = 0;
                    to_next.AskPrice3 = 0;
                }
                if (to_next.AskSize2 == 0)
                {
                    to_next.AskCount2 = 0;
                    to_next.AskPrice2 = 0;
                }
                if (to_next.AskSize1 == 0)
                {
                    to_next.AskCount1 = 0;
                    to_next.AskPrice1 = 0;
                }


                // 移动到下一个数据块
                from_last = from_next;
                from_next = from_next.Next;

                to_last = to_next;
                to_next = to_next.Next;

                last_last = last_next;
                if (last_next != null)
                    last_next = last_next.Next;
            }
            #endregion

            #region 常用行情信息
            tick.Volume = prev.Volume + diff.Volume;
            tick.OpenInterest = prev.OpenInterest + diff.OpenInterest;
            tick.Turnover = prev.Turnover + diff.Turnover;
            tick.AveragePrice = prev.AveragePrice + diff.AveragePrice;
            tick.TradingDay = prev.TradingDay + diff.TradingDay;
            tick.ActionDay = prev.ActionDay + diff.ActionDay;

            tick.Time_HHmm = prev.Time_HHmm + diff.Time_HHmm;
            tick.Time________ff = prev.Time________ff + diff.Time________ff;
            // 还原时间
            tick.Time_____ssf__ = prev.Time_____ssf__ + diff.Time_____ssf__ + _config.Time_ssf_Diff;
            #endregion

            #region Bar数据
            if (prev.Bar != null || diff.Bar != null)
            {
                tick.Bar = new BarInfo();
                if (prev.Bar == null)
                    prev.Bar = new BarInfo();
                if (diff.Bar == null)
                    diff.Bar = new BarInfo();

                tick.Bar.Open = prev.Bar.Open + diff.Bar.Open;
                tick.Bar.High = prev.Bar.High + diff.Bar.High;
                tick.Bar.Low = prev.Bar.Low + diff.Bar.Low;
                tick.Bar.Close = prev.Bar.Close + diff.Bar.Close;
                tick.Bar.BarSize = prev.Bar.BarSize + diff.Bar.BarSize;
            }
            #endregion

            #region 静态数据
            if (prev.Static != null || diff.Static != null)
            {
                tick.Static = new StaticInfo();
                if (prev.Static == null)
                    prev.Static = new StaticInfo();
                if (diff.Static == null)
                    diff.Static = new StaticInfo();

                tick.Static.LowerLimitPrice = prev.Static.LowerLimitPrice + diff.Static.LowerLimitPrice;
                tick.Static.UpperLimitPrice = prev.Static.UpperLimitPrice + diff.Static.UpperLimitPrice;
                tick.Static.SettlementPrice = prev.Static.SettlementPrice + diff.Static.SettlementPrice;

                tick.Static.Symbol = string.IsNullOrWhiteSpace(diff.Static.Symbol) ? prev.Static.Symbol : diff.Static.Symbol;
                tick.Static.Exchange = string.IsNullOrWhiteSpace(diff.Static.Exchange) ? prev.Static.Exchange : diff.Static.Exchange;
            }
            #endregion

            #region 除权除息数据
            // 没有做过差分,所以直接返回
            if (diff.Split != null)
            {
                tick.Split = diff.Split;
            }
            #endregion

            return tick;
        }
Ejemplo n.º 9
0
 public bool IsSame(ConfigInfo config)
 {
     return Version == config.Version
         && TickSize == config.TickSize
         && TickSizeMultiplier == config.TickSizeMultiplier
         && SettlementPriceMultiplier == config.SettlementPriceMultiplier
         && AveragePriceMultiplier == config.AveragePriceMultiplier
         && ContractMultiplier == config.ContractMultiplier
         && Time_ssf_Diff == config.Time_ssf_Diff;
 }