既存の重みのセットから選択して、目標合計を作成します


9

ウエイトリフティングをするとき、バーに数枚のプレートをつけて比重を出したいです。

私は次の皿を持っています:

  • 各1 kgの6つのプレート
  • 各2.5 kgのプレート6枚
  • 各5 kgのプレート6枚
  • 各10 kgのプレート6枚

バー自体の重量は10 kgです。

プレートはペアでのみ取り付けることができます-プレートはバーの両端に取り付けられ、両端の配置は完全に対称でなければなりません(たとえば、2つの5 kgプレートを一方の端に取り付け、1つの10 kgプレートを安全上の理由から、もう一方の端は禁止されています)。

特定の総重量を得るために使用する必要がある各種類のプレートの数を教えてくれるプログラムまたは関数を作成します。入力は11より大きい整数です。出力は4つの数値のリスト/配列/文字列です。既存のプレートを組み合わせて目標重量を取得することが不可能な場合は、ゼロ/空の配列、無効な文字列を出力し、例外などをスローします。

いくつかの解決策がある場合、コードは1つだけを出力する必要があります(ユーザーに選択させないでください-彼は他のもので忙しすぎます)。

テストケース:

12 -> [2 0 0 0] - 2 plates of 1 kg plus the bar of 10 kg
13 -> [0 0 0 0] - a special-case output that means "impossible"
20 -> [0 0 2 0] - 2 plates of 5 kg + bar
20 -> [0 4 0 0] - a different acceptable solution for the above
21 -> [6 2 0 0] - 6 plates of 1 kg + 2 plates of 2.5 kg + bar
28 -> [0 0 0 0] - impossible
45 -> [0 2 6 0] - a solution for a random number in range
112 -> [2 4 6 6] - a solution for a random number in range
121 -> [6 6 6 6] - maximal weight for which a solution is possible

コードが数値を逆の順序で出力する場合(重いプレートから軽いプレートへ)、混乱を避けるためにこれを明示的に指定してください。


1
これは最小のコイン数の質問の真似ではありませんか?同じ種類のプレートの6の制限を除いて、同じ貪欲なアルゴリズムが失敗するとは思いません。それでは十分とは言えないかもしれませんが、よくわかりません。
FryAmTheEggman

1
数字が限られているので、正確に貪欲アルゴリズムは、(少なくとも、ない変更なしで)動作しません
anatolyg

関連していますが、それはASCIIです
AdmBorkBork

はい、投稿した理由は、変更が十分に重要であるかどうか確信がなかったためです。コミュニティのフィードバックを得るために投稿しましたが、コミュニティが同意しないようであれば、コメントを削除します。
FryAmTheEggman

1つだけでなくすべてのソリューションを出力できますか?
Luis Mendo 2016年

回答:


5

ゼリー、22 バイト

4ṗạµ×2,5,10,20S€+⁵iƓịḤ

オンラインでお試しください!またはすべてのテストケースを確認します

使い方

4ṗạµ×2,5,10,20S€+⁵iƓịḤ  Main link. No arguments

4                       Set the left argument and initial return value to 4.
 ṗ                      Take the Cartesian power of [1, 2, 3, 4] and 4, i.e.,
                        generate all 4-tuples of integers between 1 and 4.
  ạ                     Take the absolute difference of all integers in the
                        4-tuples and the integer 4. This maps [1, 2, 3, 4] to
                        [3, 2, 1, 0] and places [0, 0, 0, 0] at index 0.
   µ                    Begin a new, monadic chain. Argument: A (list of 4-tuples)
     2,5,10,20          Yield [2, 5, 10, 20].
    ×                   Perform vectorized multiplication with each 4-tuple in A.
              S€        Sum each resulting 4-tuple.
                +⁵      Add 10 to each sum.
                   Ɠ    Read an integer from STDIN.
                  i     Find its first index in the array of sums (0 if not found).
                     Ḥ  Unhalve; yield the list A, with all integers doubled.
                    ị   Retrieve the 4-tuple at the proper index.

6

MATL29 28バイト

4t:qEZ^!"[l2.5AX]@Y*10+G=?@.

解がない入力の場合、これは空の出力を生成します(エラーなし)。

オンラインでお試しください!

説明

4           % Push 4
t:q         % Duplicate 4 and transform into range [0 1 2 3]
E           % Multiply by 2: transform into [0 2 4 6]
Z^          % Cartesian power. Each row is a "combination" of the four numbers
!           % Transpose
"           % For each column
  [l2.5AX]  %   Push [1 2.5 5 10]
  @         %   Push current column
  Y*        %   Matrix multiply. Gives sum of products
  10+       %   Add 10
  G=        %   Compare with input: are they equal?
  ?         %   If so
    @       %     Push current column, to be displayed
    .       %     Break loop
            %   Implicit end
            % Implicit end
            % Implicit display

5

Mathematica、70バイト

