按数字拆分 big.Int

我正在尝试将 a 拆分big.Int为多个int64s,以便每个都是较大数字的一部分,标准偏移量为 18 位。例如,给定以下输入值1234512351234088800000999,我希望得到以下输出:[351234088800000999, 1234512]。对于负数,我希望所有部分都是负数(即-1234512351234088800000999produces [-351234088800000999, -1234512])。


我已经知道我可以这样做以获得我想要的结果:


func Split(input *big.Int) []int64 {

    const width = 18


    asStr := in.Coefficient().Text(10)

    strLen := len(asStr)

    offset := 0

    if in.IsNegative() {

        offset = 1

    }


    length := int(math.Ceil(float64(strLen-offset) / width))

    ints := make([]int64, length)

    for i := 1; i <= length; i++ {

        start := strLen - (i * width)

        end := start + width

        if start < 0 || (start == 1 && asStr[0] == '-') {

            start = 0

        }


        ints[i-1], _ = strconv.ParseInt(asStr[start:end], 10, 64)

        if offset == 1 && ints[i-1] > 0 {

            ints[i-1] = 0 - ints[i-1]

        }

    }


    return ints

}

但是,我不喜欢使用字符串解析的想法,也不喜欢使用strconv. 有什么方法可以直接使用吗big.Int?


慕后森
浏览 74回答 1
1回答

沧海一幻觉

您可以使用该DivMod函数在这里执行您需要的操作,并特别注意处理负数:var offset = big.NewInt(1e18)func Split(input *big.Int) []int64 {&nbsp; &nbsp; rest := new(big.Int)&nbsp; &nbsp; rest.Abs(input)&nbsp; &nbsp; var ints []int64&nbsp; &nbsp; r := new(big.Int)&nbsp; &nbsp; for {&nbsp; &nbsp; &nbsp; &nbsp; rest.DivMod(rest, offset, r)&nbsp; &nbsp; &nbsp; &nbsp; ints = append(ints, r.Int64() * int64(input.Sign()))&nbsp; &nbsp; &nbsp; &nbsp; if rest.BitLen() == 0 {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; break&nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; }&nbsp; &nbsp; return ints}将每个输出乘以input.Sign()确保如果输入为负,则每个输出将为负。输出值的总和乘以 1e18 乘以它们在输出中的位置应该等于输入。
打开App,查看更多内容
随时随地看视频慕课网APP

相关分类

Go