func RabinMiller(p *big.Int) bool { pdec := new(big.Int).Sub(p, big.NewInt(1)) // = p - 1 big2 := big.NewInt(2) for i := 0; i < 20; i++ { x := RandNumSmaller(p) stg := new(big.Int).Exp(x, pdec, p) // = x^(p-1) mod p if stg.Cmp(big1) != 0 { return false } // test na Carmichaelova cisla (kontrola zda x^[(p-1)/2] je +1 nebo -1) p2 := new(big.Int).Rsh(p, 1) // = (p - 1)/2 for { stg.Exp(x, p2, p) if stg.Cmp(pdec) == 0 { break } if stg.Cmp(big1) != 0 { return false } _, res := p2.Div(p2, big2) if res.Cmp(big1) == 0 { break } } } return true }
// Zjisti a0, b0, z tak aby: a0*x + b0*y = z (mod n) func Euklid(x, y, n *big.Int) (a0, b0, z *big.Int) { a0 = big1 a := big0 b0 = big0 b := big1 g := new(big.Int) t := new(big.Int) // tmp if x.Cmp(y) < 0 { x, y = y, x a0, a, b0, b = b0, b, a0, a } for { z = y _, y = g.Div(x, y) x = z a0, a = a, _Euklid_sub(a0, t.Mul(a, g), n) b0, b = b, _Euklid_sub(b0, t.Mul(b, g), n) if y.Cmp(big0) == 0 { break } } return }
func number_divide(x, y Obj) Obj { xfx := (uintptr(unsafe.Pointer(x)) & fixnum_mask) == fixnum_tag yfx := (uintptr(unsafe.Pointer(y)) & fixnum_mask) == fixnum_tag if xfx && yfx { i1 := int(uintptr(unsafe.Pointer(x))) >> fixnum_shift i2 := int(uintptr(unsafe.Pointer(y))) >> fixnum_shift // A good optimizer will combine the div and mod into // one instruction. r, m := i1/i2, i1%i2 if m == 0 && r > fixnum_min && r < fixnum_max { return Make_fixnum(r) } else { return wrap(big.NewRat(int64(i1), int64(i2))) } } if (!xfx && (uintptr(unsafe.Pointer(x))&heap_mask) != heap_tag) || (!yfx && (uintptr(unsafe.Pointer(y))&heap_mask) != heap_tag) { panic("bad type") } if xfx { x = wrap(big.NewInt(int64(fixnum_to_int(x)))) } if yfx { y = wrap(big.NewInt(int64(fixnum_to_int(y)))) //return wrap(z.Div(vx,vy)) } switch vx := (*x).(type) { case *big.Int: var z *big.Int = big.NewInt(0) switch vy := (*y).(type) { case *big.Int: return simpBig(z.Div(vx, vy)) case *big.Rat: z := big.NewRat(1, 1) z.SetInt(vx) return simpRat(z.Quo(z, vy)) default: panic("bad type") } case *big.Rat: z := big.NewRat(1, 1) switch vy := (*y).(type) { case *big.Int: z.SetInt(vy) return simpRat(z.Quo(vx, z)) case *big.Rat: return simpRat(z.Quo(vx, vy)) } } panic("bad type") }
//encodes big.Int to base58 string func Big2Base58(val *big.Int) Base58 { answer := "" valCopy := new(big.Int).Abs(val) //copies big.Int if val.Cmp(big.NewInt(0)) <= 0 { //if it is less than 0, returns empty string return Base58("") } tmpStr := "" tmp := new(big.Int) for valCopy.Cmp(big.NewInt(0)) > 0 { //converts the number into base58 tmp.Mod(valCopy, big.NewInt(58)) //takes modulo 58 value valCopy.Div(valCopy, big.NewInt(58)) //divides the rest by 58 tmpStr += alphabet[tmp.Int64() : tmp.Int64()+1] //encodes } for i := (len(tmpStr) - 1); i > -1; i-- { answer += tmpStr[i : i+1] //reverses the order } return Base58(answer) //returns }
/** * Find the next palindrome after the current number. */ func (factory *PalinFactory) Next() string { var ( buffer bytes.Buffer numberLen = len(factory.number) oddLength = numberLen%2 > 0 // Greedily split the number into two halves. Greedily meaning for // odd-length numbers, the middle digit belongs to both sides (e.g., // "987" splits into "98" and "87"). leftSide = factory.number[0 : (numberLen+1)/2] rightSide = factory.number[numberLen/2:] mirroredSide = Reverse(leftSide) leftLength = len(leftSide) ) // Before we create a palindrome, we can determine if the resulting // palindrome will not be greater than the original number by mirroring the // left side and comparing it to the right side. // // Using 123456 as an example, the palindrome will be 123321, which is less // than 123456. If we mirror the left side, we get 321. The right side is // 456. Since 321 <= 456, we know the palindrome will not be greater than // the original number. if !Greater(mirroredSide, rightSide) { // Since it is not greater, we can increment the palindrome by // incrementing the left side. This is essentially incrementing the // middle digits of the palindrome, which results in the very next // palindrome. Since we are also incrementing the left side, the // resulting palindrome will also be greater than the original number. leftSide = Increment(leftSide) // One obvious optimization is to set leftSide here and then set it // again in the next inner if {}, rather than calling leftValue.String() // twice, but that seems to consistently be slower for some reason. // If we introduced a new digit, this changes the evenness/oddness of // the number, and we need to account for this when constructing the // palindrome. Since we greedily split the number, going from odd to // even means we need to drop a digit on the left. // // For example, the left side of 999 is "99". The left side of 1001 is // "10". Notice both have two digits. However, if we increment "99" // (as a left side), we get "100", so we need to divide by 10 to get the // two digits that will be mirrored to form the palindrome 1001. This // doesn't need to be done when going from odd to even, because the left // side has one more digit (left side of 99 is "9", left side of 101 is // "10"). if len(leftSide) != leftLength { oddLength = !oddLength if !oddLength { var leftValue big.Int leftValue.SetString(leftSide, 10) leftValue.Div(&leftValue, big.NewInt(10)) leftSide = leftValue.String() } } mirroredSide = Reverse(leftSide) } buffer.WriteString(leftSide) // Mirror the left side onto the right to form a palindrome if oddLength { // When odd, the left and right sides "overlap" on the middle digit, so // don't include in on the right buffer.WriteString(mirroredSide[1:]) } else { buffer.WriteString(mirroredSide) } return buffer.String() }