Konuşma tercümanı


10

"Konuşma" Dennis'in cevaben oluşturulan bir baroquified akümülatör tabanlı dildir alıntı talk.tryitonline.net üzerinde.

Waiting for someone to create an esolang called talk. 

. "Google Talk" dilinde 4 komut vardır:

  • 00 Akümülatör 0 ise, akümülatörü 0 olarak ayarlayın.
  • 01 Akümülatör 0 ise, akümülatörü 1 olarak ayarlayın.
  • 10 Akümülatör 1 ise, akümülatörü 0 olarak ayarlayın.
  • 11 Akümülatör 1 ise, akümülatörü 1 olarak ayarlayın.

Giriş:

  • Giriş, standart I / O kurallarımıza göre kabul edilebilir herhangi bir giriş yöntemi ile alınabilir.

  • İlk akümülatör değeri ve program olmak üzere iki giriş vardır. İsterseniz bu iki girişi bir girişte birleştirebilir veya girişinizi geçerli komutlara bölebilirsiniz (örneğin, bunları bir liste olarak almak; örneğin [00, 01, 00]).

Çıktı:

  • Bir komut yürütmesinin sonunda, akümülatör örtük olarak çıkar.

Kurallar:

  • Giriş yapabilirsiniz tek bir dize veya karakter listesi olacak.
  • Bu olduğu gibi , en kısa cevap bayt cinsinden kazanır.
  • Rakamlar veya dizeler / karakterler alırız.

    Test senaryoları:

0 0001111101 -> 1
0 000100 -> 1
0 11001000 -> 0

Liderler

İşte hem düzenli bir skor tablosu hem de kazananları dile göre gözden geçirmek için bir Yığın Parçacığı.

Yanıtınızın göründüğünden emin olmak için lütfen aşağıdaki Markdown şablonunu kullanarak yanıtınızı bir başlıkla başlatın:

# Language Name, N bytes

Ngönderiminizin büyüklüğü nerede . Puanınızı artırmak varsa, olabilir onları içinden vurarak, başlığa eski hesapları tutmak. Örneğin:

# Ruby, <s>104</s> <s>101</s> 96 bytes

Başlığınıza birden fazla sayı eklemek istiyorsanız (örneğin, puanınız iki dosyanın toplamı olduğu veya yorumlayıcı bayrak cezalarını ayrı olarak listelemek istediğiniz için), gerçek puanın başlıktaki son sayı olduğundan emin olun :

# Perl, 43 + 2 (-p flag) = 45 bytes

Dil adını, daha sonra skor tablosu snippet'inde görünecek bir bağlantı da yapabilirsiniz:

# [><>](http://esolangs.org/wiki/Fish), 121 bytes


3
Yani iki giriş var, komutlar dizisi ve ilk akümülatör değeri?
xnor

4
Akümülatörü değiştirmeyen, akümülatörde 1 ile başlayan veya talimatı olmayan bazı test durumları iyi olacaktır
Jo King

8
Can konuşmak gerçekten dikkate alınması programlama dili ?
Luis Mendo

8
@A_ Bu yorum muhtemelen şaka amaçlıydı. O günlerde, Lang adlı bir dilin bir URL'si olurdu lang.tryitonline.net(şimdi tio.run/#lang). Yani Talk adlı bir dil , yakın zamanda oluşturulan sohbet odasının URL'si ile karışıklığa neden olur, bu datalk.tryitonline.net
Luis Mendo

7
Gelecekte, bir dizi yanıt gönderildikten sonra lütfen G / Ç'yi değiştirmekten kaçının. Bugün geri döndüm ve eşlenmiş girdilere izin verilmesi, bunu yanıtladığımdan tamamen farklı bir zorluk haline getiriyor .
GammaFunction

Yanıtlar:


21

Jöle , 3 bayt

y@/

Giriş tek bir listedir: akümülatör, ardından çiftler.

Çevrimiçi deneyin!

Nasıl çalışır

yAtomu gerçekleştirir çevirisi; [a, b] yc yerine geçer , bir ile b , döndürür, böylece b eğer a = C ve C ise bir ≠ c .

y@/yHer çift için bir harf çevirisi gerçekleştirerek, değiştirilen bağımsız değişkenlerle girdiyi katlar / azaltır .


14
Bu, şimdiye kadar gördüğüm, sadece ASCII karakterleri kullanan tek Jelly cevabı.

2
Birkaç tane vardı. Bak anne, Unicode yok!
Dennis

21

Python 3 , 43 bayt

lambda s:re.sub("00|11","",s)[-1]
import re

Çevrimiçi deneyin!

