0
0

みかん仕分け

Last updated at Posted at 2024-02-13

うーん、これで、一部はうまくいったんですが
2つのテストケースでだめでした。

N,M = map(int,input().split())
for _ in range(M):
    w = int(input())
    if 0 < w < N:
        print(N)
        continue
    if w % N >= round(N/2,0):
        print((w//N+1) * N)
    else:
        print((w//N) * N)
#1つ目入力
13 4
244
686
344
685

#出力(間違い)
247
689
351
689

#2つ目入力
1 2
665
429

#出力(間違い)
666
430

2つ目の入力は1の倍数なんですよね。。。。
四捨五入したらどうなるのか?
のは
1時間経ってしまったので強制ギブで。
ansが最初-100000となっているのが説明を読んでも分からず。

N,M = map(int,input().split())

for _ in range(M):
    x = int(input())
    #とんでもなく最低値を低くしておく
    ans = -100000

    for w in range(1, 1201):
        #Nの倍数の箱でなければスキップ
        if w % N != 0:
            continue
        #多分余りをどこにするかという話?
        if abs(x - w) <= abs(x - ans):
            ans = w

    print(ans)

みかんの重さが最大で 1000 程度なので、みかんを入れる箱の候補は 1 ~ 1200 の箱です。
( N が最大 100 より、1100 の箱とかも候補になるので、余分に調べることにする )
各みかんごとにどの箱に入れるのが良いかを計算することができます。
みかん 1 つにつき、最大 1000 回程度の計算が行われるので、M(≦10) 個のみかんそれぞれに計算を行っても 10000 回程度の計算しか行われないため、制限時間に余裕をもって間に合います。
重さが x のみかんを入れる箱の求め方を考えます。
箱の候補は 1 ~ 1200 なので、変数 : w が 1~1200 の範囲で for 文を回します。
みかんを入れる箱には N の倍数が書かれているので、w が N の倍数かどうかを判定する必要があります。
w が N の倍数かどうかは、以下のように判定することができます。
w % N == 0 : (w を N で割ったあまりが 0 かどうか)
候補の箱の中で、箱に書かれた数が x に最も近い箱(複数ある場合は大きい方)を探す必要があります。
以下の変数を定義して for 文を回すと良いでしょう。
ans := これまでにみた候補の箱に書かれた番号のうち、x に最も近いもの

えーと。。。全然文章が理解できないです。
とくに「みかんを入れる箱の候補は 1 ~ 1200 の箱です。」
( N が最大 100 より、1100 の箱とかも候補になるので、余分に調べることにする )
のところ。

・ 1 ≦ N ≦ 100
・ 1 ≦ M ≦ 10
・ 1 ≦ w_i ≦ 1,000 (1 ≦ i ≦ M)

ってことなので、
本当はNが最大100*Mが最大10でそれらを掛けると1000。
ただし、NがMAX100なので、
たとえば、1001~1049までは1000になるが、1050以上だと実は1100の可能性もある。
そのためみかんのいれる箱は1100なのだが、念の為余分に1200まで増やすということらしい。

ここで、みかんを入れる箱は1200個とするということはわかった。
で、それらをループで回しつつ、Nの倍数にならない場合はスキップ、

つまりNの倍数になる箱のときだけ、候補の箱の中で、
箱に書かれた数が x に最も近い箱(複数ある場合は大きい方)を探すことになります。

ということで、

1つ目のケースで
#1つ目入力
10 3
24
35
3

Nが10ですね。xは24。wは最初は10なので、

w: 10
abs(x - w): 14
abs(x - ans): 100024
ans: 10
w: 20
abs(x - w): 4
abs(x - ans): 14
ans: 20
w: 30
abs(x - w): 6
abs(x - ans): 4
w: 40
abs(x - w): 16
abs(x - ans): 4
w: 50
abs(x - w): 26
abs(x - ans): 4
w: 60
abs(x - w): 36
abs(x - ans): 4
w: 70
abs(x - w): 46
abs(x - ans): 4


と、x−wが一番小さくなる数値を探していたわけですね。
そしてそれをansにするということをやっていたわけです。

というわけで見直します

N,M = map(int,input().split())

for _ in range(M):
    x = int(input())
    #とんでもなく最低値を低くしておく
    ans = -100000

    for w in range(1, 1201):
        #Nの倍数の箱でなければスキップ
        if w % N != 0:
            continue
        #絶対値で差が限りなく小さくなる数値を探してAnsにする
        if abs(x - w) <= abs(x - ans):
            ans = w

    print(ans)

とこういう形になりました。

コメントも頂いていました。
そうですね、丸めるのがなかなか難しいんです。。。
それを、商(//)で解決されていました。。なるほど。
たとえば
24+(10//2)=29 これを10で割ってかけ直すと20
35+(10//2)=40 これを10で割ってかけ直すと40
3はそのまま10ですね。
なるほど。。。。

N,M = map(int,input().split())
for _ in range(M):
    w = int(input())
    # Nよりwが下だったら問答無用でNに寄せる
    if w < N:
        print(N)
    else:
    #それ以外は、
        print((w + N // 2) // N * N)

いやあ難しかったです。。。
けど、ロジックを考えるのっておもしろいですね!

0
0
2

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0