リストを半分に折ります


24

整数のリストを折りたたみます。これを行う手順は次のとおりです。リストの長さが偶数の場合、新しいリストのn番目の項目が古いリストのn番目の項目とn番目からn番目までの合計の長さの半分のリストを作成します古いリストの最後のアイテム。たとえば、リストがある場合

[1 2 3 4 5 6 7 8]

折ります

 [8 7 6 5]
+[1 2 3 4]
__________
 [9 9 9 9]

リストの長さが奇数の場合、折りたたむには、まず中間のアイテムを削除し、偶数のように折り、結果に中間のアイテムを追加します。

たとえば、リストがある場合

[1 2 3 4 5 6 7]

折ります

 [7 6 5]
+[1 2 3]
__________
 [8 8 8]
++     [4]
__________
 [8 8 8 4]

仕事

入力として整数のリストを取り、そのリストを折りたたんで出力するプログラムまたは関数を作成します。

これは質問なので、回答はバイト単位でスコアリングされ、バイト数は少ない方が良いでしょう。

サンプル実装

以下fは、折り畳みを実行する関数を定義するHaskellの実装です。

f(a:b@(_:_))=a+last b:f(init b)
f x=x

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


整数と言うとき、これにはゼロまたは負の整数が含まれますか?
ニール

1
@Neilはい。
小麦ウィザード

2
@GrzegorzPuławskiリストをソートしないでください。ベクトルや配列など、順序付けられたコレクションが許可されます。
小麦ウィザード

1
@DavidStarkeyほとんどの妥当なリストは、妥当な量のメモリでオーバーフローしません。折りたたみは実際には合計を増加させないため、リストは元のリストの合計のシングルトンに収束します。
小麦ウィザード

2
@WheatWizardそれについては知りませんが、リストを7回以上半分に折り畳むことは不可能だと聞いています。
カーマイスター

回答:


9

Python、46バイト

f=lambda l:l[1:]and[l[0]+l[-1]]+f(l[1:-1])or l

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

同じ長さ:

f=lambda l:l[1:]and[l.pop(0)+l.pop()]+f(l)or l

偶数のリスト(30バイト)には、はるかに短いソリューションが機能します

lambda l:[x+l.pop()for x in l]

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

私はまだそれを奇数の長さに修正する短い方法を見つけようとしています。


ああ、ひどくアウトゴルフされた÷_÷
Xcoder氏17

「中間」ソリューションf=lambda l:l[1:]and[l[0]+l.pop()]+f(l[1:])or lも同じ長さです
...-ETHproductions


8

絵文字コード、203バイト

🐋🍨🍇🐖🔢🍇🔂i⏩0➗🐔🐕2🍇😀🔡➕🍺🔲🐽🐕i🚂🍺🔲🐽🐕➖🐔🐕➕1i🚂10🍉🍊😛1🚮🐔🐕2🍇😀🔡🍺🔲🐽🐕➗🐔🐕2🚂10🍉🍉🍉

これは私にとってコードに対する最も苦痛な絵文字コードの回答でした。不要な長さ:/

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



3

ガイア、7 バイト

e2÷ev+†

説明

e        Eval the input (push the list).
 2÷      Split it in half. The first half will be longer for an odd length.
   e     Dump the two halves on the stack.
    v    Reverse the second.
     +†  Element-wise addition. If the first half has an extra element, it is simply appended.

2

Mathematica、88バイト

