gitee.com/quant1x/engine@v1.8.4/config/range_number.go (about) 1 package config 2 3 import ( 4 "fmt" 5 "gitee.com/quant1x/gox/api" 6 "gitee.com/quant1x/num" 7 "gitee.com/quant1x/pkg/yaml" 8 "regexp" 9 "strings" 10 ) 11 12 // 值范围正则表达式 13 var ( 14 numberRangePattern = "[~]\\s*" 15 numberRangeRegexp = regexp.MustCompile(numberRangePattern) 16 ) 17 18 // NumberRange 数值范围 19 // 20 // 支持: 21 // 1) "1~2", 最小值1, 最大值2 22 // 2) "", 最小值默认, 最大值默认 23 // 3) "3.82", 最小值, 最大值默认 24 // 4) "3.82~", 最小值, 最大值默认 25 // 5) "~3.82", 最小值默认, 最大值 26 type NumberRange struct { 27 min float64 28 max float64 29 } 30 31 func (this NumberRange) String() string { 32 return fmt.Sprintf("{min: %f, max: %f}", this.min, this.max) 33 } 34 35 func (this *NumberRange) setMinDefault() { 36 this.min = num.MinFloat64 37 } 38 39 func (this *NumberRange) setMaxDefault() { 40 this.max = num.MaxFloat64 41 } 42 43 func (this *NumberRange) init() { 44 this.setMinDefault() 45 this.setMaxDefault() 46 } 47 48 func (this *NumberRange) Max() float64 { 49 return this.max 50 } 51 52 func (this *NumberRange) Min() float64 { 53 return this.min 54 } 55 56 func (this *NumberRange) Parse(text string) error { 57 text = strings.TrimSpace(text) 58 if len(text) == 0 { 59 // 如果字符串为空, 设置默认值 60 this.init() 61 return ErrRangeFormat 62 } 63 arr := numberRangeRegexp.Split(text, -1) 64 if len(arr) > 2 { 65 // 如果字符串拆分超过2个元素,格式错误,设置默认值 66 this.init() 67 return ErrRangeFormat 68 } 69 var begin, end string 70 switch len(arr) { 71 case 1: // 如果只有1个值,只是最小 72 begin = strings.TrimSpace(arr[0]) 73 case 2: // 如果有2个值, 分最大值和最小值 74 begin = strings.TrimSpace(arr[0]) 75 end = strings.TrimSpace(arr[1]) 76 default: 77 // 如果字符串拆分超过2个元素,格式错误,设置默认值 78 // 按说流程是不会走到这里的 79 this.init() 80 return ErrRangeFormat 81 } 82 // 修订最大最小值 83 if len(begin) == 0 { 84 // 如果begin为空, 设置最小默认值 85 this.setMinDefault() 86 } else { 87 this.min = num.AnyToFloat64(begin) 88 } 89 if len(end) == 0 { 90 // 如果end为空, 设置最大默认值 91 this.setMaxDefault() 92 } else { 93 this.max = num.AnyToFloat64(end) 94 } 95 if this.min > this.max { 96 this.min, this.max = this.max, this.min 97 } 98 return nil 99 } 100 101 func (this NumberRange) MarshalText() (text []byte, err error) { 102 str := this.String() 103 return api.String2Bytes(str), nil 104 } 105 106 // UnmarshalYAML YAML自定义解析 107 func (this *NumberRange) UnmarshalYAML(node *yaml.Node) error { 108 var value string 109 if len(node.Content) == 0 { 110 value = node.Value 111 } else if len(node.Content) == 2 { 112 value = node.Content[1].Value 113 } 114 115 return this.Parse(value) 116 } 117 118 // UnmarshalText 设置默认值调用 119 func (this *NumberRange) UnmarshalText(bytes []byte) error { 120 text := api.Bytes2String(bytes) 121 return this.Parse(text) 122 } 123 124 // Validate 验证 125 func (this *NumberRange) Validate(v float64) bool { 126 if this.min == 0 && this.max == 0 { 127 return true 128 } else if v >= this.min && v < this.max { 129 return true 130 } 131 return false 132 }