İşlev, giriş olarak tek bir dize alır; burada ilk karakter ilk durumdur ve dizenin geri kalanı komutları temsil eder. Bu çözüm, düzenli ifadeler için daha iyi desteği olan diğer dillere kolayca taşınabilir.

Zor kısım, çözeltinin doğru sonucu verdiğini kanıtlamaktır. Bunu görmek için, komutların derinlemesine bir analizine ihtiyacımız var. İlk olarak, komutların aşağıdaki özelliklere sahip olduğunu görebiliriz:

  • Özellik (1) : akümülatör durumunu komutlar 00ve 11korur.
  • Özellik (2) : komutları verir 01ve 10akümülatör durumunu orijinal durumuna bakılmaksızın ikinci bit ile aynı yapar.

Bu nedenle, son akümülatör durumu:

  • Durum 1 : Hayır 01veya 10komut varsa, son durum ilk durumla aynıdır.
  • Durum 2 : Aksi takdirde, son 10veya 01komutun son biti .

Daha sonra, çözümün her iki durumda da doğru sonucu verdiğini göstereceğiz. Nihai durumun açıklamasını kanıtlayacağız 0ve nihai durumu 1benzer şekilde kanıtlanabilir. Son durum ise 0, giriş aşağıdaki biçimlerden birindeyse:

  • ^0{2k+1}11(11|00)*

    For Durumunda 1 , girdi dizesi sile başlamalıdır 2k+1ardından 0s, 11ve 00komutlar. 00S ve 11s'nin ortadan kaldırılması 0, nihai durum olan bir tek verir .

  • .+10{2k+1}11(11|00)*

    İçin Durumunda 2 , bir ile giriş dizesi uçları 10komutu sıfır ya da daha fazla takip 00ve 11s. Bu örüntü, 1ardından 2k+10'lara ve ardından sıfır veya daha fazla 11s ve 00s'ye eşdeğerdir . 00S ve 11s'nin ortadan kaldırılması 2k+1, son durumu temsil eden dizenin sonunda 0'ların sonuncusunun arkasını bırakır .

Yukarıdakilerin hepsine dayanarak, 00s ve 11s'yi aynı anda tek bir geçişte ( bir geçişte ve sonra başka bir geçişte elimine 01001edilirse bir karşı örnek 00) ortadan kaldırdıktan sonra son karakter son durumdur. Böylece çözümün doğruluğu kanıtlanmıştır.11s


PPCG'ye Hoşgeldiniz! Mükemmel cevap ve onunla gitmek için güzel bir resmi kanıt!
GammaFunction

3
Teşekkürler. İnsanların böyle basit bir çözümün ilk bakışta doğru sonucu verdiğinden şüphe edebileceklerini hissediyorum. Yani bunun için bir kanıt sunmaya ihtiyaç var.
Joel

9

Perl 6 , 17 bayt

{m/.)>[(.)$0]*$/}

Çevrimiçi deneyin!

Yararlanır komutları örn ile birleştirilmiş akümülatör değeri olarak girdi alarak "sizin gibi eğer tek bir girişe bu iki girdileri birleştirebilirsiniz" 1,[00,11]olduğunu 10011. Bu uygun değilse, onu almak için sadece 5 ekstra bayt daha f(accumulator, commands). Bir dizeye zorlanabilecek bir eşleşme nesnesi döndürür.

Açıklama:

{                }  # Anonymous code block
 m/             /   # Find the first match from the input
   .)>              # Capture a number
      [     ]*      # Followed by any number of
       (.)$0        # Pairs of identical characters
              $     # Ending the string

Temel olarak bu çalışır, çünkü 00ve 11komutları tam anlamıyla hiçbir şey yapmazken, 01ve 10komutları akümülatörü komutun ikinci basamağına ayarlar. Komut yoksa, akümülatörün başlangıç ​​değerini alır.


6

Zsh , 33 bayt

Karakter listesi argümanlar olarak, akümülatörün başlangıç ​​değeri stdin olarak iletilir.

read a
for x y;a=$[x^a?a:y]
<<<$a

Çevrimiçi deneyin!


39 bayt : Komutların tek bir dize olması gerekiyorsa

Girdi accumulator commandsargümanlar gibidir.

for x y (${(s::)2})1=$[x^$1?$1:y]
<<<$1

Çevrimiçi deneyin!


Eğlenmek için, 50 baytlık özyinelemeli bir astar ( TIO ):

<<<${${2+`f $[$1^${2[1]}?$1:${2[2]}] ${2:2}`}:-$1}

6

Python 3 , 52 bayt

f=lambda a,s:s and f([s[1],a][s[0]==s[1]],s[2:])or a

