183 lines
3.7 KiB
Go
183 lines
3.7 KiB
Go
package engine
|
||
|
||
// operators.go - 查询操作符实现
|
||
// 使用 helpers.go 中的公共辅助函数
|
||
|
||
// compareEq 相等比较
|
||
func compareEq(a, b interface{}) bool {
|
||
return CompareEq(a, b)
|
||
}
|
||
|
||
// compareGt 大于比较
|
||
func compareGt(a, b interface{}) bool {
|
||
return CompareNumbers(a, b) > 0
|
||
}
|
||
|
||
// compareGte 大于等于比较
|
||
func compareGte(a, b interface{}) bool {
|
||
return CompareNumbers(a, b) >= 0
|
||
}
|
||
|
||
// compareLt 小于比较
|
||
func compareLt(a, b interface{}) bool {
|
||
return CompareNumbers(a, b) < 0
|
||
}
|
||
|
||
// compareLte 小于等于比较
|
||
func compareLte(a, b interface{}) bool {
|
||
return CompareNumbers(a, b) <= 0
|
||
}
|
||
|
||
// compareIn 检查值是否在数组中
|
||
func compareIn(value interface{}, operand interface{}) bool {
|
||
arr, ok := operand.([]interface{})
|
||
if !ok {
|
||
return false
|
||
}
|
||
|
||
return ContainsElement(arr, value)
|
||
}
|
||
|
||
// compareRegex 正则表达式匹配
|
||
func compareRegex(value interface{}, operand interface{}) bool {
|
||
return MatchRegex(value, operand)
|
||
}
|
||
|
||
// compareType 类型检查
|
||
func compareType(value interface{}, operand interface{}) bool {
|
||
if value == nil {
|
||
return operand == "null"
|
||
}
|
||
|
||
switch op := operand.(type) {
|
||
case string:
|
||
return CheckType(value, op)
|
||
case []interface{}:
|
||
for _, t := range op {
|
||
if ts, ok := t.(string); ok && CheckType(value, ts) {
|
||
return true
|
||
}
|
||
}
|
||
}
|
||
|
||
return false
|
||
}
|
||
|
||
// compareAll 数组包含所有指定元素
|
||
func compareAll(value interface{}, operand interface{}) bool {
|
||
arr, ok := value.([]interface{})
|
||
if !ok {
|
||
return false
|
||
}
|
||
|
||
required, ok := operand.([]interface{})
|
||
if !ok {
|
||
return false
|
||
}
|
||
|
||
return ContainsAllElements(arr, required)
|
||
}
|
||
|
||
// compareElemMatch 数组元素匹配
|
||
func compareElemMatch(value interface{}, operand interface{}) bool {
|
||
arr, ok := value.([]interface{})
|
||
if !ok {
|
||
return false
|
||
}
|
||
|
||
filter, ok := operand.(map[string]interface{})
|
||
if !ok {
|
||
return false
|
||
}
|
||
|
||
for _, item := range arr {
|
||
if itemMap, ok := item.(map[string]interface{}); ok {
|
||
if MatchFilter(itemMap, filter) {
|
||
return true
|
||
}
|
||
}
|
||
}
|
||
|
||
return false
|
||
}
|
||
|
||
// compareSize 数组大小比较
|
||
func compareSize(value interface{}, operand interface{}) bool {
|
||
arr, ok := value.([]interface{})
|
||
if !ok {
|
||
return false
|
||
}
|
||
|
||
size := 0
|
||
switch s := operand.(type) {
|
||
case int:
|
||
size = s
|
||
case int64:
|
||
size = int(s)
|
||
case float64:
|
||
size = int(s)
|
||
default:
|
||
return false
|
||
}
|
||
|
||
return len(arr) == size
|
||
}
|
||
|
||
// compareMod 模运算:value % divisor == remainder
|
||
func compareMod(value interface{}, operand interface{}) bool {
|
||
num := ToFloat64(value)
|
||
|
||
var divisor, remainder float64
|
||
switch op := operand.(type) {
|
||
case []interface{}:
|
||
if len(op) != 2 {
|
||
return false
|
||
}
|
||
divisor = ToFloat64(op[0])
|
||
remainder = ToFloat64(op[1])
|
||
default:
|
||
return false
|
||
}
|
||
|
||
if divisor == 0 {
|
||
return false
|
||
}
|
||
|
||
// 计算模
|
||
mod := num - divisor*float64(int(num/divisor))
|
||
// 处理负数情况
|
||
if mod < 0 {
|
||
mod += divisor
|
||
}
|
||
|
||
return mod == remainder
|
||
}
|
||
|
||
// compareBitsAllClear 位运算:所有指定位都为 0
|
||
func compareBitsAllClear(value interface{}, operand interface{}) bool {
|
||
num := ToInt64(value)
|
||
mask := ToInt64(operand)
|
||
return (num & mask) == 0
|
||
}
|
||
|
||
// compareBitsAllSet 位运算:所有指定位都为 1
|
||
func compareBitsAllSet(value interface{}, operand interface{}) bool {
|
||
num := ToInt64(value)
|
||
mask := ToInt64(operand)
|
||
return (num & mask) == mask
|
||
}
|
||
|
||
// compareBitsAnyClear 位运算:任意指定位为 0
|
||
func compareBitsAnyClear(value interface{}, operand interface{}) bool {
|
||
num := ToInt64(value)
|
||
mask := ToInt64(operand)
|
||
return (num & mask) != mask
|
||
}
|
||
|
||
// compareBitsAnySet 位运算:任意指定位为 1
|
||
func compareBitsAnySet(value interface{}, operand interface{}) bool {
|
||
num := ToInt64(value)
|
||
mask := ToInt64(operand)
|
||
return (num & mask) != 0
|
||
}
|