私からの最初のパズル、改善の提案を喜んで受け取った!
シナリオは次のとおりです。あなたは急流ラフティング会社のマネージャーとして働いています。毎朝、予約のリストが表示され、ラフトロードに並べ替える必要があります。選択した言語でこれを行うプログラムまたは関数を作成します。
各ラフトには最大数のn
クライアントが収容され、各予約は1 n
人以上のグループ(包括的)です。次のルールを順守する必要があります。
グループを分割することはできません。一緒に予約した場合、全員が同じラフトにいなければなりません。
いかだの数は最小限に抑える必要があります。
上記の2つの規則に従って、グループはいかだの間で可能な限り均等に広げられなければなりません。
入力。
番号n
(これは正の整数であると想定できます)、およびすべての予約のサイズ。言語がそのようなことをサポートしている場合、これは配列、リスト、または同様のデータ構造になります。これらはすべて1〜の正の整数になりn
ます。予約の順序は定義されておらず、重要でもありません。
出力。 いかだ積み荷にグループ化された予約番号のリスト。次のように、グループ化を明確に示す必要があります。
- リスト、または配列の配列。
- いかだごとのコンマ区切りリスト。各ラフト間の改行。
3番目のルールをどのように実装するかはユーザー次第ですが、これには、いかだの平均占有率を見つけ、それから可能な限り逸脱を最小限に抑えることが含まれます。ここにいくつかのテストケースがあります。
n Bookings Output
6 [2,5] [5],[2]
4 [1,1,1,1,1] [1,1,1],[1,1]
6 [2,3,2] [2,2],[3]
6 [2,3,2,3] [2,3],[2,3]
6 [2,3,2,3,2] [2,2,2],[3,3]
12 [10,8,6,4,2] [10],[8,2],[6,4]
6 [4,4,4] [4],[4],[4]
12 [12,7,6,6] [12],[7],[6,6]
標準ルールが適用され、最短のコードが優先されます。楽しむ!
編集済み; 3番目のルールを可能な限り均等に定義するための提案された方法。
いかだの数r
が決定されると(2番目の規則に従い)、a
予約を合計し、で割ることで平均占有率を計算できますr
。各ラフトについて、を使用して平均占有率からの偏差を見つけることができますd(x) = abs(n(x)-a)
。ここn(x)
で、は各ラフトとの人数です1 <= x <= r
。f(y)
厳密に正であり、すべての正に対して厳密に正の1次および非負の2次導関数をもつ連続的な単一値関数では、すべてのの合計としてy
非負の量を定義します。最初の2つのルールを満たし、グローバルミニマムに等しいラフト割り当ての選択は、3番目のルールも満たします。F
f(d(x)), 1 <= x <= r
F
g(y) = y
(2番目の派生ゼロ)またはg(y) = y²
(最初の派生ゼロ)を使用できないことに少し驚いてy = 0
います。