Çevrimiçi deneyin!

Chas Brown sayesinde tutarsız dönüş türü düzeltildi

Girdiyi iki dize olarak alır; akümülatör ve kod.


Oh hayır, hızlıydı.
Oldukça Radyoaktif

1
Güzel ama bu potansiyel bir sorunu var - f(1,'11')==f(1,'01')öyle False; intbazen a, bazen a döndürür str. Belki de dize olarak acc girişi alır belirtin?
Chas Brown

@ChasBrown İyi görüşme, düşündüğümden çok daha basit.
negatif yedi

Güzel, ama işleviniz özyinelemeli olduğundan anonim olamaz. 52 bayt olmalıdır .
Jitse

5

Brachylog , 11 9 bayt

tġ₂≠ˢtt|h

Çevrimiçi deneyin!

Her komuttan sonra akümülatörü basma fikrini unutabileceğim kadar uzun olduğu için , Jo King'in Perl cevabından ilham alarak daha az naif bir çözüm formüle ettim.

       |     The output is
     tt      the last element of the last element of
t            the last element of the input
 ġ₂          split into length-2 slices
   ≠ˢ        with equal pairs removed.
       |     If there is no such element, the input
        h    's first element is the output.

Eski çözüm:

Brachylog , 18 16 bayt

ġ₂ᵗc{th~h?tt|h}ˡ

Çevrimiçi deneyin!

Giriş formatını değiştirmekten -2 bayt.


5

JavaScript (ES6), 27 bayt

Girdiyi alır; (a)(code)burada kod bir 2 bitlik tamsayıların listesidir.

a=>c=>c.map(x=>a^=x==a+1)|a

Çevrimiçi deneyin!


JavaScript (ES6),  47  40 bayt

Girdiyi (a)(code), kodun bir dize olduğu gibi alır.

a=>c=>c.replace(/../g,x=>a^=x%4==a+1)&&a

Çevrimiçi deneyin!

Nasıl?

Tüm olası durumlar aşağıda özetlenmiştir. Akümülatörü değiştirmemiz gereken sadece iki durum(bir=0,x=012) ve (bir=1,x=102).

  a | x (bin) | int(x) % 4 | a + 1 | equal?
----+---------+------------+-------+--------
  0 |   "00"  |  0 % 4 = 0 |   1   |   N
  1 |   "00"  |  0 % 4 = 0 |   2   |   N
  0 |   "01"  |  1 % 4 = 1 |   1   |   Y
  1 |   "01"  |  1 % 4 = 1 |   2   |   N
  0 |   "10"  | 10 % 4 = 2 |   1   |   N
  1 |   "10"  | 10 % 4 = 2 |   2   |   Y
  0 |   "11"  | 11 % 4 = 3 |   1   |   N
  1 |   "11"  | 11 % 4 = 3 |   2   |   N

4

sed -E, 26 19 bayt

Tüm çiftleri kaldırarak @Cowsquack'ten bir kuyruklu -7 bayt da çalışır.

s/(.)\1//g
s/.*\B//

Stdin üzerinde birleştirilmiş girdileri alır. Jo King'in Perl cevabından ilham aldı . Sondaki çiftleri şeritle Tüm çiftleri kaldır, sonra son basamağı al.

Çevrimiçi deneyin! Çevrimiçi deneyin!


1
Son satır basit olabilir s/.*\B//, ancak yine de yaklaşımı biraz değiştirerek 19 bayt daha da kısaltır . Çevrimiçi deneyin!
user41805

1
Ha, s/(.)\1//gbunun işe yarayacağını düşünmedim , çünkü bir çiftin sonunu ve bir sonrakinin başlangıcını kaldırabilir, ama yine de işe yarıyor. Mükemmel!
GammaFunction

@GammaFunction s/(.)\1//geşdeğerdir s/00|11//gbenim çözümde gösterildiği gibi.
Joel

4

Retina 0.8.2 , 18 11 bayt

(.)\1

!`.$

Çevrimiçi deneyin! Bağlantı, test senaryolarını içerir. Birleştirilen girdiyi alır. @CowsQuack sayesinde tüm çift karakterlerin kaldırılıp sonra kalan son karakterlerin işe yaradığına dikkat çektiği için 6 bayt kaydedildi, ancak @ JoKing'in orijinal cevabının limanı bu numara olmadan bile 3 bayt tarafından golf edilebilirdi.



@Cowsquack D'oh, aşamaları ayırmayı düşündüğünüzde, bu zaten 2 baytlık bir tasarruf, daha sonra kullanabileceğiniz başka bir bayt !`.$ve daha sonra başka bir 4 bayt, çünkü sondaki çiftlerle sınırlamak zorunda değilsiniz ...
Neil

