헤비 박스 스태킹


27

무거운 상자가 많이 있으며 가능한 적은 수의 스택에 쌓으려고합니다. 문제는 지원할 수있는 것보다 많은 상자를 상자에 쌓을 수 없으므로 더 큰 상자는 스택의 맨 아래에 있어야합니다.

도전

입력 : 전체 박스 무게 목록 (kg 단위).

출력 : 상자 스택을 설명하는 목록 목록입니다. 이것은 입력에 가능한 가장 적은 수의 스택을 사용해야합니다. 유효한 스택이 되려면 스택의 각 상자 무게가 위에있는 모든 상자 무게의 합보다 크거나 같아야합니다.

유효한 스택의 예

(맨 아래 순서로)

  • [삼]
  • [1, 1]
  • [3, 2, 1]
  • [4, 2, 1, 1]
  • [27, 17, 6, 3, 1]
  • [33, 32, 1]
  • [999, 888, 99, 11, 1]

유효하지 않은 스택의 예

(아래에서 위로)

  • [1, 2]
  • [3, 3, 3]
  • [5, 5, 1]
  • [999, 888, 777]
  • [4, 3, 2]
  • [4321, 3000, 1234, 321]

테스트 사례 예

1

IN: [1, 2, 3, 4, 5, 6, 9, 12]
OUT: [[12, 6, 3, 2, 1], [9, 5, 4]]

2

IN: [87, 432, 9999, 1234, 3030]
OUT: [[9999, 3030, 1234, 432, 87]]

IN: [1, 5, 3, 1, 4, 2, 1, 6, 1, 7, 2, 3]
OUT: [[6, 3, 2, 1], [7, 4, 2, 1], [5, 3, 1, 1]]

4

IN: [8, 5, 8, 8, 1, 2]
OUT: [[8, 8], [8, 5, 2, 1]]

규칙과 가정

  • 표준 I / O 규칙 및 금지 허점 적용
  • 편리한 I / O 형식을 사용하십시오
    • 일관된 한 스택은 위에서 아래로 또는 아래에서 위로 설명 될 수 있습니다.
    • 스택 내 상자가 아닌 스택 순서는 중요하지 않습니다.
    • 입력 상자를 미리 정렬 된 목록으로 사용할 수도 있습니다. 정렬 자체로 일반적인 문제가 해결되지 않는 한 순서는 입력에 특히 중요하지 않습니다.
  • 최적의 스택 구성이 두 개 이상인 경우 그 중 하나를 출력 할 수 있습니다
  • 상자가 하나 이상 있고 모든 상자의 무게가 1kg 이상이라고 가정 할 수 있습니다
  • 최소 9,999kg의 무게를 지탱해야합니다.
  • 최소 9,999 개의 총 상자를 지원해야합니다.
  • 무게가 같은 상자는 구별 할 수 없으므로 어느 상자를 어디에 사용했는지 주석을 달 필요가 없습니다.

행복한 골프! 행운을 빕니다!


2
가중치를 정렬 된 순서로 가져갈 수 있습니까? (오름차순 또는 내림차순)
Arnauld

4
"최소한 총 9,999 개의 박스를 지원해야합니다." 여기서 "지원"은 어떻게 해석됩니까? 프로그램이 그러한 크기의 입력을받을 수 있어야한다는 의미입니까, 아니면 프로그램이 실제로 적절한 시간 내에 답변을 제공해야한다는 의미입니까? 후자의 경우 훨씬 더 큰 테스트 사례가 제공되어야합니다.
Joel

1
권장 테스트 사례 : [8, 8, 8, 5, 1]->[[8, 8], [8, 5, 1]]
Hiatsu

3
또는 더 나은 : [8, 5, 8, 8, 1, 2]->[[8, 8], [8, 5, 2, 1]]
히 아츠

2
@Arnauld, 그렇지 않으면 흥미롭지 않은 정렬 코드가 답변에 추가되므로 yes 라고 말하면 입력을 정렬 된 순서로 취할 수 있습니다.
Beefster

답변:


5

젤리 , 19 바이트

Œ!ŒṖ€ẎṖÄ>ḊƲ€¬ȦƊƇLÞḢ

온라인으로 사용해보십시오!

Nick Kennedy 덕분에 명백한 -3 ...

위에서 아래로.

설명:

