배열 정렬 추가


39

소개

두 개의 비어 있지 않은 정수 배열, 예를 들어 A = [0 3 2 2 8 4]B = [7 8 7 2]를 고려하십시오 . 정렬 정렬 을 수행하기 위해 다음을 수행합니다.

  1. 총 길이 lcm (length (A), length (B)) 가되도록 각 배열을 반복하십시오 . 여기서 lcm 은 최저 공배수를 나타냅니다.

    A -> [0 3 2 2  8 4][0 3  2 2 8 4]
    B -> [7 8 7 2][7 8  7 2][7 8 7 2]
    
  2. 반복 된 배열에서 요소 별 추가를 수행하고 그 중 하나가 잘린 모든 위치에서 결과를 자릅니다.

    A -> [0  3 2 2   8  4][0 3  2  2  8 4]
    B -> [7  8 7 2][ 7  8  7 2][7  8  7 2]
      -> [7 11 9 4][15 12][7 5][9 10 15 6]
    
  3. 이 배열 배열이 결과입니다.

작업

입력은 비어 있지 않은 2 개의 정수 배열이며 출력은 위에 정의 된대로 정렬을 추가 한 결과입니다. 입력 및 출력은 임의의 합리적인 형식 일 수 있습니다. 더하기를 수행 할 때 정수 오버플로에 대해 걱정할 필요가 없습니다.

규칙과 득점

전체 프로그램이나 함수를 작성할 수 있습니다. 가장 낮은 바이트 수가 이깁니다.

테스트 사례

[1] [4] -> [[5]]
[1,2,-3,-4] [15] -> [[16],[17],[12],[11]]
[0,-4] [2,1,0,-3] -> [[2,-3],[0,-7]]
[0,3,2,2,8,4] [7,8,7,2] -> [[7,11,9,4],[15,12],[7,5],[9,10,15,6]]
[18,17,16] [-1,-2,-3,-4] -> [[17,15,13],[14],[16,14],[15,13],[15],[16,14,12]]
[18,17,16,15] [-1,-2,-3,-4] -> [[17,15,13,11]]
[1,1,1,1,1] [6,5,6,5,6,5,6,2,1] -> [[7,6,7,6,7],[6,7,3,2],[7],[6,7,6,7,6],[7,3,2],[7,6],[7,6,7,6,7],[3,2],[7,6,7],[6,7,6,7,3],[2],[7,6,7,6],[7,6,7,3,2]]
[1,1,1,1,1,1] [6,5,6,5,6,5,6,2,1] -> [[7,6,7,6,7,6],[7,3,2],[7,6,7],[6,7,6,7,3,2]]
[1,1,1,1,1,1,1] [6,5,6,5,6,5,6,2,1] -> [[7,6,7,6,7,6,7],[3,2],[7,6,7,6,7],[6,7,3,2],[7,6,7],[6,7,6,7,3,2],[7],[6,7,6,7,6,7,3],[2],[7,6,7,6,7,6],[7,3,2],[7,6,7,6],[7,6,7,3,2],[7,6],[7,6,7,6,7,3,2]]

C는 배열의 길이를 알 수있는 방법이 없습니다-배열의 길이를 인수로 요청하거나 배열의 시작 부분에 저장할 수 있습니까?
cat

1
@cat 다른 길이 얻을 수 없다면 길이를 추가 인수로 취할 수 있습니다.
Zgarb

답변:


9

자바 스크립트 (ES6), 101 99 바이트

입력을 2 개의 배열로 취합니다. 문자열을 반환합니다.

f=(a,b,j=0,s='')=>a.map((v,i)=>(s+=i*j?' ':s&&'][',s+=b[j]+v,j=++j%b.length))|j?f(a,b,j,s):`[${s}]`

작동 원리

두 번째 배열에 다른 포인터 를 업데이트하는 동안 포인터 로 첫 번째 배열 a을 반복합니다 . 합계 는 출력 문자열에 추가됩니다 . 또는 마다 구분 기호가 삽입됩니다 . 반복이 시작될 때 정확하게 돌아올 때까지이 프로세스를 반복합니다.ijba[i] + b[j]si == 0j == 0jb