(d=Array[s[[#]]+s[[-#]]&,x=⌊t=Length[s=#]/2⌋];If[IntegerQ@t,d,d~AppendTo~s[[x+1]]])&

2

Mathematica 57バイト

(#+Reverse@#)[[;;d-1]]&@Insert[#,0,d=⌈Length@#/2⌉+1]&

中間点にゼロを挿入し、その逆にリストを追加し、適切な長さを取ります。










1

MATL、9バイト

`6L&)swtn

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

使い方

配列[a b c ... x y z][a z]指定すると、「クラスト」サブアレイおよび[b c ... y z]「コア」サブアレイと呼ばれます。

コードは、クラストを削除し、その合計を計算し、コアをスタックの最上部に移動して、次の反復の準備ができるループで構成されます。ループ条件は、コアサブアレイ内の要素の数です

`       % Do...while
  6L    %   Push [2 -1+1j]. As an index, this is interpreted as 2:end-1
  &)    %   2-output reference indexing: pushes a subarray with the indexed 
        %   elements (core) and another with the ramaining elements (crust)
  s     %   Sum of (crust) subarray
  w     %   Swap. Moves the core subarray to the top
  t     %   Duplicate
  n     %   Number of elements.
        % End (implicit). Procced with next iteration if top of the stack is
        % nonzero; else exit
        % Display stack (implicit)


1

C#(.NET Core)118 111バイト

a=>a.Reverse().Zip(a,(c,d)=>c+d).Take(a.Length/2).Concat(a.Skip(a.Length/2).Take(a.Length%2))

バイト数も含まれます

using System.Linq;

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

入力として、コンマ(,)またはスペースで区切られた数字を使用してください。説明:

a =>                                  // Take one input parameter (array)
a.Reverse()                           // Reverse it
.Zip(a, (c, d) => c + d)              // Take every corresponding member of reversed
                                      //    and original, and add them together
.Take(a.Length / 2)                   // Get first half of the collection
.Concat(                              // Add another collection
    a.Skip(a.Length / 2)              // Take input and leave out first half of it
    .Take(a.Length % 2)               // If length is odd, take first element (so the middle)
                                      //    otherwise create an empty collection
);

長さを変数に設定し、明示的な戻り値に切り替えることでバイトを節約できますか?
TheLethalCoder

@TheLethalCoder残念ながらそれは長いです
グジェゴシPuławski

1

Perl、42 38文字

sub f {@ a = map {$ + pop} splice @、0、@ / 2; @ a、@ }

sub f{(map{$_+pop}splice@_,0,@_/2),@_} 

たとえば次のようにしてみてください。

perl -e 'my @input=(1..9); sub f{(map{$_+pop}splice@_,0,@_/2),@_}  print join(",",f(@input));

1
私の感情的で専門的な変数への愛着のために忍び込んだエラーを修正しました。JSによるアウトゴルフの拒否:P
bytepusher

1

Pyth、18 17 13バイト

V.Tc2Q aYsN;Y

私の最初のアプローチは

WtQ aY+.)Q.(Q0;+Y

Xcoder氏のおかげで-1バイト

FryAmTheEggmanのおかげで-4バイト


c2<list>リストを半分に分割して使用してみてください。役に立つかもしれない別のコマンドは.Tです。
-FryAmTheEggman


1

C ++ 17、75 73 71バイト

名前のないラムダとして、vectorまたはのようなコンテナを受け入れるとlist、入力を変更して戻ります。

[](auto&L){for(auto a=L.begin(),b=L.end();a<--b;L.pop_back())*a+++=*b;}

よく知られている「goes-to」演算子<--とトリプルプラスの使用+++

Ungolfedと例:

#include<iostream>
#include<vector>

using namespace std;

auto f=
[](auto&L){
 for(
  auto a=L.begin(),b=L.end();
  a<--b;
  L.pop_back()
 )
 *a+++=*b;
}
;

void test(auto L) {
 for(auto x:L)cout << x << ", ";
 cout << endl;
 f(L);
 for(auto x:L)cout << x << ", ";
 cout << endl << endl;
}

int main() { 
 vector<int> A = {1,2,3,4,5,6,7,8}, B = {1,2,3,4,5,6,7};
 test(A);
 test(B);
}


1

APL(Dyalog Unicode)、21 バイトSBCS

@Adámのおかげで-3バイト。

(⌊2÷⍨≢)(↑{+⌿↑⍺⍵}∘⌽↓)⊢

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

説明:

(⌊2÷⍨≢)(↑{+⌿↑⍺⍵}∘⌽↓)⊢   Monadic function train
(⌊2÷⍨≢)                   Left portion:
                         Take the length of the input...
  2÷⍨                     Divide it by two...
                         And floor it. This gives our midpoint index. Call it "X"
                         Right portion: return the original input. Call it "Y"
       (↑{+⌿↑⍺⍵}∘⌽↓)    Midddle portion: takes X and Y as arguments
                        Take and drop Y by X. Essentially splits Y in half
                          Presents the two halves to the next function
                 ∘⌽      Reverse the second half
         {+⌿↑⍺⍵}        Final function, takes first half and reversed second half
              ⍺⍵         Construct a nested list of first and second halves...
                        ...and "mix" them into a matrix. Has the nice property that
                         it will pad the first half with a zero if needed.
          +⌿            Sum the matrix along the columns, return resulting vector

:Dyalogは、18バイトの拡張+⌿(⌊2÷⍨≢)(↑↑⍮⌽⍤↓)⊢
アダム

21バイト、トレーニング:(⌊2÷⍨≢)(↑{+⌿↑⍺⍵}∘⌽↓)⊢`
アダム



0

Scala、91バイト

(s:Seq[Int])=>(s.take(s.size/2),s.reverse).zipped.map(_+_)++s.drop(s.size/2).take(s.size%2)


0

JavaScript(ES6)、46 43バイト

f=(a,[b,...c]=a)=>c+c?[b+c.pop(),...f(c)]:a

Asafからインスピレーションを得て3バイトを節約しました。


いいね 「1 / c [0]」を「[] + c」に変更して、2バイト節約できます。
アサフ

@Asaf実際にc+cは、3バイト目で動作すると思います。
ニール

0

Java 8、93バイト

二桁!これはを受け取り、int[]を返すラムダですint[]

l->{int n=l.length,i=0;for(;i<n/2;)l[i]+=l[n-++i];return java.util.Arrays.copyOf(l,n/2+n%2);}

ゴルフされていないラムダ

l -> {
    int n = l.length, i = 0;
    for (; i < n / 2; )
        l[i] += l[n - ++i];
    return java.util.Arrays.copyOf(l, n / 2 + n % 2);
}

とても簡単です。入力の前半に所定の位置で後半を折り返し、前半のみのコピーを返します。

驚いたことに、returnステートメントの配列コピーは、奇数長の入力に対する最終的な要素の癖を処理する最も安価な方法のようです。


弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.