forked from victor-yacovlev/kumir2
-
Notifications
You must be signed in to change notification settings - Fork 14
Factorial 1
Alexander A. Maly edited this page Jan 29, 2019
·
1 revision
На вход программе подаётся положительное целое число, не превосходящее 100.
Вывести факториал это числа.
Реализация длинной арифметики через текстовые строки. Не слишком эффективная, но показаны простейшие техники работы со строками и символами, разные способы передачи параметров и возврата значений, использования утверждений.
цел D = 10
алг Factorial
нач
цел x, i
ввод x
утв 0 < x <= 10000
лит res = "1", xs = "1"
нц для i от 2 до x
addhere1(1, xs)
res := mul(res, xs)
кц
reverse(res)
вывод res, нс
кон
алг reverse(аргрез лит s)
нач
цел a = 1, b
сим c
b := длин(s)
нц пока a < b
c := s[a]
s[a] := s[b]
s[b] := c
a := a + 1
b := b - 1
кц
кон
алг лит цел2лит(цел n)
нач
утв 0 <= n
цел x
лит res = ""
x := n
нц пока x > 0
res := res + символ(mod(x, D) + код('0'))
x := div(x, D)
кц
знач := res
кон
алг addhere1(цел x, аргрез лит b)
нач
утв 0 <= x < D
цел lb, carry, i, y, z, r
если x = 0 то
выход
все
carry := x
lb := длин(b)
нц для i от 1 до lb
y := код(b[i]) - код('0')
утв 0 <= y < D
z := y + carry
carry := div(z, D)
r := mod(z, D)
b[i] := символ(r + код('0'))
кц при carry = 0
если carry > 0 то
b := b + символ(carry + код('0'))
все
кон
алг addhere(лит a, цел shift, аргрез лит b)
нач
утв 0 <= shift
цел la, lb, carry = 0, i, x, y, z, r
la := длин(a)
lb := длин(b)
нц пока lb < shift + la
b := b + '0'
lb := lb + 1
кц
нц для i от shift + 1 до shift + la
x := код(a[i - shift]) - код('0')
утв 0 <= x < D
y := код(b[i]) - код('0')
утв 0 <= y < D
z := x + y + carry
carry := div(z, D)
r := mod(z, D)
b[i] := символ(r + код('0'))
кц
нц для i от shift + la + 1 до lb
y := код(b[i]) - код('0')
утв 0 <= y < D
z := y + carry
carry := div(z, D)
r := mod(z, D)
b[i] := символ(r + код('0'))
кц при carry = 0
если carry > 0 то
b := b + символ(carry + код('0'))
все
кон
алг лит mul1(цел x, лит b)
нач
утв 0 <= x < D
цел lb, carry = 0, i, y, z, r
лит c = ""
если x = 0 то
знач := c
выход
все
lb := длин(b)
нц для i от 1 до lb
y := код(b[i]) - код('0')
утв 0 <= y < D
z := x * y + carry
carry := div(z, D)
r := mod(z, D)
c := c + символ(r + код('0'))
кц
если carry > 0 то
c := c + символ(carry + код('0'))
все
знач := c
кон
алг лит mul(лит a, лит b)
нач
цел la, lb, carry = 0, i, x, y, z, r
лит res = "", c
лит таб rss[1:D-1]
la := длин(a)
lb := длин(b)
если la = 0 или lb = 0 то
знач := res
выход
все
нц для i от 1 до D - 1
rss[i] := ""
кц
нц для i от 1 до lb
y := код(b[i]) - код('0')
утв 0 <= y < D
если 0 < y то
если длин(rss[y]) > 0 то
c := rss[y]
иначе
c := mul1(y, a)
rss[y] := c
все
addhere(c, i - 1, res)
все
кц
знач := res
кон