Beginning of Beginners Contest 001 解説
A問題
が成り立つかどうかで場合分けをすれば良いです.出力文のタイプミスには注意してください(サンプルの出力をコピペすると確実です).
A,B,C = map(int,input().split()) if A+B>C: print('Correct :)') else: print('Wrong :(')
B問題
各 に対して愚直に を計算すると,全体で 回の計算を行う必要があるためTLEしてしまいます.
そこで, であることを利用すれば,計算量を削減し で解くことができます.
N = int(input()) A = list(map(int,input().split())) MOD = 10**9+7 ans = 0 S = 0 for a in A: S += a S %= MOD ans += S ans %= MOD print(ans)
もしくは, であることを利用して で解くことができます.
N = int(input()) A = list(map(int,input().split())) MOD = 10**9+7 ans = 0 for i in range(N): ans += A[i]*(N-i) ans %= MOD print(ans)
C問題
を素因数分解して,2番目に大きい正の約数を求めれば良いです.
以上 以下の整数 について, が で割り切れるかどうかを調べようとすると,最悪の場合に の計算量がかかりTLEしてしまいます.
ここで,仮に が を満たす約数 を持つならば, も の約数であり が成り立ちます.言い換えれば, が 以上 以下のすべての整数で割り切れなければ, は か でしか割り切れない素数であることが分かります.
よって, 以上 以下の整数 について が で割り切れるかどうかを調べれば良いので, の計算量で問題を解くことができます.
また,今回は2番目に大きい正の約数にしか興味がないので,正の約数すべてを列挙する必要はなく,
を答えれば良いです.
N = int(input()) # 小数の丸め誤差を考慮して,念のため√N+1まで調べる for x in range(2,int(N**0.5)+2): if N%x==0: print(N//x) exit() # Nが素数の場合 print(1)
D問題
この問題でやっていることはバブルソートそのものであることに気付ければ,条件を満たすかどうかは転倒数から判定できることが分かります.転倒数とは かつ を満たす の個数であり,愚直に計算すれば の計算量がかかりますが,BITなどのデータ構造を用いれば で求めることができます.
しかし,今回の場合はソート回数が3回までと限定されているので,愚直なシミュレーションを行うことが可能です.数列を順に見ていき入れ替えるべきところ( となっているところ)を見つけたら,そこを入れ替えるという操作を3回まで行うようにすれば良いです.計算量は です.
N = int(input()) h = list(map(int,input().split())) for k in range(3): for i in range(N-1): if h[i]>h[i+1]: h[i],h[i+1] = h[i+1],h[i] break ok = True for i in range(N): if h[i]!=i+1: ok = False break if ok: print('Yes') else: print('No')
E問題
を で割った商と余りをそれぞれ とすると, 円を支払う際には1円硬貨を 枚,10円硬貨を 枚を使用することになります.よって, を満たす の個数を求める問題であると言い換えることが出来ます.
考えられる の値は最大で になるため,全探索ではTLEしてしまいます.
しかし, の値からある程度それぞれの硬貨の使用枚数に目星をつけられることが分かります.
- のとき,10円硬貨を 枚より多く使うと支払額が 円を超えるため,10円硬貨は高々 枚までしか使われず,さらに1円硬貨は高々 枚までしか使われないため,硬貨の使用枚数は 枚より少ない.
- のとき,10円硬貨は最低 枚使う必要があり,加えて1円硬貨または10円硬貨を 枚以上使うことになるので,硬貨の使用枚数は 枚を超える.
以上をふまえると, の範囲のみを調べれば良いことが分かります.この範囲内に整数は高々 個しか存在しないため,全探索が可能です.
N = int(input()) ans = 0 for x in range(max(1,10*N-100),10*N+1): if (x//10)+(x%10)==N: ans+=1 print(ans)
よりスマートな解法を示します.ポイントは,1円硬貨は高々 枚までしか使用されないことと,1円硬貨の使用枚数と が決まれば,10円硬貨の使用枚数と も一意に決まることです.
のとき,
- (1円硬貨を 枚,10円硬貨を 枚)
- (1円硬貨を 枚,10円硬貨を 枚)
︙ - (1円硬貨を 枚,10円硬貨を 枚)
の 通りが考えられます.
のとき,
- (1円硬貨を 枚,10円硬貨を 枚)
- (1円硬貨を 枚,10円硬貨を 枚)
︙ - (1円硬貨を 枚,10円硬貨を 枚)
の 通りが考えられます.
よって,求める答えは です.
N=int(input()) print(min(N+1,10))
F問題
は に関して単調増加になっているので,二部探索で答えを求めることができます.計算量は です.
K,N = map(int,input().split()) l = 1 r = 10**18 while r-l: mid = (l+r)//2 X = mid for i in range(1,K+1): X = ((X-1)//i+1)*i if X>=N: r = mid else: l = mid+1 print(l)