無限の言葉を見つけよう!


36

(注:これは、以前の課題Find the Swirling Wordsから派生したものです!

Infinity Wordの定義:

  1. アルファベット(AZ)上の無限大単語のすべての文字を曲線でつなぐと、下の図のように無限大記号∞が得られます。
  2. すべての偶数接続がダウンしていなければならず、すべての奇数接続がアップしていなければなりません。
  3. 大文字/小文字を無視するか、すべてを大文字に変換するか、すべて小文字に変換/変換することができます。
  4. 入力単語は、A〜Zのアルファベット範囲の文字のみで、スペース、句読点、記号は使用できません。
  5. 各単語は正確に5文字でなければなりません。5文字以上または5文字未満の単語は無効です。
  6. 単語に二重連続文字がある場合、「FLOOD」や「QUEEN」のように、単語は無効です。
  7. すべての無限語は同じ文字で始まり、同じ文字で終わります。

ここにいくつかの例があります:

無限の言葉

仕事:

標準入力から単語を取得し、Infinity Wordかどうかを出力する完全なプログラムまたは関数を作成します。出力はtrue / false、1 / 0、1 / Nullなどです。

テストケース:

Infinity Words:
ALPHA, EAGLE, HARSH, NINON, PINUP, RULER, THEFT, WIDOW

NOT Infinity Words:
CUBIC, ERASE, FLUFF, LABEL, MODEM, RADAR, RIVER, SWISS, TRUST, 
KNEES, QUEEN, GROOVE, ONLY, CHARACTER, OFF, IT, ORTHO

ルール:

  1. 最短のコードが優先されます。

オプションのタスク:

リストとして、英語の辞書でできる限り多くのInfinity Wordsを見つけてください。たとえば、ここで英語の単語の完全なリストを参照することができます


入力は常に長さ5であると想定できますか?ルール5を定義しました:「各単語は正確に5文字でなければなりませ。5文字以上または5文字未満の単語は無効です。」が、5文字未満または5文字を超える無限単語は使用できません
ケビンCruijssen

4
アルファがそのパターンを作ることはかなり面白いです
16年

@KevinCruijssenあなたは言葉が定義を尊重していることを確認しなければなりません、私は虚偽のケースを更新しました。
マリオ

1
@Arnauld 5個の「A」は自分自身に接続し(またはまったく移動しない)、1つのポイントを作成し、無限大記号を描画しないため、ポジティブなケースではないと思います。
マリオ

3
「リストとして、英語の辞書でできる限り多くのInfinity Wordsを見つけてください...」このタスクKevin Cruijssenの回答を使用し、278 Infinity Wordsのこのリストを作成しました。
トーマスクインケリー

回答:


19

ゼリー43 41 40 25 24 23 22 21 14 13 バイト

fireflame241のおかげで-7バイト(0ị=1ị$-> =ṚḢおよびIIA⁼2,24回転のテストに使用)

-1 Kevin Cruijssenに感謝(以前は利用できなかったnilad Ø2を使用してを生成[2,2]

=ṚḢȧOIṠIIA⁼Ø2

TryItOnline
またはすべてのテストケース(および「ルール」)

どうやって?

無限の単語には次のものがあります。

  1. 同じ最初と最後の手紙;
  2. 長さ5;
  3. 隣り合う等しい文字はありません。
  4. ゼロに等しい4つのアルファベットのデルタの合計。
  5. ゼロに等しい4つのアルファベットのデルタ記号の合計。
  6. 連続した2つの正のアルファベットデルタまたは2つの負のアルファベットデルタ。

(1)と(同等に)(4)を除くすべては、アルファベットのデルタ記号が[1,1,-1,-1]0です0

fireflame241は、これは、アルファベットのデルタ記号のデルタのデルタ[[2,2],[2,-2],[-2,2],[-2,-2]]と同等であり、その絶対値は[2,2]

どうやって?

=ṚḢȧOIṠIIA⁼Ø2 - Main link: word
 Ṛ            - reverse word
=             - equals? (vectorises)
  Ḣ           - head (is the first character equal to the last?)
   ȧ          - and
    O         - cast word to ordinals
     I        - increments - the alphabet deltas (or just [] if 1st != last)
      Ṡ       - sign (vectorises)
       I      - increments - deltas of those signs
        I     - increments - deltas of those
         A    - absolute value (vectorises)
           Ø2 - literal [2,2]
          ⁼   - equals? (non-vectorising version)

これはどのように作動しますか?
オリバーNi

入ってくる説明。
ジョナサンアラン

2
@PascalvKootenそれは主に楽しみのためであり、コードゴルフで競争力があることです-私はコードゴルフとジェリーの両方にかなり新しいので、ゼリープログラムをまとめることはほとんど毎回小さなパズルのようです。満足です。このゲームから具体的なものを取得したい場合は、実際の世界でより一般的に使用されている言語でスキルを磨くためにそれを使用するか、もちろん、自分のゴルフ言語を作成する必要があります!
ジョナサンアラン

1
@ lois6b :)。チュートリアルから始めて、Atom定義Quicks定義を含むページを使用し、ソースコードを参照します
ジョナサンアラン

1
14バイトここのメインゴルフはII、1,1、-1、-1の回転と等しいかどうかをチェックするために使用します。
fireflame241

11

ジャワ8、231の 193 185 122 103 78バイト

s->s.length==5&&(s[1]-s[0])*(s[3]-s[2])<0&(s[2]-s[1])*(s[4]-s[3])<0&s[4]==s[0]

ここで試してみてください。

-dbyteのchar[]代わりにを使用することを思い出させてくれた@ dpa97に感謝しますString@KarlNapfの派生式の
おかげで-63バイト。 Java 7からJava 8に変換することにより、-25バイトになりました(整数ではなくブール値を返すようになりました)。

193バイトの答え:

int c(char[]s){if(s.length!=5)return 0;int a=s[0],b=s[1],c=s[2],d=s[3],e=s[4],z=b-a,y=c-b,x=d-c,w=e-d;return e!=a?0:(z>0&y>0&x<0&w<0)|(z<0&y>0&x>0&w<0)|(z>0&y<0&x<0&w>0)|(z<0&y<0&x>0&w>0)?1:0;}

説明:

  • 文字列の長さが5でない場合は、戻ります false
  • 最初の文字が最後の文字と等しくない場合、戻ります false
  • 次に、4つの有効なケースを1つずつ確認し(5文字を1から5として示しましょう)、trueいずれかに該当する場合(およびfalseそうでない場合)に戻ります。
    1. 5文字が次のように分布している場合:(1<2<3>4>5すなわちALPHA
    2. 5つの文字が同じように分散している場合:1>2<3<4>5(つまりEAGLEHARSHNINONPINUP
    3. 5文字が次のように分布している場合:(1<2>3>4<5すなわちRULER
    4. 5文字が次のように分布している場合:(1>2>3<4<5つまりTHEFTWIDOW

これらの4つのルールは単純化できます1*3<0 and 2*4<0@KarlNapfのPython 2の回答に感謝)。


2
原因不明のダウンボートを補うために+1 ...私が知る限り、これは完全に機能するソリューションです。
アーナウルド

1
sをchar [] char [] c = s.toCharArray(); int z = c [1] -c [0]、y = c [2] -c [1]、に変換する215になりました。 ..
dpa97

@ dpa97のchar[]代わりに入力として使用するリマインダーをありがとうString。-38バイトありがとう。
ケビンCruijssen

1
あなたのブール値を最適化することができますz,xし、w,y交互の符号を持っている必要がありますので、チェックすることで十分z*x<0w*y<0
カールNAPF

@KarlNapfああ、数時間前にあなたのコメントを誤解しました。なんと-63バイトの派生式を実装しました。:)ありがとう。
ケビンCruijssen

4

JavaScript(ES6)、91 89 87バイト

Ismael Miguelのおかげで2バイト節約

s=>(k=0,[...s].reduce((p,c,i)=>(k+=p>c?1<<i:0/(p<c),c)),k?!(k%3)&&!s[5]&&s[0]==s[4]:!1)

使い方

k文字列の5文字間の4つの遷移を表す4ビットのビットマスクを作成します。

k += p > c ? 1<<i : 0 / (p < c)
  • 前の文字が次の文字よりも高い場合、ビットが設定されます
  • 前の文字が次の文字よりも低い場合、ビットは設定されません
  • 前の文字が次の文字と同一である場合、ビットマスク全体が強制されNaN、単語が拒否されます(ルール#6に準拠するため)

有効なビットマスクは、正確に2つの連続した1遷移を持つものです(最初と最後のビットも連続と見なされます)。

Binary | Decimal
-------+--------
0011   | 3
0110   | 6
1100   | 12
1001   | 9

言い換えれば、これらは次の組み合わせです。

  • k? :0より大きい
  • !(k%3)3を法とする0に一致
  • 15未満

その他の条件は次のとおりです。

  • !s[5] :5文字以下です
  • s[0]==s[4] :1番目と5番目の文字は同じです

NB:このk != 15ようなパターンに続く単語は、この最後の条件によって拒否されるため、明示的にチェックしません。

テストケース

初期バージョン

記録のために、私の初期バージョンは63バイトでした。すべてのテストケースに合格していますが、連続する同一の文字を検出できません。

([a,b,c,d,e,f])=>!f&&a==e&&!(((a>b)+2*(b>c)+4*(c>d)+8*(d>e))%3)

以下は、コメントでニールが提案した53バイトのバージョンであり、同様に機能します(そして失敗します)。

([a,b,c,d,e,f])=>!f&&a==e&&!((a>b)-(b>c)+(c>d)-(d>e))

編集:上記のコードの修正版/完成版については、ニールの回答を参照してください。


00003を法とする0にも一致しますが、最初と最後の文字を同じにすることはできません。したがって、15のように、明示的にテストする必要はありません。
ニール

その初期バージョンでは、使用できます!((a>b)-(b>c)+(c>d)-(d>e))か?
ニール

p<c?0:NaNとして記述でき0/(p<c)、2バイトを節約します。
イスマエルミゲル

@Neil 0に対するテストに関して:あなたは完全に正しいです。(ただし、k?可能性があるため、テストが必要NaNです。)代替バージョンに関して:それは実際に機能するはずです。
アーナルド

@IsmaelMiguel-いいね!ありがとう。
アーナルド

4

JavaScript(ES6)、78バイト

([a,b,c,d,e,f])=>a==e&&!(f||/(.)\1/.test(a+b+c+d+e)||(a>b)-(b>c)+(c>d)-(d>e))

@Arnauldの誤ったコードに基づいていますが、ゴルフをして修正しました。最初に最初の文字が5番目と同じであること(したがって5文字を保証すること)、および文字列の長さが5以下であることを最初にチェックすることにより機能します。ピークとトラフが2文字離れている必要があります。

  • ピークとトラフが中央の文字と最初/最後の文字である場合、最初の2つの比較と最後の2つの比較はキャンセルされます
  • ピークとトラフが2番目と4番目の文字である場合、中央の2つの比較と外側の2つの比較はキャンセルされます。
  • そうでない場合、何かがキャンセルに失敗し、全体的な式がfalseを返します

編集:@KarlNapfの答えに基づいた78バイトの代替ソリューション:

([a,b,c,d,e,f],g=(a,b)=>(a<b)-(a>b))=>a==e&&!f&&g(a,b)*g(c,d)+g(b,c)*g(d,e)<-1

3

Python 2終了コード、56バイト

s=input()
v,w,x,y,z=map(cmp,s,s[1:]+s[0])
v*x+w*y|z>-2>_

終了コードによる出力:Falseの場合はエラー、Trueの場合は正常に実行されます。

文字sを含む文字列を受け取り、abcdeそれを回転させbcdea、対応する文字の要素ごとの比較を行い、それらを5つの変数に割り当てますv,w,x,y,z。間違った長さはエラーになります。

無限の言葉はすべて持っています

v*x == -1
w*y == -1
z == 0

これはとして一緒にチェックできますv*x+w*y|z == -2v*x+w*y|z>-2>_これが当てはまる場合、連鎖比較は短絡し、そうでない場合は評価に進み-2>_、名前エラーが発生します。


ああ、それはあなたが条件付きでもっとゴルフをする方法です。
カールナップ

3

Python 2、110 87 60バイト

ニールのおかげで1バイト節約

引用符で囲まれた入力が必要です。例 'KNEES'

True無限語であるFalse場合、そうでない場合、長さが5で、長さが間違っている場合はエラーメッセージを出力します。

s=input()
a,b,c,d,e=map(cmp,s,s[1:]+s[0])
print a*c+b*d|e<-1

xnorの回答に触発されてmap(cmp...

s=input()
e=map(cmp,s,s[1:]+s[0])
print e[4]==0and e[0]*e[2]+e[1]*e[3]==-2and 5==len(s)

以前のソリューション:

s=input()
d=[ord(x)-ord(y)for x,y in zip(s,s[1:])]
print s[0]==s[4]and d[0]*d[2]<0and d[1]*d[3]<0and 4==len(d)

Kevin Cruijssenの最適化されたロジックを使用する


何故なの a*c+b*d+2==0==e
ニール

@ニールはい、なぜそうではありませんが、xnorの a*c+b*d|eはさらに短くなっています。
カールナップ

<-1両方-2|1-2|-1等しいので、私は働くかもしれないと思います-1
ニール


2

Python 2、71バイト

lambda s:map(cmp,s,s[1:]+s[0])in[[m,n,-m,-n,0]for m in-1,1for n in-1,1]

文字sを含む文字列を取得し、abcdeそれをに回転しbcdea、対応する文字の要素ごとの比較を行います。

a  b   cmp(a,b)
b  c   cmp(b,c)
c  d   cmp(c,d)
d  e   cmp(d,e)
e  a   cmp(e,a)

結果はのリストです-1, 0, 1。次に、結果が有効なアップとダウンのシーケンスの1つであるかどうかを確認します。

[-1, -1, 1, 1, 0]
[-1, 1, 1, -1, 0]
[1, -1, -1, 1, 0]
[1, 1, -1, -1, 0]

テンプレートから生成された [m,n,-m,-n,0]m,n=±1。最後0は最初と最後の文字が等しいことをチェックし、長さは入力文字列の長さが5であることを保証します。


代替案71。正しい長さを確保しながら、比較の条件をチェックします。

def f(s):a,b,c,d,e=map(cmp,s,s[1:]+s*9)[:5];print a*c<0==e>b*d>len(s)-7

1

R、144バイト

答えは、@ Jonathan Allanの論理に基づいています。たぶんゴルフもできるかもしれません。

s=strsplit(scan(,""),"")[[1]];d=diff(match(s,LETTERS));s[1]==tail(s,1)&length(s)==5&all(!rle(s)$l-1)&!sum(d)&!sum(sign(d))&any(rle(sign(d))$l>1)

Rフィドルテストケース(ベクトル化された例、同じロジック)


すでにチェックしていることがあるのでlength(s)==5、あなたは置き換えることができs[1]==tail(s,1)s[1]==s[5]。長さをチェックする1バイトの短い方法はis.na(s[6])です。一緒にこれらの2つの変更が返すTRUEためにs、正確かつ長さ5のFALSEように、そうでない場合TRUE&NAであるNAが、FALSE&NAですFALSE。に置き換えること!sum(sign(d))&any(rle(sign(d))$l>1)で、数バイト節約することもできます!sum(a<-sign(d))&any(rle(a)$l>1)
rturnbull

1

GNU Prolog、47バイト

i([A,B,C,D,A]):-A>B,B>C,C<D,D<A;i([B,C,D,A,B]).

クラッシュする述語を定義します。再帰呼び出しは、末尾呼び出しとして処理できる必要があります。どうやらGNU Prologのオプティマイザーはあまり良くありません。)成功はPrologの真実と同等であり、falseと同等の失敗です。クラッシュは間違いよりも偽りであり、それを修正するとソリューションが大幅に長くなるので、これが有効なソリューションとしてカウントされることを願っています。i無限の単語に対して成功する(実際には無限に何度も)をます。したがって、インタプリタから実行されると「yes」を出力します(Prologの通常の場合)。最初と最後の文字が一致しない、または5文字の長さではない候補語では失敗します。したがって、インタープリターから実行すると「no」が出力されます。無限の単語ではないが、最初と最後の2つの一致する5文字の候補単語を指定すると、スタックオーバーフローでクラッシュします。(理由はわかりません

アルゴリズムはかなり単純です(実際、プログラムはかなり読みやすいです)。文字が無限の単語を作る4つのパターンの1つを形成しているかどうかを確認し、そうでない場合は、周期的に並べ替えて再試行します。<and >演算子を使用すると、デルタが一致することを暗黙的に確認できるため、二重文字を明示的に確認する必要はありません。


1

実際38 27バイト

この答えは、主にジョナサンアランの優れたゼリーの答えに触発されました。これをゴルフできる場所はおそらくいくつかあるので、ゴルフの提案を歓迎します!オンラインでお試しください!

O;\♀-dY@♂s4R`0~;11({k`Míub*

アンゴルフ

     Implicit input s.
O    Push the ordinals of s. Call this ords.
;    Duplicate ords.
\    Rotate one duplicate of ords left by 1.
♀-   Vectorized subtraction. This effectively gets the first differences of ords.
d    Pop ord_diff[-1] onto the stack. This is ords[0] - ords[-1].
Y    Logical negate ord_diff[-1], which returns 1 if s[0] == s[-1], else 0.
@    Swap (s[0] == s[-1]) with the rest of ord_diff.

♂s       Vectorized sgn() of ord_diff. This gets the signs of the first differences.
4R       Push the range [1..4] onto the stack.
`...`M   Map the following function over the range [1..4]. Variable x.
  0~;      Push -1 onto the stack twice.
  11       Push 1 onto the stack twice.
  (        Rotate x to TOS.
  {        Rotate the stack x times, effectively rotating the list [1, 1, -1, -1].
  k        Wrap it all up in a list.

     Stack: list of rotations of [1, 1, -1, -1], sgn(*ord_diff)
í    Get the 0-based index of sgn(*ord_diff) from the list of rotations. -1 if not found.
ub   This returns 1 only if sgn(*ord_diff) was found, else 0.
     This checks if the word loops like an infinity word.

*    Multiply the result of checking if the word s loops and the result of s[0] == s[-1].
     Implicit return.


1

TI-BASIC、81バイト

プログラムに渡す文字列はAnsです。入力された単語がInfinity Wordの場合は1を返し(暗黙的に表示)、そうでない場合は0(またはエラーメッセージで終了)を返します。

seq(inString("ABCDEFGHIJKLMNOPQRSTUVWXYZ",sub(Ans,A,1)),A,1,length(Ans
min(Ans(1)=Ans(5) and {2,2}=abs(deltaList(deltaList(deltaList(Ans)/abs(deltaList(Ans

繰り返される文字のエラー、または5文字以外の単語。


1

05AB1E、16 バイト

Ç¥DO_s.±¥¥Ä2DиQ*

@JonathanAllanのJelly回答のポート。

オンラインそれを試してみたり、すべてのテストケースを確認してください

説明:

Ç             # Convert the (implicit) input string to a list of unicode values
              #  i.e. "RULES" → [82,85,76,69,82]
 ¥            # Take the deltas
              #  i.e. [82,85,76,69,82] → [3,-9,-7,13]
  DO          # Duplicate and take the sum
              #  i.e. [3,-9,-7,13] → 0
    _         # Check if that sum is exactly 0
              # (which means the first and last characters are equal)
              #  i.e. 0 and 0 → 1 (truthy)
 s            # Swap so the deltas are at the top of the stack again
            # Get the sign of each
              #  i.e. [3,-9,-7,13] → [1,-1,-1,1]
    ¥         # Get the deltas of those signs
              #  i.e. [1,-1,-1,1] → [-2,0,2]
     ¥        # And then get the deltas of those
              #  i.e. [-2,0,2] → [2,2]
      Ä       # Convert them to their absolute values
       2Dи    # Repeat the 2 two times as list: [2,2]
          Q   # Check if they are equal
              #  i.e. [2,2] and [2,2] → 1 (truthy)
 *            # Check if both are truthy (and output implicitly)
              #  i.e. 1 and 1 → 1 (truthy)
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.