주 :|조작자가 적용되고 a.map(...)하나에 강제된다 NaN(경우 a또는 현재 값 이상의 원소를 함유) j(경우에 a정확히 하나의 원소를 포함). 따라서 a.map(...)|j == j모든 경우에 여기에서 사용하는 것이 안전합니다.

테스트 사례


나는 심지어에 대한 대답, +1 이해하는 시도하지 않은 메모를 . 필요할 때 복사하여 붙여 넣을 것입니다.
edc65

6

하스켈, 84 79 바이트

a#b=a%b where(c:d)%(e:f)|(x:y)<-d%f=(c+e:x):y;[]%[]=[[]];c%[]=[]:c%b;_%d=[]:a%d

첫 번째 버전은 읽기 쉬운 레이아웃에서 동일했습니다.

a#b=a%b where
 (c:d)%(e:f)|(x:y)<-d%f=(c+e:x):y
 []%[]=[[]]
 c%[]=[]:c%b
 _%d=[]:a%d

및에 (%)대한 추가 인수 를 제공하지 않기 위해 로컬 정의를 사용합니다 . 놀랍게도, 이것은 @nimi와 거의 동시에 거의 동일한 해결책이며, 로컬 정의에 한 줄만 사용한다는 아이디어를 얻었습니다.ab

용법:

*Main> [0,3,2,2,8,4] # [7,8,7,2]
[[7,11,9,4],[15,12],[7,5],[9,10,15,6]]

오, 이것이 목록의 첫 번째 요소에 합계를 추가하는 좋은 방법입니다. 성가신 것보다 훨씬 짧습니다 !.
nimi

4

PHP, 126120 바이트

function($a,$b){do{$c[$j][]=$a[$i%$x=count($a)]+$b[$i%$y=count($b)];++$i%$x&&$i%$y?:$j++;}while($i%$x|$i%$y);return$c;};

여기 사용해보십시오!

결과 배열 배열을 반환하는 익명 함수.

본질적으로 두 배열의 내용을 반복하여 배열 길이만큼 반복자를 모아서 '복사'를 시뮬레이션합니다. 배열에서 각 값을 가져 와서 합산하여의 배열에 추가합니다 $c. 입력 배열 중 하나의 끝 (도전 측면에서 분할)에 도달하면에서에 새 배열을 할당하기 시작 $c합니다.

do while루프 의 이유 는 조건이 $i에서 시작 하기 때문 0입니다. 처음에 조건을 확인하는 루프를 사용하면 루프가 실행되지 않습니다

우리는 동시에 두 배열의 끝에 도달하면 합산을 끝내고 LCM을 의미합니다.


그럴까요 $b[$i%$y]? ; $x=count($a)의 첫 번째 사용법으로 이동 하여 3 바이트를 절약 할 수 있습니다 $x. $y=count($b)비트 단위로 또는 while조건 에 따라 1 바이트와 동일
Titus

그러나 익명 함수는 스 니펫으로 간주되므로 유효한 답변이 아닙니다.
Titus

@Titus 익명 함수는 기본적으로 Meta에 대한 합의에 따라 허용됩니다 .
Zgarb

@Titus의 제안에 감사드립니다. 나는 다른 PHP 답변을 이길 원했기 때문에 이것을 함께 던졌습니다 : P
Xanderhall

4

하스켈, 87 84 바이트

a#b=a%b where[]%[]=[[]];(e:f)%(g:h)=f%h!(e+g);e%[]=[]:e%b;_%g=[]:a%g
(m:n)!l=(l:m):n

사용 예 : [0,3,2,2,8,4] # [7,8,7,2]-> [[7,11,9,4],[15,12],[7,5],[9,10,15,6]].

간단한 재귀. 기본 사례 : 두 목록이 모두 비어 있습니다. 둘 중 하나만 비어 있으면 정식 버전으로 다시 시작하고 출력에서 ​​새 클러스터를 시작하십시오. 비어있는 것이없는 경우 합계를 from 요소 앞에 추가하십시오.

