В ходе беседы возникли пару маленьких, но интересных вопросов.
На свежую голову написал.
Q: можно ли обнаружить максимальное число в произвольном ряде, для примера Xn * Xn-1 * … X0 eщe не вызвающее overflow для целого при рекусивных вычислениях.
A: Можно. Запас можно проверить делением. Но есть противоречие. Для обнаружения необходимо войти в рекурсию с заведомо большим числом рекурсивных итераций. Что порождает доп вычисления, плюс может быть чревато последствиями
Что делает метод ограниченно применимым, пожалуй только для предварительных оценок.
/* * * Copyright 2022 Oleg Borodin <borodin@unix7.org> * */ package main import ( "fmt" "math" ) const maxUint uint = math.MaxUint64 func seq1(next uint) uint { if (next == 0) { return 0 } if (next == 1) { return 1 } return next * seq1(next - 1) } func seq2(next uint, max uint) uint { if (max == 0) { return 0 } if (max == 1) { return 1 } if (next >= max) { return next } res := seq2(next + 1, max) fmt.Printf("### step = %2d div = %21d <> next = %2d res = %21d max = %21d\n", max - next, maxUint / res, next, res, maxUint - res) return next * res } func main() { var num uint = 25 res1 := seq1(num) fmt.Println(num, res1) res2 := seq2(1, num) fmt.Println(num, res2) }
Граница для числа итераций = 17 (step 16), для большего числа overflow.
Реплика была шуткой наполовину. В банках действительно используют целые числа. Но один момент - взымание-исчисление процентов.
Берется дробное от целого. 30% от 100 центов = 33.33333333333333333333.
Итого все банки порождают очень маленький шум погрешности от вычислений (“шумы квантования”
), иногда трактуемый в пользу банка, иногда клиента. Похожий на тот, который возникает при операциях с мантиссой float.