Œ!ŒṖ€ẎṖÄ>ḊƲ€¬ȦƊƇLÞḢ  Arguments: S (e.g. [1, 2, 3, 4, 5])
Œ!                   Permutations (e.g. [..., [4, 1, 5, 2, 3], ...])
    €                Map link over left argument (e.g. [..., [..., [[4, 1], [5], [2, 3]], ...], ...])
  ŒṖ                  Partitions (e.g. [..., [[4, 1], [5], [2, 3]], ...])
     Ẏ               Concatenate elements (e.g. [..., ..., [[4, 1], [5], [2, 3]], ..., ...])
               Ƈ     Filter by link (e.g. [..., [[1, 3], [2], [4], [5]], ...])
              Ɗ       Create >=3-link monadic chain (e.g. [[1], [], [0]])
           €           Map link over left argument (e.g. [[1], [], [0]])
          Ʋ             Create >=4-link monadic chain (e.g. [1])
      Ṗ                  Remove last element (e.g. [4])
       Ä                 Cumulative sum (e.g. [4])
         Ḋ               [Get original argument] Remove first element (e.g. [1])
        >                Greater than (vectorizes) (e.g. [1])
            ¬          Logical NOT (vectorizes) (e.g. [[0], [], [1]])
             Ȧ         Check if non-empty and not containing zeroes after flattening (e.g. 0)
                 Þ   Sort by link (e.g. [[[1, 2, 3], [4, 5]], ..., [[5], [4], [3], [2], [1]]])
                L     Length (e.g. 4)
                  Ḣ  Pop first element (e.g. [[1, 2, 3], [4, 5]])

설명이 덜 간결한 버전 일 가능성이 있습니까? 나는 그들로부터 톤을 배웁니다.
John Keates

1
@JohnKeates 하나를 추가했습니다.
Outgolfer Erik

5

자바 스크립트 (Node.js를)  139 122  116 바이트

오름차순으로 정렬 된 입력을 예상합니다.

f=(A,s=[],[n,...a]=A,r)=>n?s.some((b,i,[...c])=>n<eval(b.join`+`)?0:f(A,c,a,c[i]=[n,...b]))?S:r?0:f(A,[...s,[]]):S=s

온라인으로 사용해보십시오!

댓글

f = (                        // f is a recursive function taking:
  A,                         //   A[] = input array
  s = [],                    //   s[] = list of stacks, initially empty
  [n,                        //   n   = next weight to process
      ...a] = A,             //   a[] = array of remaining weights
  r                          //   r   = recursion flag
) =>                         //
  n ?                        // if n is defined:
    s.some((b, i,            //   for each stack b[] at position i in s[],
                  [...c]) => //   using c[] as a copy of s[]:
      n < eval(b.join`+`) ?  //     if n is not heavy enough to support all values in b[]:
        0                    //       abort
      :                      //     else:
        f(                   //       do a recursive call:
          A, c, a,           //         using A[], c[] and a[]
          c[i] = [n, ...b]   //         with n prepended to c[i]
        )                    //       end of recursive call
    ) ?                      //   end of some(); if successful:
      S                      //     return S[]
    :                        //   else:
      r ?                    //     if this is a recursive call:
        0                    //       do nothing
      :                      //     else:
        f(A, [...s, []])     //       try again with an additional stack
  :                          // else:
    S = s                    //   success: save the solution in S[]

2

Python 3.8 (시험판) , 178 바이트

f=lambda b,s=[[]]:(a for i in range(len(s))if b[0]>=sum(s[i])for a in f(b[1:],s[:i]+[[b[0]]+s[i]]+s[i+1:]+[[]]))if b else[s]
g=lambda a:(c:=sorted(f(a),key=len)[0])[:c.index([])]

온라인으로 사용해보십시오!

이제 가능한 모든 입력에서 작동합니다. (10 개 이상의 상자가있는 TIO에서 시간 초과되지만 정답을 계산합니다)


2
list(reversed(sorted(a)))sorted(a)[::-1]골프 목적 으로 쓸 수 있습니다 .
Joel

지금까지, 특히 다른 인덱싱을 많이하고 있기 때문에 지금까지 알고 있다고 생각할 것입니다. 감사.
히아 쓰

사이드 비고로서, 골프 용이 아니라면 sorted(a, reverse=True)대신 쓰는 것이 더 좋습니다.
Joel
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.