裏 RjpWiki

Julia ときどき R, Python によるコンピュータプログラム,コンピュータ・サイエンス,統計学

羃乗数の桁数の逆関数

2016年03月03日 | ブログラミング

締め切りが 2016/03/03 10:00 AM なので,10:01 に登録されるよう予約

自然数 n に対して、関数 F(n) を、nnnn 乗)を 10 進数で表したときの桁数と定義します。
例えば、55 = 3125 ですので、F(5) = 4 です。同様に、F(20) = 27 です。

さらに、2 以上の自然数 m に対して、F(n) = m となる n の値を G(m) と定義します。
もしそのような n が存在しない場合は、G(m) = -1 と定義します。

例えば G(4) = 5、G(27) = 20 です。同様に、G(7) = -1、G(101) = 57、G(11111) = 3173 となることが確かめられます。

標準入力から、自然数 m(2 ≦ m ≦ 1010)が与えられます。
標準出力に G(m) の値を出力するプログラムを書いてください。


チョー簡単

G = function(m) {
    a = floor(uniroot(function(x) x*log10(x)-m,c(1, 1e10))$root)
    if (ceiling(a*log10(a)) == m) cat(a) else cat(-1)
}

答が合わないときがあるんじゃないかというコメントをいただきました。

n が 10 の羃乗である場合は,間違った答になりますね。10^10  は 11 桁ですからね。

 

G = function(m) {
    a = floor(uniroot(function(x) x*log10(x)-m,c(1, 1e10))$root)
    b = a*log10(a)
    if (b == m-1) return(a) else if (b == m || ceiling(a*log10(a)) != m) return(-1) else return(a)
}

でよいでしょうか。


締め切りの件は,先方が勝手に繰り延べるだけなので,こちらでは対応しません。


コメント (1)
  • X
  • Facebookでシェアする
  • はてなブックマークに追加する
  • LINEでシェアする

「べき乗のべき乗」の大きさの見積

2016年03月03日 | ブログラミング

締め切りは 03/03 10:00AM なので,その 1 分後にこの回答が投稿されるように設定しておく。まだ 3 ヶ月以上も先のことで,鬼が笑うどころか,鬼が飽きてあくびをしたり,居眠りしそうなのだけど,しょうがない。

累乗の累乗,つまり,x^y^z = x^(y^z) は,x, y, z (>1) がちょっと大きくなると,とてつもなく大きな値になり,通常のコンピュータの演算ではオーバーフローして Inf という表示がされることになる。

x = 4.5
y = 6.7
z = 9.8
のとき,
> x^y^z
[1] Inf

x = 2.1
y = 7.2
z = 3.6
のときも,
> x^y^z
[1] Inf


となり,どっちが大きいかわからないのですけど?ということか。

この問題は,何組かの x, y, z が与えられたとき x^y^z が最も大きいのはどれかを判定せよというもの。

a = x^y^z の両辺の対数をとって
log(a) = y^z * log(x)
更にもう一回両辺の対数をとって
log(log(a)) = z * log(y) + log(log(x))

一般に,u < v なら log(u) < log(v) なので,

z * log(y) + log(log(x)) が大きい方が log(log(z * log(y) + log(log(x)))) も大きい。
log(log(z * log(y) + log(log(x)))) はコンピュータで表せないほど大きい値でも,z * log(y) + log(log(x)) はそんなに大きい値ではないことがある。
ということで,回答は log(log(z * log(y) + log(log(x)))) が最も大きいものが x^y^z も最も大きいということである(高校生レベルで解ける問題だ)。

コンピュータで表せる範囲内だと x^y^z は,exp(exp( z * log(y) + log(log(x)) )) であることは以下のように確かめることができる。

x = 1.2
y = 2.3
z = 3.4

> x^y^z
[1] 22.09543
 
> exp(exp( z * log(y) + log(log(x)) ))
[1] 22.09543

こんな簡単な問題を出す人もいるのだから,それに答える人がいてもよいではないかwww

 

追記 2021/06/05

Julia では

x1 = big"4.5" # 4.5
y1 = big"6.7" # 6.699999999999999999999999999999999999999999999999999999999999999999999999999972
z1 = big"9.8" # 9.800000000000000000000000000000000000000000000000000000000000000000000000000028
x1^y1^z1      # 8.141852291891192175294360390819933153170222320673963475352901403217459199966931e+81393094

x2 = big"2.1" # 2.099999999999999999999999999999999999999999999999999999999999999999999999999986
y2 = big"7.2" # 7.199999999999999999999999999999999999999999999999999999999999999999999999999972
z2 = big"3.6" # 3.599999999999999999999999999999999999999999999999999999999999999999999999999986
x2^y2^z2      # 1.384119872013753626430173206328153257960203418740675402484696742668262448719525e+393

z1 * log(y1) + log(log(x1)) # 19.0488334435159380073817381785428805350652170271541018037443913083315619703749
z2 * log(y2) + log(log(x2)) # 6.8082012132336013423449913855664088058111210532323767709225454899520398965019

log(log(z1 * log(y1) + log(log(x1)))) # 1.080789693280837499208500181126913735357567639885908188155661700356977982900217
log(log(z2 * log(y2) + log(log(x2)))) # 0.6513496823931141280708339598949722274473422067642296361862125798228163600446146

 

コメント
  • X
  • Facebookでシェアする
  • はてなブックマークに追加する
  • LINEでシェアする

PVアクセスランキング にほんブログ村

PVアクセスランキング にほんブログ村