Select[FrobeniusSolve[{2,5,10,20},2#-20],AllTrue[EvenQ@#&&#<7&]][[1]]&

匿名関数。数値を入力として受け取り、リストまたはエラーを出力して、{}[[1]]解がない場合は戻ります。


4

ゼリー、25バイト

×2,5,10,20S+⁵⁼³
4ṗ4’ÇÐfḢḤ

ここで試してください。


2,5,10,20->2,5,⁵,20
Leaky Nun

ほんと... ,二人じゃない?私の人生はすべて嘘です
Leaky Nun

@LeakyNun ,はダイアドですが、リテラルにも使用できます。2,5,⁵,20はリテラルではありませんが(2,5and 20are、but ,and ,、atoms)、リンクを組み合わせるために何かが必要になります。
Dennis

3

Python 3、112バイト

lambda n:[i for i in[[i//4**j%4*2for j in range(4)]for i in range(256)]if i[0]+2.5*i[1]+5*i[2]+10*i[3]+10==n][0]

引数を介してターゲット質量の入力を受け取り、各プレートの数をリストとして返す無名関数。ソリューションが存在しない場合、エラーがスローされます。これは純粋な総当たりです。

使い方

lambda n                                   Anonymous function with input target mass n
...for i in range(256)                     Loop for all possible arrangement indices i
[i//4**j%4*2for j in range(4)]             Create a base-4 representation of the index i,
                                           and multiply each digit by 2 to map from
                                           (0,1,2,3) to (0,2,4,6)
[...]                                      Package all possible arrangements in a list
...for i in...                             Loop for all possible arrangements i
i...if i[0]+2.5*i[1]+5*i[2]+10*i[3]+10==n  Return i if it gives the target mass
[...]                                      Package all solutions in a list
:...[0]                                    Return the first list element. This removes any
                                           multiple solutions, and throws an error if there
                                           being no solutions results in an empty list

イデオーネでお試しください



1

Pyth、34 31 25バイト

h + fqQ +; s * VT [1 2.5 5;)yMM ^ U4 4] * 4] 0 
yMh + fqQ +; s * VT [2 5; y;)^ U4 4] * 4] 0
yMhfqQ +; s * VT [2 5; y;)^ U4 4

テストスイート。

不可能のエラー。

これは本質的に総当たりです。

可能な配置は256しかないため、これは非常に高速です。


1

Scala、202バイト

決定したScalaはここではあまり好きにならないので、(おそらく最適ではない)Scalaのソリューションを紹介します。

def w(i:Int){var w=Map(20->0,10->0,5->0,2->0);var x=i-10;while(x>0){
var d=false;for(a<-w.keys)if(a<=x & w(a)<6 & !d){x=x-a;w=w.updated(a,w(a)+2);d=true;}
if(!d){println(0);return;}}
println(w.values);}

プログラムは、ポストのソリューションと比較して、逆の順序で余分なジャンクを出力します。解が見つからない場合、0を出力します。

注:Scalaは馬鹿げているため、改行やスペースを削除できなかったため、サイズを小さくするために、明らかなものを見落とさない限り、メソッドをやり直す必要があります。


1

APL、40バイト

{2×(4⍴4)⊤⍵⍳⍨10+2×,⊃∘.+/↓1 2.5 5 10∘.×⍳4}

⎕IO←0。英語で:

  1. 10+2×,∘.+⌿1 2.5 5 10∘.×⍳4:ウェイトタイプごとのウェイトの4D外部合計を計算することにより、可能なすべてのウェイトの配列を作成します。
  2. ⍵⍳⍨:指定されたインデックスを検索します。見つからない場合、インデックスは1+手順1の配列の集計です。
  3. (4⍴4)⊤:基数4のインデックスを表します。つまり、4D空間における指定された幅の座標を計算します。
  4. :結果を問題の空間にもたらします。座標はプレートの数の半分として解釈されます。

例:{2×(4⍴4)⊤⍵⍳⍨10+ 2×、⊃∘。+ /↓1 2.5 510∘。×⍳4} 112 2 4 6 6

ボーナス:APLは配列言語であるため、一度に複数の重みをテストできます。この場合、結果は転置されます。

      {2×(4⍴4)⊤⍵⍳⍨10+2×,⊃∘.+/↓1 2.5 5 10∘.×⍳4}12 13 20 21 28 45 112 121
2 0 0 6 0 0 2 6
0 0 0 2 0 2 4 6
0 0 2 0 0 2 6 6
0 0 0 0 0 2 6 6

1

JavaScript(ES6)、109バイト

n=>`000${[...Array(256)].findIndex((_,i)=>i+(i&48)*9+(i&12)*79+(i&3)*639+320==n*32).toString(4)*2}`.slice(-4)

00-2エラー時に戻ります。undefinedエラー時に戻る別の解決策、これも109バイト:

n=>[...Array(256)].map((_,i)=>`000${i.toString(4)*2}`.slice(-4)).find(s=>+s[0]+s[1]*2.5+s[2]*5+s[3]*10+10==n)
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.