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  }