gitee.com/quant1x/engine@v1.8.4/config/range_session.go (about) 1 package config 2 3 import ( 4 "gitee.com/quant1x/gox/api" 5 "gitee.com/quant1x/pkg/yaml" 6 "slices" 7 "strings" 8 ) 9 10 // TradingSession 交易时段 11 type TradingSession struct { 12 sessions []TimeRange 13 } 14 15 func (this TradingSession) String() string { 16 builder := strings.Builder{} 17 builder.WriteByte('[') 18 var arr []string 19 for _, timeRange := range this.sessions { 20 arr = append(arr, timeRange.String()) 21 } 22 builder.WriteString(strings.Join(arr, ",")) 23 builder.WriteByte(']') 24 return builder.String() 25 } 26 27 func (this TradingSession) v2String() string { 28 builder := strings.Builder{} 29 //builder.WriteByte('[') 30 var arr []string 31 for _, timeRange := range this.sessions { 32 arr = append(arr, timeRange.String()) 33 } 34 builder.WriteString(strings.Join(arr, ",")) 35 //builder.WriteByte(']') 36 return builder.String() 37 } 38 39 func (this *TradingSession) Parse(text string) error { 40 var sessions []TimeRange 41 text = strings.TrimSpace(text) 42 arr := arrayRegexp.Split(text, -1) 43 for _, v := range arr { 44 var tr TimeRange 45 err := tr.Parse(v) 46 if err != nil { 47 return err 48 } 49 sessions = append(sessions, tr) 50 } 51 slices.SortFunc(sessions, func(a, b TimeRange) int { 52 if a.begin < b.begin { 53 return -1 54 } else if a.begin > b.begin { 55 return 1 56 } else if a.end < b.end { 57 return -1 58 } else if a.end == b.end { 59 return 0 60 } else { 61 return 1 62 } 63 }) 64 if len(sessions) == 0 { 65 return ErrTimeFormat 66 } 67 this.sessions = sessions 68 return nil 69 } 70 71 func (this TradingSession) MarshalText() (text []byte, err error) { 72 str := this.String() 73 return api.String2Bytes(str), nil 74 } 75 76 // UnmarshalYAML YAML自定义解析 77 func (this *TradingSession) UnmarshalYAML(node *yaml.Node) error { 78 var value string 79 if len(node.Content) == 0 { 80 value = node.Value 81 } else if len(node.Content) == 2 { 82 value = node.Content[1].Value 83 } else { 84 return ErrRangeFormat 85 } 86 87 return this.Parse(value) 88 } 89 90 // UnmarshalText 设置默认值调用 91 func (this *TradingSession) UnmarshalText(text []byte) error { 92 return this.Parse(api.Bytes2String(text)) 93 } 94 95 // Size 获取时段总数 96 func (this *TradingSession) Size() int { 97 return len(this.sessions) 98 } 99 100 // Index 判断timestamp是第几个交易时段 101 func (this *TradingSession) Index(timestamp ...string) int { 102 var tm string 103 if len(timestamp) > 0 { 104 tm = strings.TrimSpace(timestamp[0]) 105 } else { 106 tm = getTradingTimestamp() 107 } 108 for i, timeRange := range this.sessions { 109 if timeRange.IsTrading(tm) { 110 return i 111 } 112 } 113 return -1 114 } 115 116 // IsTrading 是否交易时段 117 func (this *TradingSession) IsTrading(timestamp ...string) bool { 118 index := this.Index(timestamp...) 119 if index < 0 { 120 return false 121 } 122 return true 123 } 124 125 // IsTodayLastSession 当前时段是否今天最后一个交易时段 126 // 127 // 备选函数名 IsTodayFinalSession 128 func (this *TradingSession) IsTodayLastSession(timestamp ...string) bool { 129 n := this.Size() 130 index := this.Index(timestamp...) 131 if index+1 < n { 132 return false 133 } 134 return true 135 } 136 137 // CanStopLoss 当前时段是否可以进行止损操作 138 // 139 // 如果是3个时段, 止损操作在第2时段, 如果是4个时段, 止损在第3个 140 // 如果是2个时段, 则是第2个时段, 也就是最后一个时段 141 func (this *TradingSession) CanStopLoss(timestamp ...string) bool { 142 n := this.Size() 143 index := this.Index(timestamp...) 144 // 1个时段, 立即止损 145 c1 := n == 1 146 // 2个时段, 在第二个时间止损 147 c2 := n == 2 && index == 1 148 // 3个以上时段, 在倒数第2个时段止损 149 c3 := n >= 3 && index+2 == n 150 if c1 || c2 || c3 { 151 return true 152 } 153 return false 154 } 155 156 // CanTakeProfit 当前时段是否可以止盈 157 func (this *TradingSession) CanTakeProfit(timestamp ...string) bool { 158 _ = timestamp 159 return true 160 }