4

Python 3 , 38 bayt

lambda l:[y for*x,y in l if[y]!=x][-1]

Çevrimiçi deneyin!

Joel'in çözümüne dayanıyor . İlk akümülatör değerinin (uzunluk-bir dize) ardından komutları (uzunluk-iki dize) bir liste olarak girer. İki eşit olmayan değerle son komutu bulur ve ikinci karakterini verir.

Böyle bir komut olmadığında bunu ilk akümülatör değerine düşürmek için, tek karakterlik ilk değer dizesinin testi geçmesi için bunu yaparız. Bunu, son karakterli tek bir listenin, herhangi bir uzunluk-bir dize veya iki farklı karakterli uzunluk-iki dize tarafından geçirilen önceki tüm karakterlerin bir listesiyle eşit olup olmadığını kontrol ederek yaparız.




3

Jöle , 8 6 bayt

EÐḟṪṪo

Çevrimiçi deneyin!

Bana bir kural değişikliği konusunda bilgi veren Nick Kennedy sayesinde -2 bayt. (Onun önerdiği golf, EÐḟFȯṪbiraz daha zeki görünüyor ama önceki çözüm eksi ile aynı uzunlukta s2.) Giriş formatı şimdi komutları iki karakterli dizelerin bir listesi olarak alıyor, ancak test altbilgisi kolaylık sağlamak için eski formattan çeviriyor.

Yeni Brachylog çözümümden çevrildi.

Eski versiyon:

Jöle , 13 bayt

ḢẎ⁼⁹a⁸o
s2ç@ƒ

Çevrimiçi deneyin!

Bunun doğru olduğundan% 100 emin değilim, ancak her üç test vakasında da başarılı. Komutları sol argüman, ilk akümülatör ise doğru argüman olarak alır.


1
Girişin bir listeye bölünmesine izin verilir, bu nedenle EÐḟFȯṪgirişle örn [[0,0],[0,1],[1,1],[1,1],[0,1]].
Nick Kennedy

Vay be, spec değişiklikleri gerçekten çok büyüktü ...
İlişkisiz String

3

Haskell , 29 bayt

Türlü ilk satırda adsız bir işlev tanımlar (Foldable t, Eq b) => b -> t [b] -> b. Bu kod golf amaçları için, Char -> [String] -> Charilk argümanın akümülatör ve ikincisinin her bir dizenin tek bir komut olduğu bir dize listesi olduğu gibi başlatabiliriz .

