ops.go raw

   1  //
   2  // Copyright 2024 CloudWeGo Authors
   3  //
   4  // Licensed under the Apache License, Version 2.0 (the "License");
   5  // you may not use this file except in compliance with the License.
   6  // You may obtain a copy of the License at
   7  //
   8  //     http://www.apache.org/licenses/LICENSE-2.0
   9  //
  10  // Unless required by applicable law or agreed to in writing, software
  11  // distributed under the License is distributed on an "AS IS" BASIS,
  12  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  13  // See the License for the specific language governing permissions and
  14  // limitations under the License.
  15  //
  16  
  17  package expr
  18  
  19  import (
  20  	"fmt"
  21  )
  22  
  23  func idiv(v int64, d int64) (int64, error) {
  24  	if d != 0 {
  25  		return v / d, nil
  26  	} else {
  27  		return 0, newRuntimeError("division by zero")
  28  	}
  29  }
  30  
  31  func imod(v int64, d int64) (int64, error) {
  32  	if d != 0 {
  33  		return v % d, nil
  34  	} else {
  35  		return 0, newRuntimeError("division by zero")
  36  	}
  37  }
  38  
  39  func ipow(v int64, e int64) (int64, error) {
  40  	mul := v
  41  	ret := int64(1)
  42  
  43  	/* value must be 0 or positive */
  44  	if v < 0 {
  45  		return 0, newRuntimeError(fmt.Sprintf("negative base value: %d", v))
  46  	}
  47  
  48  	/* exponent must be non-negative */
  49  	if e < 0 {
  50  		return 0, newRuntimeError(fmt.Sprintf("negative exponent: %d", e))
  51  	}
  52  
  53  	/* fast power first round */
  54  	if (e & 1) != 0 {
  55  		ret *= mul
  56  	}
  57  
  58  	/* fast power remaining rounds */
  59  	for e >>= 1; e != 0; e >>= 1 {
  60  		if mul *= mul; (e & 1) != 0 {
  61  			ret *= mul
  62  		}
  63  	}
  64  
  65  	/* all done */
  66  	return ret, nil
  67  }
  68