@Christian Sievers의 답변 도 살펴보십시오.이 답변 은 거의 동일하며 몇 초 전에 게시되었습니다.


확실합니까? 정확한 시간을 얻는 방법이 있습니까?
Christian Sievers

@ChristianSievers : 시간을 직접 볼 수 있는지 모르겠습니다. 편집 시간이 몇 분 안에 나타 났을 때, 나는 당신보다 몇 초 일찍 (약 20 초) 계산 된 것을 기억합니다.
nimi

맞습니다 :이 페이지의 html 소스 코드에서 타임 스탬프를 찾았습니다
Christian Sievers

정확한 시간을 보려면 "2 일 전 답변"에 시간이 지남에 있습니다. (힌트 : 인터넷 전체의 표준 UI이므로 (a) 정확한 시간을 원하면 상대 시간을 호버링하고 (b) 상대 시간을 표시하는 무언가를 구현 한 경우 호버에 정확한 시간을 표시하십시오. !)
wchargin

2

옥타브, 113 바이트

@(a,b)mat2cell(sum([repmat(a,1,(L=lcm(A=numel(a),B=numel(b)))/A);repmat(b,1,L/B)]),1,diff(unique([0:A:L,0:B:L])))

이 함수는 괄호로 묶고 (@ (a, b) ...) ([1 2 3 4], [6 4 5])로 직접 호출 할 수 있습니다.


1
이제 TIO-Nexus는 Octave를 지원합니다. 다음 은 코드를 테스트
Luis Mendo

@LuisMendo 감사합니다, 재미있는 서비스
rahnema1

2

CJam , 30 바이트

{Sf*Laf+_s,f*:.+La/0=S2*a-Sa/}

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

입력을 한 쌍의 목록으로 가져옵니다.

설명

아이디어는 정렬 된 배열이 끝나는 위치와 배열에 나누기를 삽입 해야하는 위치를 나타내는 일부 마커를 입력 배열에 (짧은 문자열 형태로) 삽입하는 것입니다. 이런 식으로 LCM을 계산하지 않아도됩니다.

Sf*    e# Riffle each list with spaces. These are just place holders, so that having
       e# an array-end marker between two elements doesn't misalign subsequent elements.
Laf+   e# Append an empty string to each list. This is the array-end marker.
_s,    e# Convert the pair of lists to a string and get its length. This is always
       e# greater than the number of elements in either input.
f*     e# Repeat either array that many times. This is definitely more than necessary
       e# to reach the LCM (since multiplying by the length of the other list always
       e# gives a common multiple).
:.+    e# Pairwise addition of the list elements. There are four cases:
       e# - Both elements are numbers, add them. This is the actual addition
       e#   we need for the problem.
       e# - Both elements are spaces. This is just a regular position between
       e#   list elements.
       e# - One is a space, one is empty: the result is a single space, and
       e#   this marks a position where one of the arrays ended, which means
       e#   we need to split here.
       e# - Both elements are empty. This happens at the LCM of both list lengths
       e#   and indicates where we need to stop the output.
La/0=  e# Split the input around empty strings and discard everything except
       e# the first chunk.
S2*a-  e# Remove the double-space strings, we no longer need them.
Sa/    e# Split the list around single spaces.

2

젤리 , 21 20 18 바이트

ṁ€L€æl/$S
J€ỊÇœṗÇḊ

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

작동 원리

ṁ€L€æl/$S  Helper link. Argument [X, Y] (arrays of integers).

       $   Combine the two links to the left into a monadic chain.
  L€       Length each; yield the lengths of X and Y.
    æl/    Reduce by least common multiple.
ṁ€         Mold each; cyclically repeat the elements of X and Y to extend them
           to length lcm(length(X), length(Y)).
        S  Compute the sum of the extended X and Y arrays.

J€ỊÇœṗÇḊ   Main link. Argument [A, B] (arrays of integers).