foldl(#)
a#[x,y]|a==x=y|1>0=a

Çevrimiçi deneyin!


1
Önek notasyonunu kullanarak tanımlarsanız aynı bayt sayısı . Aynı anda neredeyse aynı cevabı yazdığımı, tip imzası açıklamasını da dahil ettiğime inanamıyorum…
cole

2

Python, 111 bayt

def f(a,b):
    c=a
    for i in range(0,len(b)-1,2):
        c=(not b[i])*(c or b[i] or b[i+1]) or c*b[i]*b[i+1]
    return c

Ungolfed. EDIT: AHHH Birisi beni dövdü!





2

Fıçı ,, -ir16 bayt

"(!;½|':"=['_"|_

Çevrimiçi deneyin!

Açıklaması:

  1. Örtülü girdiyi alır ve sağ akümülatörlerin değerini aşağıya kaydırır

  2. Aşağıdaki (yığın uzunluğu - 1 bölü 2) kez tekrarlayın

2.1. Akümülatörü en üste kaydırın

2.2. Eşitlik için komutun ilk bölümü ile karşılaştırın

2.2.1. Doğruysa, akümülatörü değiştirin, aksi takdirde yedek parçayı açın

Giriş, kaynak ile birleştirilen ilk acc değeri olarak alınır. Örneğin

010011000
  • İlk karakter acc değeridir
  • Gerisi program

1

Bash , 58 40 bayt

Tam program için bir bayt ekleyin: değişikliğini fiçin $0.

(($1=$2-a?a:$3,1))&&f $1 ${@:4}||echo $1

58 bytes Çevrimiçi deneyin!

Üçlü, $1olarak ayarlandığında false döndürür 0, ancak ,1sonunda bir sözdizimi hatası dışında bütünün ((expression))doğru dönmesini sağlar .

Tüm bağımsız değişkenler tüketildiğinde, bir sözdizimi hatası oluşur ve özyineleme sona erer.



1

Kömür , 16 bayt

F⪪η²F⁼θ§ι⁰≔§ι¹θθ

Çevrimiçi deneyin! Bağlantı, kodun ayrıntılı versiyonudur. Ayrı argümanlar alır. Açıklama:

F⪪η²

Talimatları basamak çiftlerine bölün ve üzerlerine döngü yapın.

F⁼θ§ι⁰

Akümülatör ilk basamağa eşitse ...

≔§ι¹θ

... sonra ikinci basamağı atayın.

θ

Akümülatörü döngünün sonuna yazdırın.



1

Jöle , 7 bayt

fؽḂ⁹;Ṫ

Programı solda bir tamsayılar listesi ve sağda bir tamsayı veren ilk akümülatör listesi olarak kabul eden ikili bir bağlantı.

Çevrimiçi deneyin! Veya bir test takımına bakın


@GammaFunction bunu yapmamı önerdiğinden girdi eşlemesini kaldırıyorum.

@A_ ah OK mobil cihazdan silemez bu yüzden daha sonra bunu ele almak zorunda kalacak
Jonathan Allan

@A_ 0,1,2,3 ile çalışacak şekilde düzeltilmiş basamaklı olarak talimatların eşlenmemiş versiyonu iyi mi?
Jonathan Allan

1
Evet herşey yolunda.


1

Runik Efsunlar , 28 bayt

/~@/i~/i<
/=?/~iR:l}i{l1-=?!

Çevrimiçi deneyin!

Girdileri baytlarla ayrılmış bir dizi boşluk olarak alır (Runic listeleri anlamıyor). İlk bayt başlangıç ​​durumudur ve diğer her bayt programdır. Doğrulama yapılmaz (yani yalnızca geçerli programların girdi olarak verildiğini varsayar ve hangi değerin temsil edileceği ile ilgilenmez 0ve 1).


1

x86 Meclisi, 33 Bayt

İlk akümülatör durumunu CL(tamsayı 0veya 1) ve komutların adresini sıfır sonlu ASCII Dizesi olarak alır ESI. Son akümülatör durumunu bırakır CL.

Görüşme talimatını ofsete doğrultun 0x1B( interpretAçıklamadaki etiket ).

3C 30 74 03 B0 01 C3 30 C0 C3 E8 F1 FF FF FF 38
C8 AC 75 07 E8 E7 FF FF FF 88 C1 AC 84 C0 75 EA
C3

Açıklama (Intel Sözdizimi Kullanarak):

; function to convert ASCII '1'/'0' into 0 or 1 int values (from AL to AL)
ctob:
        CMP AL, 0x30 ; '0'
        JE .zero
        MOV AL, 1
        RET
        .zero:
        XOR AL, AL
        RET

; interpreting function
        interp_lp:
                CALL ctob     ; convert to number
                CMP AL, CL    ; compare to current accumulator
                LODSB         ; read the next character of the string
                              ; this doesn't affect any flags and we need to do
                              ; it in both cases anyway
                JNE interpret ; if AL != CL (from above, not the new value of AL), skip forward
                CALL ctob     ; convert AL to number
                MOV CL, AL    ; store AL in CL
interpret:      LODSB         ; read the next character of the string
                TEST AL, AL   ; check if it is a zero byte
                JNZ interp_lp ; if not, jump back into the loop
        RET



0

Kristal , 46 bayt

Array(Tuple(Int32,Int32))Gibi komutları ile , gibi [{0,0}, {0,1}, {0,0}].

def f(s,i);i.map{|c,v|s+=~(s^c)&(s^v)%2};s;end

Çevrimiçi deneyin!

Daha okunabilir bir biçimde anlamak oldukça kolaydır:

def f(state, instructions)
  instructions.map do |check, value|
    state += ~(state ^ check) & (state ^ value) % 2
  end
  state
end

İşlev, her bir komutta dolaşır ve demet değerlerini otomatik olarak cve değerlerine açar v. Daha sonra stateformülle

state = state + NOT(state XOR check) AND (state XOR value) mod 2

hangi çoğunlukla deneme yanılma ile geldi. Tüm komutlar işlendikten sonra durum değerini döndürür.


0

C (clang) , 68 62 bayt

t(s,e,a)char*s,*e;{for(;s<e;++s)a=*s++-48^a?a:*s-48;puts(&a);}

Çevrimiçi deneyin!

Kaynak dizenin başına bir işaretçi, kaynak dizenin sonuna bir işaretçi (start + strlen (start)) ve ilk akümülatör değerini alır.

Eski sürüm (0/1 için ASCII 48/49 yazdırır):

t(s,e,a)char*s,*e;{for(;s<e;++s)a=*s++-48^a?a:*s-48;putchar(a+48);}

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.