github.com/matrixorigin/matrixone@v1.2.0/pkg/sql/plan/function/agg/bit_xor.go (about)

     1  // Copyright 2024 Matrix Origin
     2  //
     3  // Licensed under the Apache License, Version 2.0 (the "License");
     4  // you may not use this file except in compliance with the License.
     5  // You may obtain a copy of the License at
     6  //
     7  //      http://www.apache.org/licenses/LICENSE-2.0
     8  //
     9  // Unless required by applicable law or agreed to in writing, software
    10  // distributed under the License is distributed on an "AS IS" BASIS,
    11  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    12  // See the License for the specific language governing permissions and
    13  // limitations under the License.
    14  
    15  package agg
    16  
    17  import (
    18  	"github.com/matrixorigin/matrixone/pkg/container/types"
    19  	"github.com/matrixorigin/matrixone/pkg/sql/colexec/aggexec"
    20  	"math"
    21  )
    22  
    23  func RegisterBitXor1(id int64) {
    24  	aggexec.RegisterSingleAggFromFixedToFixed(
    25  		aggexec.MakeSingleAgg1RegisteredInfo(
    26  			aggexec.MakeSingleColumnAggInformation(id, types.T_bit.ToType(), BitXorReturnType, false, true),
    27  			newAggBitXor[uint64],
    28  			InitAggBitXor[uint64],
    29  			FillAggBitXor1[uint64], nil, FillsAggBitXor1[uint64],
    30  			MergeAggBitXor1[uint64],
    31  			nil,
    32  		))
    33  
    34  	aggexec.RegisterSingleAggFromFixedToFixed(
    35  		aggexec.MakeSingleAgg1RegisteredInfo(
    36  			aggexec.MakeSingleColumnAggInformation(id, types.T_uint8.ToType(), BitXorReturnType, false, true),
    37  			newAggBitXor[uint8],
    38  			InitAggBitXor[uint8],
    39  			FillAggBitXor1[uint8], nil, FillsAggBitXor1[uint8],
    40  			MergeAggBitXor1[uint8],
    41  			nil,
    42  		))
    43  
    44  	aggexec.RegisterSingleAggFromFixedToFixed(
    45  		aggexec.MakeSingleAgg1RegisteredInfo(
    46  			aggexec.MakeSingleColumnAggInformation(id, types.T_uint16.ToType(), BitXorReturnType, false, true),
    47  			newAggBitXor[uint16],
    48  			InitAggBitXor[uint16],
    49  			FillAggBitXor1[uint16], nil, FillsAggBitXor1[uint16],
    50  			MergeAggBitXor1[uint16],
    51  			nil,
    52  		))
    53  
    54  	aggexec.RegisterSingleAggFromFixedToFixed(
    55  		aggexec.MakeSingleAgg1RegisteredInfo(
    56  			aggexec.MakeSingleColumnAggInformation(id, types.T_uint32.ToType(), BitXorReturnType, false, true),
    57  			newAggBitXor[uint32],
    58  			InitAggBitXor[uint32],
    59  			FillAggBitXor1[uint32], nil, FillsAggBitXor1[uint32],
    60  			MergeAggBitXor1[uint32],
    61  			nil,
    62  		))
    63  
    64  	aggexec.RegisterSingleAggFromFixedToFixed(
    65  		aggexec.MakeSingleAgg1RegisteredInfo(
    66  			aggexec.MakeSingleColumnAggInformation(id, types.T_uint64.ToType(), BitXorReturnType, false, true),
    67  			newAggBitXor[uint64],
    68  			InitAggBitXor[uint64],
    69  			FillAggBitXor1[uint64], nil, FillsAggBitXor1[uint64],
    70  			MergeAggBitXor1[uint64],
    71  			nil,
    72  		))
    73  
    74  	aggexec.RegisterSingleAggFromFixedToFixed(
    75  		aggexec.MakeSingleAgg1RegisteredInfo(
    76  			aggexec.MakeSingleColumnAggInformation(id, types.T_int8.ToType(), BitXorReturnType, false, true),
    77  			newAggBitXor[int8],
    78  			InitAggBitXor[int8],
    79  			FillAggBitXor1[int8], nil, FillsAggBitXor1[int8],
    80  			MergeAggBitXor1[int8],
    81  			nil,
    82  		))
    83  
    84  	aggexec.RegisterSingleAggFromFixedToFixed(
    85  		aggexec.MakeSingleAgg1RegisteredInfo(
    86  			aggexec.MakeSingleColumnAggInformation(id, types.T_int16.ToType(), BitXorReturnType, false, true),
    87  			newAggBitXor[int16],
    88  			InitAggBitXor[int16],
    89  			FillAggBitXor1[int16], nil, FillsAggBitXor1[int16],
    90  			MergeAggBitXor1[int16],
    91  			nil,
    92  		))
    93  
    94  	aggexec.RegisterSingleAggFromFixedToFixed(
    95  		aggexec.MakeSingleAgg1RegisteredInfo(
    96  			aggexec.MakeSingleColumnAggInformation(id, types.T_int32.ToType(), BitXorReturnType, false, true),
    97  			newAggBitXor[int32],
    98  			InitAggBitXor[int32],
    99  			FillAggBitXor1[int32], nil, FillsAggBitXor1[int32],
   100  			MergeAggBitXor1[int32],
   101  			nil,
   102  		))
   103  
   104  	aggexec.RegisterSingleAggFromFixedToFixed(
   105  		aggexec.MakeSingleAgg1RegisteredInfo(
   106  			aggexec.MakeSingleColumnAggInformation(id, types.T_int64.ToType(), BitXorReturnType, false, true),
   107  			newAggBitXor[int64],
   108  			InitAggBitXor[int64],
   109  			FillAggBitXor1[int64], nil, FillsAggBitXor1[int64],
   110  			MergeAggBitXor1[int64],
   111  			nil,
   112  		))
   113  
   114  	aggexec.RegisterSingleAggFromFixedToFixed(
   115  		aggexec.MakeSingleAgg1RegisteredInfo(
   116  			aggexec.MakeSingleColumnAggInformation(id, types.T_float32.ToType(), BitXorReturnType, false, true),
   117  			newAggBitXor[float32],
   118  			InitAggBitXor[float32],
   119  			FillAggBitXor1[float32], nil, FillsAggBitXor1[float32],
   120  			MergeAggBitXor1[float32],
   121  			nil,
   122  		))
   123  
   124  	aggexec.RegisterSingleAggFromFixedToFixed(
   125  		aggexec.MakeSingleAgg1RegisteredInfo(
   126  			aggexec.MakeSingleColumnAggInformation(id, types.T_float64.ToType(), BitXorReturnType, false, true),
   127  			newAggBitXor[float64],
   128  			InitAggBitXor[float64],
   129  			FillAggBitXor1[float64], nil, FillsAggBitXor1[float64],
   130  			MergeAggBitXor1[float64],
   131  			nil,
   132  		))
   133  
   134  	aggexec.RegisterSingleAggFromVarToVar(
   135  		aggexec.MakeSingleAgg4RegisteredInfo(
   136  			aggexec.MakeSingleColumnAggInformation(id, types.T_binary.ToType(), BitXorReturnType, false, true),
   137  			aggexec.GenerateFlagContextFromVarToVar,
   138  			aggexec.InitFlagContextFromVarToVar,
   139  			FillAggBitXorBinary, nil, FillsAggBitXorBinary,
   140  			MergeAggBitXorBinary,
   141  			nil,
   142  		))
   143  
   144  	aggexec.RegisterSingleAggFromVarToVar(
   145  		aggexec.MakeSingleAgg4RegisteredInfo(
   146  			aggexec.MakeSingleColumnAggInformation(id, types.T_varbinary.ToType(), BitXorReturnType, false, true),
   147  			aggexec.GenerateFlagContextFromVarToVar,
   148  			aggexec.InitFlagContextFromVarToVar,
   149  			FillAggBitXorBinary, nil, FillsAggBitXorBinary,
   150  			MergeAggBitXorBinary,
   151  			nil,
   152  		))
   153  }
   154  
   155  var BitXorReturnType = BitAndReturnType
   156  
   157  type aggBitXor[T numeric] struct{}
   158  
   159  func newAggBitXor[T numeric]() aggexec.SingleAggFromFixedRetFixed[T, uint64] {
   160  	return aggBitXor[T]{}
   161  }
   162  
   163  func (a aggBitXor[T]) Marshal() []byte  { return nil }
   164  func (a aggBitXor[T]) Unmarshal([]byte) {}
   165  
   166  func InitAggBitXor[from numeric](
   167  	exec aggexec.SingleAggFromFixedRetFixed[from, uint64], setter aggexec.AggSetter[uint64], arg, ret types.Type) error {
   168  	setter(0)
   169  	return nil
   170  }
   171  func FillAggBitXor1[from numeric](
   172  	exec aggexec.SingleAggFromFixedRetFixed[from, uint64], value from, getter aggexec.AggGetter[uint64], setter aggexec.AggSetter[uint64]) error {
   173  	vv := float64(value)
   174  	if vv > math.MaxUint64 {
   175  		setter(math.MaxInt64 ^ getter())
   176  		return nil
   177  	}
   178  	if vv < 0 {
   179  		setter(uint64(int64(value)) ^ getter())
   180  		return nil
   181  	}
   182  	setter(uint64(value) ^ getter())
   183  	return nil
   184  }
   185  func FillsAggBitXor1[from numeric](
   186  	exec aggexec.SingleAggFromFixedRetFixed[from, uint64],
   187  	value from, isNull bool, count int, getter aggexec.AggGetter[uint64], setter aggexec.AggSetter[uint64]) error {
   188  	if !isNull {
   189  		if count%2 == 1 {
   190  			return FillAggBitXor1(exec, value, getter, setter)
   191  		}
   192  		setter(getter())
   193  	}
   194  	return nil
   195  }
   196  func MergeAggBitXor1[from numeric](
   197  	exec1, exec2 aggexec.SingleAggFromFixedRetFixed[from, uint64],
   198  	getter1, getter2 aggexec.AggGetter[uint64], setter aggexec.AggSetter[uint64]) error {
   199  	setter(getter1() ^ getter2())
   200  	return nil
   201  }
   202  
   203  func FillAggBitXorBinary(
   204  	exec aggexec.SingleAggFromVarRetVar, value []byte, getter aggexec.AggBytesGetter, setter aggexec.AggBytesSetter) error {
   205  	a := exec.(*aggexec.ContextWithEmptyFlagOfSingleAggRetBytes)
   206  	if a.IsEmpty {
   207  		a.IsEmpty = false
   208  		return setter(value)
   209  	}
   210  	v := getter()
   211  	types.BitXor(v, v, value)
   212  	return nil
   213  }
   214  func FillsAggBitXorBinary(
   215  	exec aggexec.SingleAggFromVarRetVar,
   216  	value []byte, isNull bool, count int, getter aggexec.AggBytesGetter, setter aggexec.AggBytesSetter) error {
   217  	if !isNull {
   218  		if count%2 == 1 {
   219  			return FillAggBitXorBinary(exec, value, getter, setter)
   220  		}
   221  		a := exec.(*aggexec.ContextWithEmptyFlagOfSingleAggRetBytes)
   222  		if a.IsEmpty {
   223  			a.IsEmpty = false
   224  			return setter(make([]byte, len(value)))
   225  		}
   226  	}
   227  	return nil
   228  }
   229  func MergeAggBitXorBinary(
   230  	exec1, exec2 aggexec.SingleAggFromVarRetVar,
   231  	getter1, getter2 aggexec.AggBytesGetter, setter aggexec.AggBytesSetter) error {
   232  	a1 := exec1.(*aggexec.ContextWithEmptyFlagOfSingleAggRetBytes)
   233  	a2 := exec2.(*aggexec.ContextWithEmptyFlagOfSingleAggRetBytes)
   234  	if a2.IsEmpty {
   235  		return nil
   236  	}
   237  	if a1.IsEmpty {
   238  		a1.IsEmpty = false
   239  		return setter(getter2())
   240  	}
   241  	v1, v2 := getter1(), getter2()
   242  	types.BitXor(v1, v1, v2)
   243  	return nil
   244  }