J€         Indices each; replace A and B by the arrays of there 1-based indices.
  Ị        Insignificant; map 1 to itself, all other indices to 0.
   Ç       Apply the helper link to the result.
           This yield a Boolean array with a 1 (or 2) at all indices where a new
           repetition of A or B (or both) begins.
      Ç    Apply the helper link to [A, B].
    œṗ     Partition; break the result to the right at truthy elements (1 or 2) in
           the result to the right.
       Ḋ   Dequeue; remove the first element of the partition (empty array).

2

파이썬 3.5 - ( 146 (137) 134 130 + 12) = 142 바이트

import math
def s(a,b):
 l,k,*r=map(len,[a,b])
 for i in range(l*k//math.gcd(l,k)):
  r+=a[i%l]+b[i%k],
  if i%k==k-1or i%l==l-1:print(r);r=[]

전체 for 루프를 한 줄에 넣는 방법을 알 수 없습니다.

편집 :

  • 덕분에 zgarb 9 바이트를 저장하는!
  • 감사합니다 vaultah 3 바이트를 절약!
  • 덕분에 mathmandan 5 바이트를 저장!

이것은 나에게 오류를 제공합니다 . gcd기능에 fractions하지 math.
Zgarb

@Zgarb 분수 단위의 gcd 모듈은 더 이상 사용되지 않습니다 . 여기서 변경 사항을 확인할 수 있습니다 . 나는 rexter가 이전 버전을 사용하고 있다고 생각한다 3.4.3.
Gurupad Mamadapur

깔끔하게, 나는이 변화에 대해 몰랐다. 3.4 이전 버전에서는 작동하지 않으므로 언어를 "Python 3.5"로 표시해야합니다. 또한, 주위에 괄호를 놓을 수 있습니다 l*k및이 print(r);r=[]마지막 줄에.
Zgarb

바이트 수가 정확합니까? 145 바이트 만 있다고 생각합니다.
vaultah

1
142 바이트를 얻고 있습니다. Windows를 사용하고 있습니까? Windows는 일반적으로 개행을 각각 2 바이트로 계산하지만 여기서 각 개행은 단일 바이트로 계산됩니다.
mathmandan

2

파이썬 2, 119 바이트

a=input()
i,v,l=0,list(a),len
while 1:q=l(v[0])>l(v[1]);print map(sum,zip(*v)[i:]);i=l(v[q]);v[q]+=a[q];1/(i-l(v[q^1]))

쉼표로 구분 된 두 개의 튜플로 stdin에서 입력을 가져 와서 결과 목록을 stdout으로 출력합니다. 허용ZeroDivisionError 되는 것처럼 보이기 때문에 예외 를 제기하여 종료합니다 .

예를 들어, 입력이 (0, 3, 2, 2, 8, 4), (7, 8, 7, 2)인 경우 프로그램은

[7, 11, 9, 4]
[15, 12]
[7, 5]
[9, 10, 15, 6]

stdout에 대한 예외 추적 및 stderr에 대한 예외 추적


오류가 발생하여 프로그램을 종료 할 수 있습니다 . 그러면 루프를 한 줄로 만들 수 있습니다.
Zgarb

2

J , 34 32 바이트

[:(<;.1~*)/[:+/*.&#$&>,:&(;2>#\)

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

설명

[:(<;.1~*)/[:+/*.&#$&>,:&(;2>#\)  Input: array A (LHS), array B (RHS)
                             #\   Length of each prefix of A and B
                           2>     Less than 2
                          ;       Link each with A and B
                      ,:&         Pair them
                  #               Length of A and B
               *.&                LCM of the lengths
                    &>            For each box
                   $              Reshape it to the LCM of the lengths
           [:+/                   Reduce by addition
[:        /                       Reduce by
        *                           Sign of RHS
   <;.1~                            Box each partition of LHS

1

하스켈, 166 바이트

이것은 아마도 가장 우아한 접근 방식이 아닐 것입니다. 기본적으로 함수 ?는 필요한 길이의 %합계 를 하나의 목록으로 만들고이 합계를 다시 잘라냅니다. !이 둘을 병합하는 최종 함수입니다.

l=length
a?b=take(lcm(l a)$l b)$zipWith(+)(cycle a)$cycle b
l%(i:ind)|l==[]=[]|1>0=take i l:(drop i l)%(map(+(-i))ind)
a!b=(a?b)%[k|k<-[1..],k`mod`l a<1||k`mod`l b<1]

당신은 대체 할 수 indk또는 뭔가, 거기에 불필요한 괄호는 주위 drop i lmap(+(-i))ind. %패턴 일치가 설정된 두 가지 경우도 고려해야 합니다 l.
Zgarb

1

[PHP] 183 152 135 바이트

function O($A,$B){while($f<2){$O[$k][]=$A[+$i]+$B[+$j];$f=0;isset($A[++$i])?:$i=!++$k|!++$f;isset($B[++$j])?:$j=!++$k|!++$f;}return$O;}

좋은 버전 :

function O($A,$B)
{
    while($f<2) {
        $O[$k][]=$A[+$i]+$B[+$j];
        $f=0;
        isset($A[++$i])?:$i=!++$k|!++$f;
        isset($B[++$j])?:$j=!++$k|!++$f;
    }

    return$O;
}

산출:

array (size=4)
  0 => 
    array (size=4)
      0 => int 7
      1 => int 11
      2 => int 9
      3 => int 4
  1 => 
    array (size=2)
      0 => int 15
      1 => int 12
  2 => 
    array (size=2)
      0 => int 7
      1 => int 5
  3 => 
    array (size=4)
      0 => int 9
      1 => int 10
      2 => int 15
      3 => int 6

이 조정을 사용하여 나와 함께 그리기 : 추가 할당 (-8 바이트)의 배열 인덱스 등에 등을 $i=$j=$k=0;사용하는 경우 불필요합니다 +$i. $i++;if(!isset($A[$i])){$i=0;$k++;}-> isset($A[++$i])?:$i=!++$k;(-9, 두 번). $i==0&&$j==0&&!isset()-> !$i&!$j&!isset()(-6). return$O;공간이 필요 없습니다 (-1).
Titus

$i=$j=0;배열의 첫 번째 값이 정확하지 않기 때문에 @Titus는 부분을 제거 할 수 없습니다 . 이 경우 논리를 조금 수정하여 삼항 연산자를 구현하는 방법을 모르겠습니다. ++$i조언 감사합니다 .
Dexa

시도하십시오 unset($i);$A[+$i]. 는 +캐스팅됩니다 null정수로 0.
Titus

if(!isset($A[++$i])){$i=0;++$k;++$f;}->는 isset($A[++$i])?:$i=!++$k|!++$f;여전히 각각 5 바이트를 저장합니다. $f<2대신에 하나 더 저장하십시오 $f!=2. while($f=$f<3){...}대신에 다른 두 개 while($f<2){$f=0;...}( $f두 번 증가하지 않으면 초기화 및 1로 재설정 )
Titus

@Titus 감사합니다. 이제 더 짧아졌습니다.
Dexa

1

PowerShell , 147145 바이트

param($a,$b)$o=@{};do{$o[+$j]+=,($a[+$i%($x=$a.count)]+$b[$i++%($y=$b.count)]);if(!($i%$x-and$i%$y)){$j++}}until(($x,$y|?{!($i%$_)}).count-eq2)$o

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

( 골프 제안을 환영합니다. 짜낼 수있는 다른 10-15 바이트가 있다고 생각합니다. )

@(...)명령 행 인수로 입력을 두 개의 명시 적 배열 ( 구문 포함)로 사용합니다 . PowerShell의 다차원 배열이 이상 해져 일관성이 있기 때문에 결과 배열의 해시 테이블을 반환합니다. 초기 변수를 설정 한 다음 배열lcm 이 될 때까지 조건부로 do/ until루프를 다시 입력 합니다 .$i

각 루프 반복은 해당 $a$b값을 함께 ,(...)추가 $o하고 적절한 spot에서 해시 테이블 에 추가하기 전에 배열로 취급합니다 $j. 산술 덧셈을 방지하기 위해 배열 캡슐화가 필요합니다. 이렇게하면 +=대신 배열 연결에 과부하가 걸리게됩니다. 그런 다음 조건부 켜기 $x$y(카운트)를 통해 배열 가장자리에 있는지 확인합니다 $j.

마지막으로 $o파이프 라인 을 그대로두고 출력은 암시 적입니다.
(NB : PowerShell Write-Output이 기본값으로 해시 테이블을 열거하는 방식으로 인해 "역방향"으로 출력되는 경향이 있습니다. "0 번째"결과 배열은 출력의 "하단"에 있습니다. 해시 자체는 양호하며 예를 들어,이 코드를 반환 변수에 캡슐화하면 잘 사용됩니다. 인쇄 될 때 이상하게 보입니다.)

$ x와 $ y를 분리하지 않고 배열 인덱싱으로 이동하여 2 바이트를 절약했습니다 (두 개의 세미콜론 저장).


1

파이썬 2, 113 바이트

a,b=input()
i=m=n=0;r=[]
while(not i)+m+n:r+=[[]]*(not m*n);r[-1]+=[a[m]+b[n]];i+=1;m=i%len(a);n=i%len(b)
print r

대신에 notS가 될 수 <1있습니까?
Zgarb

1

파이썬 3.5 210 176 173 169 158 바이트

def f(a,b):
 x=[];e=f=0              
 while 1:
  if e==len(a):         
   print(x);x=[];e=0;
   if f==len(b):break
  if f==len(b):print(x);x=[];f=0
 x+=a[e]+b[f],;e+=1;f+=1

두 개의 목록을 입력으로 취하고 모든 목록을 인쇄합니다.

첫 번째 대답이며 아직 골프를 치는 법을 모르겠습니다. 내가 사용한 기본 아이디어는 각 목록마다 추가 된 값이 추가되는 분할 및 현재 목록을 나타내는 두 개의 카운터를 갖는 것입니다. 분할이 발생하자마자 현재 목록을 인쇄하고 비어있는 새 목록을 만듭니다.

  • 34 바이트 절약 : DennisTimmyD 덕분에
  • 3 바이트 저장 : len (a) 및 len (b)에 c와 d를 사용하고 있었지만 유용하지 않은 것으로 나타났습니다.
  • 4 바이트 절약 : orlp 덕분에 원치 않는 마비 제거
  • 11 바이트 저장 : 일부 블록을 재 배열하여 크런치

1
안녕하세요, Programming Puzzles & Code Golf에 오신 것을 환영합니다! 비경쟁은 여기서 다른 것을 의미합니다. 당신은 그것을 제거해야합니다. 공백을 제거하여 상당히 많은 바이트를 절약 할 수 있습니다. 예를 들어 2 ~ 5 행이 될 수 있습니다 x=[];c=len(a);d=len(b);e=f=0. 또한 true이 될 수 있습니다 1, 그리고 x.append(a[e]+b[f])될 수 있습니다 x+=a[e]+b[f],.
Dennis

1
PPCG에 오신 것을 환영합니다! Dennis의 특정 조정 외에도 Python의 골프 팁을 확인하여 일반적인 힌트와 요령을 확인하십시오.
AdmBorkBork

1
if그리고 while진술은 괄호가 필요하지 않습니다.
orlp

1

라켓 373 바이트

(let*((lg length)(fl flatten)(ml make-list)(t rest)(r reverse)(m modulo)(o cons)(ln(lg l))(jn(lg j))(c(lcm ln jn))(l2(fl(ml(/ c ln)l)))
(j2(fl(ml(/ c jn)j)))(ll(for/list((a l2)(b j2))(+ a b))))(let p((ll ll)(ol '())(tl '())(n 0))(cond[(empty? ll)(t(r(o(r tl)ol)))]
[(or(= 0(m n ln))(= 0(m n jn)))(p(t ll)(o(r tl)ol)(take ll 1)(+ 1 n))][(p(t ll)ol(o(first ll)tl)(+ 1 n))])))

언 골프 드 :

(define(f l j)
  (let* ((ln (length l))
         (jn (length j))
         (c (lcm ln jn))
         (l2 (flatten (make-list (/ c ln) l)))
         (j2 (flatten (make-list (/ c jn) j)))
         (ll (for/list ((a l2)(b j2))
               (+ a b))))

    ; TO CUT LIST INTO PARTS: 
    (let loop ((ll ll)
               (ol '())
               (templ '())
               (n 0))
      (cond
        [(empty? ll) 
         (rest (reverse (cons (reverse templ) ol)))]
        [(or (= 0 (modulo n ln))
             (= 0 (modulo n jn)))
         (loop (rest ll)
               (cons (reverse templ) ol)
               (list (first ll))
               (add1 n))]
        [(loop (rest ll)
               ol
               (cons (first ll) templ)
               (add1 n))]))))

테스트 :

(f '[1]  '[4])
(f '[1 2 -3 -4] '[15])
(f '[0 3 2 2 8 4]  '[7 8 7 2])

산출:

'((5))
'((16) (17) (12) (11))
'((7 11 9 4) (15 12) (7 5) (9 10 15 6))

1

클로저, 280206 바이트

(fn[a b](let[A(count a)B(count b)Q quot](map #(map last %)(partition-by first(take-while #((% 0)2)(map-indexed(fn[i s][[(Q i A)(Q i B)(or(= i 0)(>(mod i A)0)(>(mod i B)0))]s])(map +(cycle a)(cycle b))))))))

글쎄 이것은 훨씬 더 의미가 있습니다. 요소 별 합계를 생성하고 위치 메타 데이터를 추가하며 아직 반복하지 않은 상태에서 각 파티션에 합계 값을 넣습니다.

(def f (fn[a b]
         (let[A(count a)B(count b)Q quot]
           (->> (map +(cycle a)(cycle b))
                (map-indexed (fn [i s][[(Q i A)(Q i B)(or(= i 0)(>(mod i A)0)(>(mod i B)0))]s]))
                (take-while #((% 0)2))
                (partition-by first)
                (map #(map last %))))))

독창적 : 나는 이것을 개선하기를 바라고 있지만 이것은 내가 지금 가지고있는 가장 정렬 된 것이다.

(fn[a b](let [C cycle o count c(take-while #(or(=(% 0)0)(>(% 1)0)(>(% 2)0))(map-indexed(fn[i[A B]][i(mod i(o a))(mod i(o b))(+ A B)])(map(fn[& v]v)(C a)(C b))))](map #(map last %)(partition-by first(map(fn[p c][p(last c)])(reductions + (map #(if(or(=(% 1)0)(=(% 2)0))1 0)c))c)))))

풀리지 않고 자세하게 :

(def f (fn[a b]
         (let [c(->> (map (fn[& v]v) (cycle a) (cycle b))
                     (map-indexed (fn[i[A B]][i (mod i(count a)) (mod i(count b)) (+ A B)]))
                     (take-while #(or(=(% 0)0)(>(% 1)0)(>(% 2)0))))]
           (->> (map (fn[p c][p(last c)]) (reductions +(map #(if(or(=(% 1)0)(=(% 2)0))1 0)c)) c)
                (partition-by first)
                (map #(map last %))))))

컬렉션의 무한 사이클을 "병합"하여 시작 하고 컬렉션 내의 각 요소 인덱스에 메타 데이터를 추가 a하고 b두 시퀀스가 ​​인덱스 0에서 다시 시작될 때까지 가져옵니다.

c그런 다음 이 컬렉션 은 파티션 데이터 (1과 0의 누적 합계)와 병합되고 분할되고 마지막 요소 (항목의 합계)가 선택됩니다.

나는 상당한 개선을 위해 완전히 다른 접근법이 필요하다고 생각합니다.


1

PHP, 150 (121) 119 바이트

function($a,$b){while($i<2|$x|$y)$r[$k+=!($x=$i%count($a))|!$y=$i++%count($b)][]=$a[$x]+$b[$y];array_pop($r);return$r;}

익명 함수는 입력을 배열로받습니다.

고장

while($i<2|$x|$y)   // loop while either $a or $b has NO cut
    $r[
                // if either $a or $b has a cut, increment $k; post-increment $i
        $k+=!($x=$i%count($a))|!$y=$i++%count($b)
                // append current $a + current $b to $r[$k]
    ][]=$a[$x]+$b[$y];
array_pop($r);  // $r has one element too much; remove it
return$r;

0

C ++ 14, 206 바이트

이름 일반 람다, 필요한 입력 컨테이너로 P, Q출력 용기 R같을 vector<vector<int>>.

[](auto P,auto Q,auto&R){R.clear();auto a=P.begin(),b=Q.begin(),x=P.end(),y=Q.end();auto A=a,B=b;do{R.emplace_back();while(a!=x&&b!=y)R.back().push_back(*a+++*b++);a=a==x?A:a;b=b==y?B:b;}while(a!=A||b!=B);}

언 골프 및 사용법 :

#include<vector>
#include<iostream>

using namespace std;

auto f=
[](auto P,auto Q,auto&R){
 R.clear();               //just clear the output to be sure
 //a and b are the iterators, x and y is the end
 auto a=P.begin(),b=Q.begin(),x=P.end(),y=Q.end();
 //just some abbreviations for .begin()
 auto A=a,B=b;
 do{
  R.emplace_back();      //add new vector
  while(a!=x&&b!=y)      //while not at the end of one vector
   R.back().push_back(*a+++*b++);  //add the pointed elements and advance
  a=a==x?A:a;            //reset if at the end   
  b=b==y?B:b;
 }while(a!=A||b!=B);     //if both were resetted, then finish
}
;


int main(){
 vector<int> A = {0, 3, 2, 2, 8, 4};
 vector<int> B = {7, 8, 7, 2};
 vector<vector<int>> R;
 f(A,B,R);
 for (auto c:R){
  for (int x:c)
   cout << x << ", ";
  cout << endl;
 }
 cout << endl;
}

0

매스 매 티카 112 바이트

이것은 아마도 향상 될 수 있습니다. 아이디어는 카운터의리스를 추적하는 데 사용되는 두 번째 요소로 각 입력 배열의 길이를 조정하여 2D 배열을 만드는 것입니다.

Split[Table[{#[[1,(m=Mod[i,d=Length/@#,1])[[1]]]]+#[[2,m[[2]]]],Min@m},{i,LCM@@d}],#2[[2]]>#1[[2]]&][[;;,;;,1]]&

용법

%@{{0,3,2,2,8,4},{7,8,7,2}}

0

자바 스크립트 (ES6), 131 바이트

(a,b,g=(r,[n,...d]=a,[m,...e]=b,s=[])=>1/n?1/m?g(r,d,e,[...s,n+m]):g([...r,s],[n,...d]):1/m?g([...r,s],a,[m,...e]):[...r,s])=>g([])

약간 골퍼되지 않음 :

(a,b,r=[],[n,...d]=a,[m,...e]=b,s=[])
=>1/n?1/m?f(a,b,r,d,e,[...s,n+m])
         :f(a,b,[...r,s],[n,...d],b,[])
     :1/m?f(a,b,[...r,s],a,[m,...e],[])
         :[...r,s]
  • 두 경우 어레이 de숫자를 포함하는, 제 개수의 합에 추가되어 s, 나머지 요소는 재귀 처리
  • 배열 중 하나에 숫자가 포함 된 경우 합계 배열이 s결과에 추가되고 r다른 배열은 초기 배열로 재설정됩니다
  • 두 배열이 모두 비어 있으면 마지막 합계가 추가 된 결과 만 반환하면됩니다.

슬프게도이 솔루션에는 @Arnauld의 무자비한 효율성이 없지만 적어도 아름다운 솔루션이라고 생각합니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.