Bu sayı asal mı?


195

İster inanın ister inanmayın, basit bir ilkellik testi için henüz bir kod golf mücadelemiz yok . Özellikle "normal" diller için en ilginç zorluk olmasa da, birçok dilde önemsiz olabilir.

Rosetta kodu, biri Miller-Rabin testi , diğeri deneme bölümünü kullanarak, birincillik testine deyimsel yaklaşımların diline göre listeler . Ancak, “en deyimsel” çoğu zaman “en kısa” ile çakışmaz. Programming Puzzles ve Code Golf'u kod golf için go-siteye dönüştürmek amacıyla, bu zorluk "Merhaba, Dünya!" Gibi, her dilde en kısa yaklaşımın bir kataloğunu derlemeye çalışır . ve Golf size harika bir iyilik için bir kuyruk! .

Ayrıca, bir birincillik testi uygulama yeteneği bizim programlama dil tanımımızın bir parçasıdır , bu yüzden bu zorluk kanıtlanmış bir programlama dili dizini olarak da işlev görecektir.

Görev

Bir yaz tam program katı bir pozitif tam sayı verilir, n, girdi olarak belirler , n asal ve basar truthy veya falsy değeri buna göre.

Bu zorluğun amacı için, tam olarak iki katı pozitif bölen varsa, bir tam sayı çok önemlidir. Bu dahil olmadığını unutmayın 1 onun sadece kesinlikle olumlu bölen olduğunu.

Algoritmanız belirleyici olmalı (örneğin, olasılık 1 ile doğru çıktıyı üretmeli) ve teoride keyfi olarak büyük tamsayılar için çalışmalıdır. Uygulamada, programın 1 - 255 arasındaki tam sayılarda çalıştığı sürece girişin veri türünüzde saklanabileceğini varsayabilirsiniz.

Giriş

  • Diliniz STDIN'den okuyabilirse, komut satırı argümanlarını veya başka bir alternatif kullanıcı girişi formunu kabul ederse, tamsayı ondalık gösterimi, tek biçimli gösterimi (seçtiğiniz bir karakteri kullanarak), bayt dizisini (büyük veya küçük endian) veya tek bayt (bu sizin dilleriniz en büyük veri türüyse).

  • Eğer (ve sadece) diliniz herhangi bir kullanıcı girişini kabul edemezse, girişi programınıza yazabilirsiniz.

    Bu durumda, kodlanmış tamsayı kolayca değiştirilebilir olmalıdır. Özellikle, programın tamamında yalnızca tek bir yerde görünebilir.

    Puanlama amacıyla, giriş 1'e karşılık gelen programı sunun .

Çıktı

Çıktı STDOUT ya da en yakın alternatife yazılmalıdır.

Mümkünse, çıktı yalnızca isteğe bağlı olarak tek bir yeni satır izleyen , bir truthy veya sahtekarlık değerinden (veya bunun bir dize temsilinden) oluşmalıdır .

Bu kuralın tek istisnası, selamlama, ANSI renk kodları veya girintiler gibi bastırılamayan dilinizin tercümanının sürekli çıktısıdır.

Ek kurallar

  • Bu, birincil test için en kısa yaklaşımı olan dili bulmakla ilgili değildir, her dilde en kısa yaklaşımı bulmakla ilgilidir. Bu nedenle, hiçbir cevap kabul edilmiş olarak işaretlenmeyecektir.

  • Çoğu dilde yapılan gönderiler, genellikle önceden var olan bir UTF-8 kodlama kodunda bayt olarak puanlanacaktır .

    Örneğin Piet dili , bu dilin doğal tercihi olan kodellerde puanlanacak.

    Klasörler gibi bazı dilleri puanlamak biraz zor. Şüpheniz varsa, üzerine sorabilirsiniz Meta .

  • Her zamanki kurallarımızdan farklı olarak, bu zorluktan daha yeni olsa bile, bir dili (veya dil sürümünü) kullanmaktan çekinmeyin. Eğer biri boş programın ilkellik testi yaptığı bir dil oluşturarak bunu kötüye kullanmak isterse, çok sıkıcı bir cevabın yolunu açtığı için tebrikler.

    Göndermenin test edilebilmesi için bir tercüman olması gerektiğini unutmayın. Daha önce uygulanmamış bir dil için bu tercümanı kendiniz yazmanıza izin verilir (ve hatta teşvik edilir).

  • Seçtiğiniz dil, zaten bir cevabı olan (belki de BASIC veya SQL lehçeleri, Unix kabukları veya önemsiz Brainfuck türevlerini düşünün), başka bir (potansiyel olarak daha popüler) dilin önemsiz bir değişkeni ise, mevcut cevaba bir not eklemeyi düşünün. aynı veya çok benzer bir çözüm, diğer dilde de en kısa olanıdır.

  • Test primality için Yerleşik işlevleri vardır izin verdi. Bu zorluk, her dilde mümkün olan en kısa çözümü kataloglamak içindir; bu nedenle, kendi dilinizde yerleşik bir kullanımı kullanmak daha kısa sürerse, bunun için gidin.

  • Daha önce reddedilmediklerinde , http://meta.codegolf.stackexchange.com/q/1061 dahil tüm standart kuralları uygulanır .

Bir yandan not olarak, lütfen golf için fazla bir şey olmadığı dillerde sıkıcı (ama geçerli) cevapları azaltmayınız; Bunlar bir kataloğu mümkün olduğu kadar eksiksiz bir şekilde derlemeye çalıştığından bu soru için hala faydalıdır. Bununla birlikte, öncelikle yazarın gerçekte kodu golf oynamak için çaba harcadığı dillerde cevapları çoğaltınız.

Katalog

Bu yazının altındaki Yığın Parçacığı, cevapları a) dil başına en kısa çözümün bir listesi olarak ve b) genel bir lider tablosu olarak oluşturur.

Cevabınızın göründüğünden emin olmak için, lütfen aşağıdaki Markdown şablonunu kullanarak cevabınızı bir başlık ile başlatın:

## Language Name, N bytes

Gönderinizin Nbü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ğundan veya tercüman bayrağı cezalarını ayrı ayrı 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 pasajda görünecek bir bağlantı da yapabilirsiniz:

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


Girişleri negatif sayılar olarak alabilir miyim, burada abs (input) test ettiğim sayı olur?
Stan Strum

Hayır, girdi kesinlikle pozitif bir tamsayıdır.
Dennis,

1
@ LyndonWhite Bu, ilkellik testlerinin bir kataloğu ( “Merhaba, Dünya!” Gibi) olarak tasarlandı , bu nedenle birleştirilmiş bir gönderme biçimi tercih edildi. Pişman olduğum bu zorlukla ilgili iki karardan biri, diğeri sadece deterministik ilkellik testlerine izin veriyor.
Dennis,

1
@Shaggy Meta için bir soru gibi görünüyor.
Dennis

1
Evet, öyle düşünüyordum. Senin onurunu yapmana izin vereceğim, senin görevin olarak görerek.
Shaggy

Yanıtlar:


225

Selam Dünya! , 13

hello, world!

83
Sen, mü sadece , bu dili oluşturmak sadece bu gönderim için? ;)
ETHproductions

41
@ETHproductions Son teslimi 10 gün önceydi.
Geobits 11:15

39
Dili herhangi bir yere bağlamadan önce dili biraz daha iyi bir hale getirmeyi umuyordum, ancak bu zorluk kaydedildi ve direnemedim.
histocrat

31
Neredeyse 1 girişine asılmanın doğru işlevsellik olduğunu söyleyebilirim.
iamnotmaynard,

21
Bunun en iyi yanı, programın sadece yerleşik bir şey olmaması, her karakterin doğru sonucu almak için kendi rolünü oynaması.
ETHProductions

157

Altıgen , 29 bayt

.?'.).@@/'/.!.>+=(<.!)}($>(<%

Bu kodun okunabilir versiyonu:

   . ? ' .
  ) . @ @ /
 ' / . ! . >
+ = ( < . ! )
 } ( $ > ( <
  % . . . .
   . . . .

Açıklama: n'yi bölen 2 ile n-1 arasında bir sayı olup olmadığını test eder.

Başlatma:

Bir hafıza hücresine n, diğerine n-1 yazınız:

   . ? ' .
  . . . . .
 . . . . . .
+ = ( . . . .
 . . . . . .
  . . . . .
   . . . .

Özel Durum n = 1:

0 yazdır ve sonlandır

   . . . .
  . . . @ .
 . . . ! . .
. . . < . . .
 . . . . . .
  . . . . .
   . . . .

Döngü

% N'yi hesaplayın ve a değerini azaltın. A = 1 veya n% a = 0 ise sonlandırın.

   . . . .
  ) . . . /
 ' / . . . >
. . . . . . .
 } ( $ > ( <
  % . . . .
   . . . .

Durum a = 1:

0'dan 1'e yükseltin, yazdırın ve sonlandırın. (Komut göstericisi NE yönünde çalışır ve doğu köşesinden güney batı köşesine döner. Ve $ bir sonraki komutu yok sayar.)

   . . . .
  . . . @ .
 . . . ! . .
. . . < . . )
 . . $ . . <
  . . . . .
   . . . .

Bir% n = 0 durumu:

0'ı yazdırın ve sonlandırın (Talimat işaretçisi SW çalışıyor ve @ üste doğru dönüyor

   . . . .
  . . @ . .
 . . . . . >
. . . . . ! .
 . . . . . .
  . . . . .
   . . . .

61
Vay canına, etkileyici ilk yazı. :) Hemen şimdi ödül vereceğim (7 gün içinde vereceğim, cevabınıza biraz daha dikkat çekeceğim). PPCG'ye Hoşgeldiniz!
Martin Ender

35
Mükemmel cevap! " Bu kodun okunabilir sürümü için +1 : <...> " :-)
agtoever

68

Hexagony , 218 92 58 55 bayt

Uyarı: Bu cevap, Etoplay tarafından 4 boyunda bir çözümle sağlam bir şekilde dövüldü .

)}?}.=(..]=}='.}.}~./%*..&.=&{.<......=|>(<..}!=...&@\[

İlk kez önemsiz olmayan (yani doğrusal olmayan) Hexagony programı! Sp3000'ün Labirenti cevabı ile aynı kare- faktoring yaklaşımına dayanıyor . Büyüklüğü 10 bir altıgen ile yola çıkıp sonra ancak büyüklük 5. için aşağı sıkıştırmak için yönetilen, bazı yinelenen kodu yeniden başardı ve hala kodda no-op oldukça bir grup vardır, bu yüzden boyutu 4 olabilir sadece mümkün olabilir.

açıklama

Kodu anlamak için önce açmamız gerek. Hexagony, herhangi bir kaynak kodunu, no-ops ( .) ile bir sonraki ortalanmış altıgen sayıya yayar 61. Daha sonra kodu, karşılık gelen boyuttaki normal bir altıgene yeniden düzenler:

     ) } ? } .
    = ( . . ] =
   } = ' . } . }
  ~ . / % * . . &
 . = & { . < . . .
  . . . = | > ( <
   . . } ! = . .
    . & @ \ [ .
     . . . . .

Bu, çapraz ve üst üste binen yürütme yolları ve çoklu komut işaretçileri (IP'ler) ile oldukça ağır bir şekilde golf oynamaktadır. Nasıl çalıştığını açıklamak için, ilk önce kontrol akışının kenarlardan geçmediği, sadece bir IP'nin kullanıldığı ve yürütme yollarının mümkün olduğu kadar basit olduğu eski bir versiyona bakalım:

             . . . . . . . . . . . . .
            . . . . . . . . . . . . . .
           . . . . . . . . . . . . . . .
          . . . . . . . . . . @ . . . . .
         . . . . . . . . . . ! . . . . . .
        . . . . . . . . . . % . . . . . . .
       . . . . . . . . . . ' . . . . . . . .
      . . . . . . . . . . & . . . . . . . . .
     . . . . . . . . . . { . . . . . . . . . .
    . . . . . . . . . . * . . . . . . . . . . .
   . . . . . . . . . . = . . . . . . . . . . . .
  . . . . . . . . . . } . . . . . . . . . . . . .
 ) } ? } = & { < . . & . . . . . . . . . . . . . .
  . . . . . . . > ( < . . . . . . . . . . . . . .
   . . . . . . = . . } . . . . . . . . . . . . .
    . . . . . } . . . = . . . . . . . . . . . .
     . . . . | . . . . | . . . . . . . . . . .
      . . . . * . . . ) . . . . . . . . . . .
       . . . . = . . & . . . . . . . . . . .
        . . . . > } < . . . . . . . . . . .
         . . . . . . . . . . . . . . . . .
          . . . . . . . . . . . . . . . .
           . . . . . . . . . . . . . . .
            . . . . . . . . . . . . . .
             . . . . . . . . . . . . .

Yan not: Yukarıdaki kod no-ops ile dolu olan ilk satırı çalıştırmakla başlar. Ardından IP kuzey doğu kenarına çarptığında ), gerçek kodun başladığı en soldaki köşeye (the ) sarılır .

Başlamadan önce, Hexagony'nin hafıza düzeni hakkında bir kelime. Brainfuck'ın steroid bantındaki gibi. Aslında, bu bir kaset değil, ancak her köşenin başlangıçta 0 olan bir tamsayı değerine sahip olduğu (sonsuz bir tane) altıgen bir ızgaradır (ve standart Brainfuck'ın aksine, değerler isteğe bağlı tamsayılar işaretlenir). Bu program için dört kenar kullanacağız:

görüntü tanımını buraya girin

Faktör A kenarını hesaplayacağız, C kenarındaki girişimizi sayıp, D girişindeki girişin bir başka kopyasını (modulo için) saklayacağız . B hesaplamalar için geçici bir kenar olarak kullanılır.

Bellek işaretçisi (MP) A kenarından başlar ve kuzeye işaret eder (bu, MP'nin etrafını dolaştırması için önemlidir). Şimdi kodun ilk kısmı:

)}?}=&{

)Faktörlüğün temeli olarak A noktasındaki artış 1. }MP'nin sağa dönmesini sağlar, yani C kenarına hareket eder (kuzeydoğuya işaret eder). Burada girişi bir tamsayı olarak okuruz ?. Sonra D ile kenara bir kez daha sağa dönüyoruz }. =MP'yi tersine çevirir, öyle ki C ile paylaşılan tepe noktasını gösterir . &değeri C'den (giriş) D'ye kopyalar - değer soldan kopyalanır, çünkü geçerli değer pozitif değildir (sıfır). Son olarak, milletvekili ile sola C dönüş sola yapmak {.

Daha sonra <, teknik olarak bir daldır, ancak mevcut değerin pozitif olduğunu biliyoruz, bu nedenle IP her zaman doğru olacaktır >. Yandan gelen bir dal, IP'nin tekrar yatay olarak hareket (ettiği ve C'deki değeri azaltan bir ayna gibi davranır .

Bir sonraki dalı <olan aslında şimdi bir dal. Bu, n-1aşağıdan aşağıya doğru nasıl döndüğümüzdür 1. C'deki geçerli değer pozitif olsa da , IP sağa döner (döngüyü çalıştırmak için). Bir kere sıfıra gidince, bunun yerine sola döner.

"Vücut" döngüsüne bakalım. |Basit aynalar vardır >ve <ayrıca yine aynalar olarak kullanılır. Bu, gerçek döngü gövdesinin aşağı doğru kaydığı anlamına gelir

}=)&}=*}=

}Kenar MP hareket B , =tepe yüz yönünü tersine ABC . )değeri artırır: bu sadece B'nin değerinin hala sıfır olduğu ilk yineleme ile ilgilidir : pozitif olmasını sağlamak istiyoruz, böylece bir sonraki komut sağdaki komşuyu, yani A'yı , yani faktörün mevcut değerini &kopyalar. hesaplama, B'ye .

}daha sonra MP hamle A , =ortak köşe yüz tekrar tersine çevirir. *her iki komşuyu, yani B ve C kenarlarını çoğaltır ve sonucu A'da saklar . Son olarak, yine de ABC tepe noktasına bakan C'ye}= dönmek için başka bir yolumuz var .

Bu faktöriyelini hesaplar nasıl görebilirsiniz umut n-1içinde A .

Şimdi bunu yaptık, C'deki döngü sayacı sıfırdır. Faktörün karesini almak ve sonra moduleti girdi ile almak istiyoruz. Bu kodun yaptığı şey:

&}=*{&'%!@

Yana C sıfırsa, &içinde faktöriyele yani kopya sol komşu, A . B'ye}=* taşınır ve faktoringin iki kopyasının (yani kare) B ürününde depolanır . C'ye geri döner , ancak MP'yi tersine çevirmez. Biz şimdiki değeri için bunu hemen olumlu olduğunu biliyoruz kopyalar girişten D içine C . MP sağa geri , yani A üzerine . Unutmayın, faktörlerin karesi B'de ve giriş C cinsindendir . Yani hesaplar , tam olarak aradığımız şey.{&'%(n-1)!^2 % n!sonucu bir tamsayı olarak (0 veya 1) yazdırır ve @programı sonlandırır.


Tamam, ama bu asılsız versiyondu. Golf versiyonundan ne haber? Altıgen hakkında iki şey daha bilmelisin:

  1. Kenarlar etrafına sarılır. IP, altıgenin bir kenarına çarparsa, karşı kenara atlar. IP bir köşeye doğrudan çarptığında belirsizdir, bu nedenle bir köşeye vurmak da dal gibi davranır: geçerli değer pozitifse, IP ızgara kenarına sağa, aksi halde sola doğru atlar.
  2. Aslında 6 IP var. Her biri kenar boyunca saat yönünde hareket ederek farklı bir köşede başlar. Bir seferde yalnızca bir tanesi aktif durumda, bu da istemiyorsanız diğer 5 IP'yi görmezden gelebileceğiniz anlamına gelir. Bir sonraki IP'ye (saat yönünde) ]ve ile bir önceki IP'ye geçebilirsiniz [. ( #Bununla birlikte belirli bir tane de seçebilirsiniz , ancak bu başka bir zaman içindir.)

Orada o birkaç yeni komutlar da şunlardır: \ve /benzeri aynalar vardır |ve ~geçerli değerini çarpar -1.

Peki, ungolfed versiyonu nasıl golfe dönüştürülür? Doğrusal kurulum kodu )}?}=&{ve temel döngü yapısı burada bulunabilir:

        ) } ? } .  ->
       . . . . . .
      . . . . . . .
     . . . . . . . .
->  . = & { . < . . .
     . . . . . > ( <
      . . . . . . .
       . . . . . .
        . . . . .

Şimdi döngü gövdesi kenarları birkaç kez geçiyor, ancak en önemlisi, gerçek hesaplama önceki IP'ye (sol köşeden başlar, kuzey doğuya doğru hareket ediyor) verilir:

        ) . . . .
       = . . . ] .
      } = . . } . .
     ~ . / . * . . .
    . . . . . . . . .
     . . . = . > ( <
      . . } . = . .
       . & . \ [ .
        . . . . .

Dalın güney doğuya doğru sıçramasından sonra IP, kenarın etrafını =sol üst köşedeki (birlikte, bir op-op olmayan) ikiye doğru sarar , sonra da sıçrar /. ~Sonraki tekrarlamalar için önemli olan şimdiki değerinin, işaretini ters çevirir. IP aynı kenarın etrafına tekrar sarılır ve nihayet [kontrolün diğer IP'ye verildiği yere vurur .

Bu, şimdi ~}=)&}=*}olumsuzlamayı geri alan ve işte sadece ungolfed döngü gövdesini (eksi =) çalıştırıyor. Sonunda ]hangi ellerin orijinal IP'ye döndüğünü kontrol eder. (Bir dahaki sefere bu IP'yi yürüttüğümüzü, bıraktığı yerden başlayacağını, böylece ilk köşeye çarpacağını unutmayın. IP'nin kuzey batı kenarına geri sıçraması için mevcut değerin negatif olması gerekir.) güney doğu yerine

Orijinal IP kontrolü tekrar başlattığında \, zıplar, kalanı yürütür ve bir sonraki döngü yinelemesine beslemek için =vurur >.

Şimdi gerçekten çılgın kısım: döngü sona erdiğinde ne olur?

        ) . . . .
       . ( . . ] =
      . . ' . } . }
     . . . % * . . &
    . . . . . . . . .
     . . . = | . . <
      . . } ! . . .
       . & @ . . .
        . . . . .

IP kuzey doğu yönünde hareket eder ve kuzey doğu <köşesine dolanır. Bu yüzden döngü gövdesi ( &}=*}]) ile aynı uygulama yolunda sona erer . Bu aslında oldukça havalıdır, çünkü bu noktada çalıştırmak istediğimiz kod budur, en azından bir tane eklersek =}(çünkü buna }=}eşittir {). Fakat bu nasıl daha önceki döngüye tekrar girmez? Çünkü bir ]sonraki IP’de olan ve şu ana kadar kullanılmayan IP’ye dönüşen sağ üst köşeden başlayıp güneye doğru ilerliyor. Oradan IP, kenar boyunca devam eder, sol üst köşeye sarar, köşegen aşağı doğru hareket eder, zıplar |ve @doğrusal kodun son bitini yürütürken sona erer :

=}&)('%!@

( )(Tabii ki hayır-op - (çünkü )zaten vardı çünkü eklemek zorunda kaldı .)

Phew ... ne dağınıklık ...


Güzel! Bu ne kadar yeni? Ayrıca, bir kararlı sürümü olsun her bir esolangs sayfası oluşturmak isteyebilirsiniz
mbomb007

18
@ mbomb007 Dili iki gün önce uyguladım (ve bundan iki veya üç gün önce tasarladım). Ve evet, kesinlikle bir esolangs sayfası ekleyeceğim, ancak spesifikasyonun henüz% 100 kararlı olmadığını düşünüyorum (örneğin hala 3 atanmamış komut var). Daha istikrarlı olduğunu hissettiğimde, onu hem esolanjlara hem de meta post'umuza ekleyeceğim.
Martin Ender

Genişletilmiş altıgen altında, en sol köşeye (the 1) kaydırılır . Orada ne 1hakkında konuşuyorsun?
mbomb007 13:15

@ Mbomb007 düzeltildi. Kullanılan )bir 1.
Martin Ender

5
Nasıl çalıştığını açıklamada sadece ayrıntı seviyesi için +1. Daha fazla dilde, daha fazla sayıda insanın kullanabileceği bir örnek daha fazla
gelirse

66

Pyth, 4 bayt

}QPQ

TrueVeya yazdırır False.


12
Bunun eski olduğunu biliyorum ama şimdi bunu da yapabilirsiniz: P_Q ve 1 byte tasarruf edin.
drobilc

14
Şimdi mümkünP_
Blue

3
@drobilc Bir argüman beklerken, EOF olarak Q'yu kesebilirsiniz, girişi kullanır
Stan Strum

55

Retina , 16 bayt

^(?!(..+)\1+$)..

Çevrimiçi deneyin!

Klasik ile başlayalım: asalları bir regex ile tespit etmek . Girdi tekrarlanan herhangi bir basılabilir karakter kullanılarak , unary olarak verilmelidir . Test paketi, kolaylık sağlamak için ondalıktan birime kadar bir dönüşümü içerir.

Tek bir satırdan oluşan bir Retina programı, bu satırı bir regex olarak kabul eder ve girişte bulunan ve 0bileşik sayılar ve 1asal sayılar için eşleşecek sayıların sayısını yazdırır .

Bakış açısı, girişin birleşik olmamasını sağlar: geriye izleme, mümkün olan her alt dizgiyi (en az 2 karakter) deneyecektir (..+); Bu mümkünse, girişin 1'den büyük, ancak kendisinden küçük bir bölen olduğu anlamına gelir. Bu durumda, negatif görünüm, eşleşmenin başarısız olmasına neden olur. Asal sayılar için böyle bir olasılık yoktur ve maç devam eder.

Tek sorun bu bakış açısının da kabul etmesidir 1, bu yüzden en az iki karakterle eşleştirerek bunu ekarte ediyoruz ...


Asal olarak düzensiz bir ifadedir, çünkü ilk harfler normal bir dil oluşturmaz.
PyRulez

@PyRulez Gerçek dünyadaki regex tatlarının çoğu, düzenli ifadelerin teorik konseptinden çok daha güçlüdür. İfadeleri yine de geliştirdim.
Martin Ender

1
Şu anda açıkta bulunan en güçlü "regex" motorları artık doğrusal sınırlı bir otomatınkine eşit tanıma gücüne sahip. Standart sorun regex, desen özyinelemesi, sınırsız bakış açısı ve sınırsız bakış açısı, içeriğe duyarlı ayrıştırma için ihtiyacınız olan tek şeydir (geri referanslar ve genel olarak verimli bir ayrıştırma işlemine yardımcı olmak için olsa da). Beni regex içine gömeceğiniz motorlara bile başlama.
eaglgenes101

52

CJam, 4 bayt

qimp

CJam, ilkellik testi için yerleşik bir operatöre sahiptir.


18
Alternatif olarak:limp
Sp3000 11:15

43
pimpcanım benim
kusur

12
pimpobjektif olarak daha pezevenk
MickLH 12:15

1
Bunları da yapabilirsinizl~mp
İnekler,

12
@Cyoce, qbir girdi satırı okur, ibir tamsayı olarak ayrıştırır ve mpyerleşiktir. CJam'da iki şarja sahip iki grup var: "genişletilmiş" olanlar başlıyor eve "matematiksel" olanlar başlıyorm
Peter Taylor

47

HTML + CSS, 254 + n maks. * 28 bayt

Düzenli ifadeler kullanarak ilkelliği kontrol edebiliriz. Mozilla, @documentşöyle tanımlanmıştır:

@document [ <url> | url-prefix(<string>) | domain(<string>) | regexp(<string>) ]# {
  <group-rule-body>
}

Öğeleri geçerli URL'ye göre CSS üzerinden filtrelemek için. Bu tek bir geçiştir, bu yüzden iki adım atmamız gerekiyor:

  1. Kullanıcıdan girdi alın. Bu giriş bir şekilde geçerli URL'ye yansıtılmalıdır.
  2. Kullanıcıya olabildiğince az kod yazarak yanıtlayın.

1. Giriş Alma

Giriş almanın ve URL'ye aktarmanın en kısa yolu GETonay kutularını içeren bir formdur. Regex için, sadece görünümleri saymak için bazı benzersiz dize ihtiyacımız var.

Böylece bununla başlayacağız (61 bytes):

<div id=q><p id=r>1<p id=s>0</div><form method=GET action=#q>

<p>Girilen sayının asal (1) olup olmadığını (0) belirtmek için iki benzersiz s elde ettik . Ayrıca formu ve eylemini de tanımlarız.

Aynı adda n max onay kutusunu takip edin (n max * 28 bytes):

<input type=checkbox name=i>

Gönderme öğesi tarafından takip edilen (34 bayt):

<input name=d value=d type=submit>

2. Cevabı Göster

<p>Ekranı seçmek için CSS'ye (159 bayt) ihtiyacımız var (1 veya 0):

#q,#s,#q:target{display:none}#q:target{display:block}@-moz-document regexp(".*\\?((i=on&)?|(((i=on&)(i=on&)+?)\\4+))d=d#q$"){#s{display:block}#r{display:none}}

»Codepen.io adresinde deneyin (yalnızca firefox)


12
+1: Bu benim tüm zamanların en sevdiğim HTML suistimali ve beni kodlayıcı aşkı yapan türler.
kedi

Bu kesinlikle ilginç, ancak bu zorluğun kurallarını yerine getirip getirmediğinden emin değilim. Özellikle, algoritmanıza [...] uygun olduğunu sanmıyorum , teoride, keyfi olarak büyük tamsayılar için çalışmalı. Bir giriş alanının değerinde bir regex kullanamaz mıydınız?
Dennis

@Dennis Belki. Muhtemelen bile. Fakat bu bahsettiğiniz sorunu çözmez. Buraya yarışmacı olmayan bir giriş olarak bırakıyorum, çünkü bu konudaki en büyük zorluk.
mınxomaτ

Neden olmasın? Bir giriş alanında unary bir numaranız varsa, kodunuz artık maksimum sayıya bağlı olmaz.
Dennis,

4
Hm, bunu biraz daha düşündüm ve sadece x onay kutularına sahip olmak ve sadece y-bit sayılarına sahip bir tercüman arasında hiçbir fark yok. Önceki yorumumu dikkate almayın.
Dennis,


40

Altıgen , 28 bayt

Yana Etoplay kesinlikle beni bozguna Bu soru , ben onun sadece diğer outgolf zorunda hissetti cevabı .

?\.">"!*+{&'=<\%(><.*.'(@>'/

Çevrimiçi deneyin!

Martin'in cevabında yaptığı gibi Wilson teoremi kullanıyorum : Verdiğim n, çıktı(n-1!)² mod n

İşte program açıldı:

   ? \ . "
  > " ! * +
 { & ' = < \
% ( > < . * .
 ' ( @ > ' /
  . . . . .
   . . . .

Ve işte okunabilir sürüm:

Çok okunabilir

Açıklama:

Programın üç ana adımı vardır: Başlatma , Faktör ve Çıktı .

Hexagony'nin bellek modeli sonsuz altıgen bir ızgaradır. Bu şemada gösterildiği gibi 5 bellek yeri kullanıyorum:

Hafıza

Bu konumlara (ve içlerinde saklanan tam sayılara) bu şema üzerindeki etiketlerinden bahsedeceğim.

Başlatma:

Başlangıç ​​durumuna

Talimat işaretçisi ( IP ), sol üst köşede başlar ve Doğu'ya gider. Bellek işaretçisi ( MP ) IN'de başlar .

İlk olarak, ?girişten sayıyı okur ve IN içine kaydeder . IP yansıyan mavi yolu kalır \. Dizisi "&(taşır MP geri ve sola (üzere A ), kopya gelen değeri IN için A ve azaltır o.

IP sonra altıgen bir tarafından çıkar ve (yeşil yola) diğer tarafı yeniden girer. Bu yürütür '+hareket eden MP için B ve içinde ne kopya A . IP'yi Batı'ya <yönlendirir .

Çarpınım:

Faktörlüğü belirli bir şekilde hesaplarım, böylelikle kareyi kolayca almak kolaydır. Depolayabilir n-1!hem de B ve C aşağıdaki gibi.

Çarpınım

Komut işaretçisi, Doğu yönünde ilerleyen mavi yoldan başlar.

='MP'nin yönünü tersine çevirir ve C'ye geri hareket ettirir . Bu eşdeğerdir {=ancak daha sonra =nerede olduğu konusunda yardımcı olmuştur.

&{gelen değer kopyalar bir üzere C , daha sonra hareket eder MP geri bir . IP sonra, kırmızı yolunu ulaşmadan isabet önce, hiçbir şey yapmadan, yeşil yolu izler \ve turuncu yoluna gidiyor.

İle A'yı(> düşürüp IP Doğu'yu yönlendiriyoruz . Burada bir şube vurur: . A pozitif için , turuncu yol boyunca devam ediyoruz. Aksi takdirde IP Kuzey-Doğu'ya yönlendirilir.<

'*hamle MP için B ve depolayan bir * C de B . Burası (n-1)*(n-2)ilk girişin olduğu yerdi n. IP sonra tekrar ilk döngüye girer ve azalan ve çoğalan kadar devam bir ulaşır 0. (bilgi işlem n-1!)

Not : Aşağıdaki döngüler üzerinde &değeri depolar B de C olarak, şimdi depolanan pozitif bir değere sahiptir. Bu bilgi işlem faktörü için çok önemlidir.

Çıktı:

Çıktı

Ne zaman bir ulaşır 0. Dal IP'yi mavi yol boyunca yönlendirir .

=*ters MP ve depolar değerini B * C de A . Sonra IP altıgenden çıkar ve yeşil yola tekrar girer; yürütülmesi "%. Bu, MP’yi OUT’a taşır ve A mod IN veya calcu değerini hesaplar (n-1!)² mod n.

Aşağıdakiler {"birbirlerini iptal ettiği için no-op görevi görür. !Nihai çıktıyı baskı ve *+'(sonlandırma önce yürütülür: @.

Yürütmeden sonra (bir giriş ile 5) bellek şöyle görünür:

Memory2

Kontrol akışının güzel görüntüleri kullanılarak yapılmıştır Timwi en Hexagony Coloror .

Bilgisayarımda yapamadığım için tüm görüntüleri oluşturduğunuz için Martin Ender'e teşekkür ederim .


Bu hafıza diyagramları için ne kullanıyorsunuz? Ezoterik
IDE'yi

@NieDzejkob, Martin'e sohbette sormakta daha iyi, çünkü o zaten benim için yaptı.
H.PWiz

@NieDzejkob Evet, bellek şeması EsoIDE'den dışa aktarılabilir. Bu konuda daha fazla sohbet etmek istiyorsanız, chat.stackexchange.com/rooms/27364/… .
Martin Ender

33

Mornington Crescent , 2448 bayt

Londra'ya geri döndük !

Take Northern Line to Bank
Take Circle Line to Bank
Take District Line to Parsons Green
Take District Line to Bank
Take Circle Line to Hammersmith
Take District Line to Upney
Take District Line to Hammersmith
Take Circle Line to Victoria
Take Victoria Line to Seven Sisters
Take Victoria Line to Victoria
Take Circle Line to Victoria
Take Circle Line to Bank
Take Circle Line to Hammersmith
Take Circle Line to Cannon Street
Take Circle Line to Hammersmith
Take Circle Line to Cannon Street
Take Circle Line to Bank
Take Circle Line to Hammersmith
Take Circle Line to Aldgate
Take Circle Line to Aldgate
Take Metropolitan Line to Chalfont & Latimer
Take Metropolitan Line to Aldgate
Take Circle Line to Hammersmith
Take District Line to Upminster
Take District Line to Hammersmith
Take Circle Line to Notting Hill Gate
Take Circle Line to Hammersmith
Take Circle Line to Notting Hill Gate
Take District Line to Upminster
Take District Line to Bank
Take Circle Line to Victoria
Take Circle Line to Temple
Take Circle Line to Aldgate
Take Circle Line to Aldgate
Take Metropolitan Line to Chalfont & Latimer
Take Metropolitan Line to Pinner
Take Metropolitan Line to Chalfont & Latimer
Take Metropolitan Line to Pinner
Take Metropolitan Line to Chalfont & Latimer
Take Metropolitan Line to Pinner
Take Metropolitan Line to Aldgate
Take Circle Line to Hammersmith
Take District Line to Upminster
Take District Line to Victoria
Take Circle Line to Aldgate
Take Circle Line to Victoria
Take Circle Line to Victoria
Take District Line to Upminster
Take District Line to Embankment
Take Circle Line to Embankment
Take Northern Line to Angel
Take Northern Line to Moorgate
Take Metropolitan Line to Chalfont & Latimer
Take Metropolitan Line to Aldgate
Take Circle Line to Aldgate
Take Circle Line to Cannon Street
Take District Line to Upney
Take District Line to Cannon Street
Take District Line to Acton Town
Take District Line to Acton Town
Take Piccadilly Line to Russell Square
Take Piccadilly Line to Hammersmith
Take Piccadilly Line to Russell Square
Take Piccadilly Line to Ruislip
Take Piccadilly Line to Ruislip
Take Metropolitan Line to Preston Road
Take Metropolitan Line to Aldgate
Take Circle Line to Aldgate
Take Circle Line to Cannon Street
Take Circle Line to Aldgate
Take Circle Line to Aldgate
Take Metropolitan Line to Preston Road
Take Metropolitan Line to Moorgate
Take Circle Line to Moorgate
Take Northern Line to Mornington Crescent

Timwi denetim akışı istasyonları uygulamak o kadar nazikti Templeve Angeliçinde Ezoterik IDE yanı sıra dil şartnameye girdi ve tamsayı ayrıştırmayı ekleyin.

Bu muhtemelen "Merhaba Dünya!" Dan daha iyi golf oynamıştır, çünkü bu sefer herhangi bir iki istasyon arasındaki en kısa yolu bulmama yardımcı olmak için bir CJam senaryosu yazdım. Kullanmak istersen (neden birisinin istediğini bilmesem de ...), çevrimiçi tercümanı kullanabilirsin . Bu kodu yapıştırın:

"Mornington Crescent"
"Cannon Street"
]qN/{'[/0=,}$:Q;{Q{1$#!}=\;_oNo'[/1>{']/0="[]"\*}%}%:R;NoQ{R\f{f{\#)}:+}:*},N*

Buradaki ilk iki satır kontrol etmek istediğiniz istasyonlardır. Ayrıca bu pastebin içeriğini giriş penceresine yapıştırın .

Çıktı size iki istasyonda hangi hatların bulunduğunu ve ardından ikisini bağlayan tüm istasyonların istasyon adlarının uzunluğuna göre sıralandığını gösterir. Bunların hepsini gösterir, çünkü bazen daha kısa bir çizgiye izin verdiği için veya istasyonun özel (Banka veya Tapınak gibi) olması nedeniyle daha uzun bir ad kullanmak daha iyidir. İki istasyonun başka herhangi bir başka istasyonla (özellikle de Metropolitan ve District hatları asla birbirine geçmez) bağlı olmadığı bazı kenar durumları vardır, bu durumda başka bir şey bulmanız gerekir. ;)

Gerçek MC koduna gelince, kare çarpma yaklaşımına dayanıyor, çünkü MC çarpma, bölme ve modulo özelliklerine sahip. Ayrıca, tek bir döngünün uygun olacağını düşündüm.

Bir konu döngüler döngüler ve eksiltilmesi ve artırım yapılması pahalı iken-do yüzden kolayca hesaplanamaz olmasıdır (n-1)!(için n > 0). Bunun yerine, hesaplama yapıyorum ve sonunda n!bölün n. Bunun için daha iyi bir çözüm olduğuna eminim.

Bunu yazmaya başladığımda -1, Hammersmith'te depolamanın iyi bir fikir olacağını düşündüm, bu yüzden daha ucuz bir şekilde azaltabilirim, ama sonuçta bu tasarruftan daha pahalıya mal olabilir. Bunu yinelemenin sabrını bulursam, -1bunun yerine Upminster'de bir yer tutmayı deneyebilirim, böylece Hammersmith'i daha yararlı bir şey için kullanabilirim.


10
Londra turingi tamamlandı mı?
Rohan Jhunjhunwala


Vaov! İyi düşünülmüş soruları görmeyi seviyorum. Özellikle program yazmak için program yazmanız gereken soruları görmeyi çok seviyorum.
Rohan Jhunjhunwala

27

Brakilog (V2), 1 bayt

Çevrimiçi deneyin!

Brakilog (V1), 2 bayt

#p

Bu #p - Prime, girişini asal sayı olarak sınırlayan yerleşik yüklemi kullanır .

Brachylog, Prolog’un Code Golf versiyonunu yapma girişimidir.

Yerleşik olmayan alternatif çözüm: 14 bayt

ybbrb'(e:?r%0)

İşte yukarıdaki kodun bir dökümü:

y            The list [0, …, Input]
bbrb         The list [2, …, Input - 1]
'(           True if what's in the parentheses cannot be proven; else false
     e           Take an element from the list [2, …, Input - 1]
     :?r%0       The remainder of the division of the Input but that element is 0
)

1
Bunun Brachylog 2 versiyonunu da yazımda düzenlemek isteyebilirsiniz, şimdi sözdizimi bir bayt daha kısadır.

1
@ ais523 Doğru, bitti.
17'de

Brachylog 2 cevap sonrası mücadeleye cevap veriyor mu?
Scott Milner

1
@ScottMilner Evet, ancak bu zorlukla açıkça buna izin verilir: "Her zamanki kurallarımızdan farklı olarak, bu zorluğundan daha yeni olsa bile, bir dil (veya dil sürümü) kullanmaktan çekinmeyin"
17'de

26

Haskell, 49 bayt

Xnor'ın Corollary'unu Wilson'un Teoremine Kullanma :

main=do n<-readLn;print$mod(product[1..n-1]^2)n>0

Yapması daha kısa olmaz mıydı main=interact$\n-> ...?
John Dvorak

2
Karşı yönden, hayır! interact...readOrada bir yerde ihtiyacın olduğunu düşün , ki bu da sadece olduğundan daha uzun sürecek readLn. Çoğunlukla dogösterim, özellikle alternatif bir lambda olduğunda beklediğinizden daha özlü olabilir.
Lynn

24

Labirent , 29 bayt

1
?
:
}  +{%!@
(:'(
 } {
 :**

STDIN'den bir tam sayı okur ve çıktılar ((n-1)!)^2 mod n. Wilson teoremi bu zorluk için oldukça faydalıdır.

Program, sol üst köşeden başlayarak 1, yığının tepesini 10 ile çarparak başlar ve 1 ekler. Bu, Labyrinth'in büyük sayılar oluşturma yöntemidir; sadece bir 1 itti.

?sonra nSTDIN'den okur ve :kopyalar. }Modülün nsonunda kullanılacak yardımcı yığına geçer . (sonra azalır nve kare faktörlülüğü hesaplamaya başlamaya hazırız.

İkinci :(yinelenen) bir kavşakta ve burada Labyrinth'in kontrol akışı özellikleri devreye giriyor. Bir talimat yapıldıktan sonra bir kavşakta, yığının tepesi pozitifse sağa döneriz, negatif için sola döneriz ve sıfır için dümdüz ilerleriz. Dönmeye çalışıp duvara vurmaya çalışırsanız, Labyrinth bunun yerine diğer yöne dönmenizi sağlar.

Çünkü n = 1, yığının tepesi nazaldığından ya da 0dümdüz ilerleriz. Sonra no-op'lara çarptık, 'ardından (bizi koyan başka bir düşüş izledi -1. Bu negatiftir, bu yüzden sola dönüp, yardımcı yığından ana ve modulo'ya ( ) geri dönmek için +artı ( -1 + 0 = -1) komutunu uygularız . Daha sonra çıktı ile sonlandırıyoruz .{n%-1 % 1 = 0!@

Çünkü n > 1, ikinci :olarak sağa dönüyoruz. Daha sonra }kopyalanan döngü sayacını yardımcı yığına kaydırırız, sayacı geri değiştirmeden ve azaltmadan önce :iki kez çoğaltır ve çoğaltırız . Hala pozitifsek sağa dönmeye çalışıyoruz ama yapamayız, bu yüzden Labyrinth bunun yerine bizi sola döndürerek döngüyü devam ettiriyor. Aksi halde, yığının tepesi, hesapladığımıza eklediğimiz 0'a indirgenmiş döngü sayacımızdır . Sonunda modulo ile geri döneriz , çıktı verir ve sonlandırırız .**{(+((n-1)!)^2n{%!@

Bunun sözü geçen 'no-op, ama aynı zamanda ayıklama için de kullanılabilir. -dHer geçişte yığının durumunu görmek için bayrakla koşun '!


2
Faktörün karesini almak gerçekten harika bir numara :)
Lynn

@ Mauris Teşekkürler!
Olması

5
Yay, ilk labirent cevap bana yazılmadı! :)
Martin Ender

24

Bash + GNU yardımcı programları, 16

  • @Dennis sayesinde 4 bayt kaydedildi

  • @Lekensteyn sayesinde 2 bayt kurtarıldı

factor|awk NF==2

Giriş, STDIN'den alınan bir satırdır. Çıktı falsey için boş dize ve truthy için boş olmayan bir dizedir. Örneğin:

$ ./pr.sh <<< 1
$ ./pr.sh <<< 2
2: 2
$ ./pr.sh <<< 3
3: 3
$ ./pr.sh <<< 4
$

2
Cool, başka bir coreutil hakkında bilgi edindi. factor|awk NF==2
Alan

@Lekensteyn - teşekkürler - nedense daha önce yorumunuzu kaçırdım :)
Digital Trauma

Biraz daha benzer ve daha uzun ve AWK'sız bir şeyler gönderecektim. Güzel bitti.
David Conrad

21

Java, 126 121 bayt

Sanırım skorbord için bir Java cevabına ihtiyacımız var ... işte basit bir deneme bölümü döngüsü:

class P{public static void main(String[]a){int i=2,n=Short.valueOf(a[0]);for(;i<n;)n=n%i++<1?0:n;System.out.print(n>1);}}

Java için her zaman olduğu gibi, "tam program" gereksinimi, çoğunlukla mainimzadan dolayı, bir işlev olsaydı, olduğundan çok daha büyük olmasını sağlar .

Genişletilmiş biçimde:

class P{
    public static void main(String[]a){
        int i=2,n=Short.valueOf(a[0]);
        for(;i<n;)
            n=n%i++<1?0:n;
        System.out.print(n>1);
    }
}

Düzenleme: Yorumlarda Peter tarafından Sabit ve regolfed. Teşekkürler!


Buggy: Bunun 1asal olduğunu bildirdi . Aksi halde çıkartarak pve söyleyerek 4-char tasarruf olacaktırfor(;i<n;)n=n%i++<1?0:n;System.out.print(n>0);
Peter Taylor

2
OTOH class P{public static void main(String[]a){int i=2,n=Short.valueOf(a[0]);for(;i<n;)n=n%i++<1?0:n;System.out.print(n>1);}}çalışır
Peter Taylor

6
satır 3 'ü' long i = 2, n = Long.valueOf (a [0]) 'a değiştirerek; `uzunlukta değişiklik olmamakla birlikte daha geniş bir geçerli girdi aralığı elde edilir.
James K Polk

4
Yerine .valueOfsize kullanabilirsiniz newolduğu gibi new Short(a[0]), ya da new Long(a[0])biraz daha kısa olan.
ECS

3
Bir arabirim kullanarak ve publicdeğiştiriciyi bırakarak 4 bayt kaydedebilirsiniz .
RamenChef

18

Brain-Flak , 112 108 bayt

({}[()]){((({})())<>){{}<>(({}<(({}[()])()<>)>)<>)<>{({}[()]<({}[()]<({}())>)>{(<()>)}{})}{}{}}}<>{{}}([]{})

Çevrimiçi deneyin!

Nasıl çalışır

İlk olarak, ilk yığın n pozitif bir tamsayı içerecek , ikinci yığın boş olacaktır.

Biz azaltılmasıyla başlamak n aşağıdaki gibi.

(
  {}      Pop n.
  [()]    Yield -1.
)       Push n - 1.

n = 1

Eğer , n = 1 sıfır, döngüdür

{
  ((({})())<>)
  {
    {}<>(({}<(({}[()])()<>)>)<>)<>{({}[()]<({}[()]<({}())>)>{(<()>)}{})}{}{}
  }
}

tamamen atlandı. Son olarak, kalan kod yürütülür.

<>    Switch to the second stack (empty).
{}    Pop one of the infinite zeroes at the bottom.
{<>}  Switch stacks while the top on the active stack is non-zero. Does nothing.
(
  []    Get the length of the active stack (0).
  {}    Pop another zero.
)     Push 0 + 0 = 0.

n> 1

N - 1 sıfır değilse , n = 1 atlayan döngüye gireriz . Bu "gerçek" bir döngü değil; kod yalnızca bir kez yürütülür. Aşağıdakileri gerçekleştirir.

{                   While the top of the active stack is non-zero:
  (
    (
      ({})                Pop and push n - 1.
      ()                  Yield 1.
    )                   Push n - 1 + 1 = n.
    <>                  Switch to the second stack. Yields 0.
  )                   Push n + 0 = n.
                      We now have n and k = n - 1 on the first stack, and n on
                      the second one. The setup stage is complete and we start
                      employing trial division to determine n's primality.
  {                   While the top of the second stack is non-zero:
    {}                  Pop n (first run) or the last modulus (subsequent runs),
                        leaving the second stack empty.
    <>                  Switch to the first stack.
    (
      (
        {}                  Pop n from the first stack.
        <
          (
            (
              {}              Pop k (initially n - 1) from the first stack.
              [()]            Yield -1.
            )               Push k - 1 to the first stack.
            ()              Yield 1.
            <>              Switch to the second stack.
          )               Push k - 1 + 1 = k on the second stack.
        >               Yield 0.
      )               Push n + 0 = n on the second stack.
      <>              Switch to the first stack.
    )               Push n on the first stack.
    <>              Switch to the second stack, which contains n and k.
                    The first stack contains n and k - 1, so it is ready for
                    the next iteration.
    {({}[()]<({}[()]<({}())>)>{(<()>)}{})}{}{}  Compute and push n % k.
  }               Stop if n % k = 0.
}               Ditto.

n% k , bölünebilirlik testi cevabımdaki 42 bayt modül algoritması kullanılarak hesaplandı .

Son olarak n'in ilkliğini belirlemek için sonuçları yorumladık .

<>    Switch to the first stack, which contains n and k - 1, where k is the
      largest integer that is smaller than n and divides n evenly.
      If (and only if) n > 1 is prime, k = 1 and (thus) k - 1 = 0.
{     While the top of the first stack is non-zero:
  {}    Pop it.
}     This pops n if n is prime, n and k - 1 if n is composite.
(
  []    Yield the height h of the stack. h = 1 iff n is prime).
  {}    Pop 0.
)     Push h + 0 = h.

2
Son 0'ı yığına sokmanıza gerek yok, çünkü üstteki gerçek 1 yeterlidir; sonuncuyu kaldırarak iki byte'ı bu şekilde kaydedebilirsiniz {}.
Steven H.

1
Hımm, yırtıldım. Bir yandan, soru söylüyor çıkış yalnızca bir truthy veya falsy değerin oluşmalıdır ve 1 0bir iki değer. Öte yandan, dil truthy veya falsy olarak gördüğü sürece dizileri kabul ederiz ve çoklu yığın öğeleri Brain-Flak'ın dizileri için en yakın şeydir. Bu meta için almaya değer olabilir.
Dennis,

Brain- 1 0Flak'ın yaratıcısı ile gerçek olanı doğruladım. chat.stackexchange.com/transcript/message/32746241#32746241
Steven H.


17

R, 37 29 bayt

n=scan();cat(sum(!n%%1:n)==2)

Deneme bölümünü kullanır. scan()STDIN'den bir tamsayı okur ve STDOUT'a cat()yazar.

n1'den nmodüle tamsayılardan oluşan bir uzunluk vektörü üretiyoruz n. Her biri 0 olup olmadığını, 0 !olduğunda ve 0'dan büyük olduğunda yanlış olan mantıksal bir değer döndüren negatif ( ) olup olmadığını test ederiz. Mantıksal bir vektörün toplamı, gerçek elemanların sayısıdır ve asal sayılar için Sıfır olmayan tek modüllerin 1 olması ve ndolayısıyla toplamın 2 olmasını bekliyoruz.

Flodel sayesinde 8 bayt kurtarıldı!


İle f=function(x)sum(!x%%1:x)==2size 28 bayt yapabilirsiniz.
Mutador

2
@ AndréMuta Bu görev için, tüm bildirimler sadece fonksiyonlardan ziyade tam programlar olmalıdır. Öneriniz için teşekkürler.
Alex A.

17

TI-BASIC, 12 bayt

2=sum(not(fPart(Ans/randIntNoRep(1,Ans

Oldukça basit. randIntNoRep(1 ile 1 arasındaki tüm tam sayıların rastgele bir permütasyonunu verir Ans.

Bu kurallara biraz eğilir; çünkü TI-BASIC’teki listeler, yorumladığım 999 öğeyle sınırlı

girişin veri türünüzde saklanabileceğini varsayalım

tüm veri tiplerinin girdiyi barındırdığı varsayılabilir. OP bu yorumu kabul eder.

Bir 17-bayt çözüm aslında 10 ^ 12 veya öylesine kadar çalışır:

2=Σ(not(fPart(Ans/A)),A,1,Ans

@toothbrush TI-BASIC tokenize edilmiş bir dildir, bu yüzden buradaki her simge randIntNoRep(iki olan hariç bir bayttır .
lirtosiast 13:15

+1 Ah, daha önce TL-BASIC görmemiştim. Bana
Diş Fırçası

1
Rağmen, olduğu bu biraz haksız değildir ...? Sadece 1-4 bayt (soru kimliği) ve sonra parametreleri gerektiren bir golf dili yazmalıyım. En iyi cevabı anlayacağı bir dilde seçer, uygular (herhangi bir parametreyi geçerek) ve sonucu döndürür ... Acaba kurallara uymuyor mu? :-)
Diş Fırçası

@toothbrush TI-BASIC'in savunmasında: tercümana, Pyth ve CJam'ın tek karakterli komutlarından daha adil değil ve TI-BASIC daha okunaklı.
lirtosiast 13:15

1
Doğru. Bu tür dillerden hoşlanmıyorum, çünkü hemen hemen her dilin çözümleri daha uzun sürüyor, ancak son zamanlarda CJB'yi VB6 ile yendim . : -]
Diş Fırçası

15

PARI / GP, 21 bayt

print(isprime(input))

Gülünç derecede büyük girdiler için çalışıyor, çünkü bu tür şeyler PARI / GP'nin yaptığı şey.


6
isprimeAPR-CL primallik kanıtı kullanıyor, bu yüzden girişler çok büyüdükçe biraz yavaşlıyor. ispseudoprime(input)100 basamaktan daha hızlı olacak olan AES BPSW muhtemel prime testini yapar. 35 yıl sonra hala bilinen herhangi bir karşı örnek yok. 2002'den önceki Pari'nin 2.1 ve önceki sürümleri, yanlış sonuçlar verebilecek farklı bir yöntem kullanıyor, ancak bunu kimse kullanmamalı.
DanaJ

15

TI-BASIC, 24 bayt

TI-Basic programlarının bir belirteç sistemi kullandığına dikkat edin, böylece sayım karakterleri programın gerçek bayt değerini döndürmez.

Thomas Kwa'nın cevabını oylayın , üstün.

:Prompt N
:2
:While N≠1 and fPart(N/Ans
:Ans+1
:End
:N=Ans

Numune:

N=?1009
                         1
N=?17
                         1
N=?1008
                         0
N=?16
                         0

Şimdi 0asal 1değilse veya öyleyse döner .


3
Karekök sadece programın doğru olması için ihtiyacınız olmayan bir optimizasyon değil mi?
Martin Ender

Neden ikiye bölmek zorundasın?
Geobits 11:15

Her zaman TI-BASIC cevaplarını seviyorum.
Grant Miller

15

Yığın Kedileri , 62 + 4 = 66 bayt

*(>:^]*(*>{<-!<:^>[:((-<)<(<!-)>>-_)_<<]>:]<]]}*<)]*(:)*=<*)>]

-lnKomut satırı bayrakları ile çalıştırılması gerekiyor (bu nedenle +4 bayt). 0Kompozit sayılar ve 1primerler için yazdırır .

Çevrimiçi deneyin!

Bunun önemsiz olmayan ilk Stack Cats programı olduğunu düşünüyorum.

açıklama

Hızlı bir Stack Cats tanıtımı:

  • Yığın Kedileri, geçerli bir yığına işaret eden bir bant başlığıyla, sonsuz bir yığın bantta çalışır. Her yığın başlangıçta sonsuz miktarda sıfır ile doldurulur. İfadelerimde bu sıfırları genellikle görmezden geleceğim, bu yüzden "yığının dibinde" derken sıfır olmayan en düşük değeri ve "yığın boş" dediğimde üzerinde yalnızca sıfır olduğunu kastediyorum.
  • Program başlamadan önce, -1ilk istifin üzerine a itilir ve ardından girişin tamamı buna itilir. Bu durumda, -nbayrak nedeniyle giriş, ondalık bir tamsayı olarak okunur.
  • Programın sonunda, mevcut yığın çıktı için kullanılır. -1Dipte bir varsa , yoksayılır. Yine, -nbayrak nedeniyle , yığından gelen değerler basitçe satır besleme ayrılmış ondalık tam sayılar olarak yazdırılır.
  • Stack Cats geri dönüşümlü bir program dilidir: her kod parçası geri alınabilir (Stack Cats açık bir geçmişi takip etmeden). Daha spesifik olarak, kodun herhangi bir parçasını tersine çevirmek için, sadece o ayna, örneğin <<(\-_)olur (_-/)>>. Bu tasarım hedefi, dilde ne tür operatörler ve kontrol akışı yapıları olduğu ve küresel bellek durumu üzerinde ne tür işlevler hesaplayabileceğiniz konusunda oldukça ciddi kısıtlamalar getirir.
  • Her şeyden önce, her Stack Cats programının kendi kendini simetrik olması gerekir. Yukarıdaki kaynak kod için böyle olmadığını fark edebilirsiniz. Bu nedir -lbayrak içindir: zımnen merkezi için ilk karakteri kullanılarak sola kodunu yansıtır. Dolayısıyla gerçek program:

    [<(*>=*(:)*[(>*{[[>[:<[>>_(_-<<(-!>)>(>-)):]<^:>!->}<*)*[^:<)*(>:^]*(*>{<-!<:^>[:((-<)<(<!-)>>-_)_<<]>:]<]]}*<)]*(:)*=<*)>]
    

Tüm kodla etkin bir şekilde programlama yapmak önemsiz ve sezgisel değildir ve henüz bir insanın nasıl yapabileceğini henüz çözemedi. Daha basit işler için bu tür bir programı zorla uyguladık, ancak buna yakın bir yere elle gidemezdik. Neyse ki, programın bir yarısını görmezden gelmenizi sağlayan temel bir kalıp bulduk. Bu kesinlikle yetersiz kalsa da, şu anda Stack Cats'te etkin bir şekilde programlamanın bilinen tek yolu.

Yani bu cevapta, söz konusu modelin şablonu şudur (nasıl yürütüldüğü konusunda bazı değişkenlikler vardır):

[<(...)*(...)>]

Program başladığında, yığın bandı şöyle görünür 4:

     4    
... -1 ...
     0
     ^

[Hamle sola yığının üst (ve birlikte teyp kafası) - bu "itme" diyoruz. Ve <bant başını rahatça hareket ettirir. Öyleyse ilk iki komuttan sonra, şu duruma sahibiz:

...   4 -1 ...
    0 0  0
    ^

Şimdi, (...)koşul olarak kolayca kullanılabilecek bir döngü var: döngü yalnızca geçerli yığının tepesi pozitif olduğunda girilir ve bırakılır. Şu anda sıfır olduğundan, programın ilk yarısının tamamını atlarız. Şimdi merkez komutu *. Bu basitçe XOR 1bu yığının en en az bit geçiş yapar ve bu durumda döner, yani 0bir içine 1:

... 1 4 -1 ...
    0 0  0
    ^

Şimdi bunun ayna görüntüsüyle karşılaşıyoruz (...). Bu kez yığınının üst pozitif ve biz yapmak kodunu girin. Parantez içinde neler olup bittiğine bakmadan önce, sonunda nasıl sarılacağımızı açıklamama izin verin: Bu bloğun sonunda, bant kafasının tekrar pozitif bir değerde olmasını sağlamak istiyoruz (böylece döngü sağa yığın çıkışı tutar ve yığın bu doğru,) tek bir yineleme sonra sona erer ve bir doğrusal koşullu olarak sadece kullanılan bu bir tutar -1. Eğer durum buysa, döngüyü terk >eder, çıktı değerine doğru hareket eder ve ]onu yukarı doğru iter, -1böylece çıktı için temiz bir yığına sahip oluruz.

Bu budur. Şimdi parantez içinde, bir önceki paragrafta anlatılanları ayarladıktan sonra (bazı itme ve bant kafa hareketleriyle kolayca yapılabilir) yaptığımızdan emin olarak, ilkelliği kontrol etmek istediğimiz her şeyi yapabiliriz. İlk önce Wilson teoremiyle problemi çözmeye çalıştım ancak 100 bayttan fazla bitti, çünkü kare faktörlü hesaplama aslında Stack Cats'de oldukça pahalı (en azından kısa bir yol bulamadım). Bu yüzden deneme bölümüne gittim ve bu gerçekten çok daha kolaylaştı. İlk lineer bit'e bakalım:

>:^]

Bu komutlardan ikisini zaten gördünüz. Ek olarak, :mevcut yığının ilk iki değerini değiştirir ve ^XOR, ikinci değeri üst değere değiştirir. Bu, :^boş bir yığındaki bir değeri çoğaltmak için ortak bir kalıp oluşturur (değerin üstüne bir sıfır çekeriz ve sonra sıfıra çeviririz 0 XOR x = x). Bundan sonra, bölüm kasetimiz şöyle görünür:

         4    
... 1 4 -1 ...
    0 0  0
         ^

Uyguladığım deneme bölümü algoritması girdi için çalışmıyor 1, bu durumda kodu atlamalıyız. Biz kolayca haritalayabilirsiniz 1için 0ve pozitif değerlere her şey *, işte biz bunu nasıl:

*(*...)

Yani, biz çevirmek olduğunu 1içine 0, biz gerçekten alırsanız kodun büyük bir kısmını atlamak 0, ama biz hemen geri içeri *geri bizim giriş değeri elde böylece. Parantezin sonunda pozitif bir değere sahip olduğumuzdan ve tekrar başlamadan emin olmaları gerektiğinden emin olmalıyız. Koşullu içinde bir yığını sağa çekip >ana deneme bölümü döngüsünü başlatırız:

{<-!<:^>[:((-<)<(<!-)>>-_)_<<]>:]<]]}

Parantezler (parantezlerin tersine) farklı bir döngü türü tanımlar: bu bir süre bitiminde döngü anlamına gelir, bu her zaman en az bir yineleme için çalıştığı anlamına gelir. Diğer fark, sonlandırma koşulu: Yığın Cat'e girerken mevcut yığının en üst değerini hatırlar ( 0bizim durumumuzda). Döngü daha sonra bu aynı değer tekrarlamanın sonunda tekrar görülene kadar çalışacaktır. Bu bizim için uygundur: her yinelemede bir sonraki potansiyel bölenin kalanını hesaplıyoruz ve döngüye başladığımız bu yığının üzerine taşıyoruz. Bir bölen bulduktan sonra, kalan 0ve döngü durur. Böylelikle başlayan bölenleri dener n-1ve sonra düşürürüz 1. Bunun anlamı: a) ulaştığımızda sona ereceğini biliyoruz.1en geç ve b) daha sonra denediğimiz son böleni inceleyerek sayının asal olup olmadığını belirleyebiliriz (eğer öyleyse 1asal, yoksa değil).

Hadi hadi bakalım. Başlangıçta kısa bir doğrusal bölüm var:

<-!<:^>[:

Şu anların çoğunun ne yaptığını biliyorsun. Yeni komutlar -ve !. Yığın Kediler'de artış veya azalma operatörleri yoktur. Bununla birlikte -(olumsuzlama, yani çarpma -1) ve !(bitsel DEĞİL, yani çarpma -1ve azaltma) vardır. Bunlar bir artım !-veya azalmayla birleştirilebilir -!. Bu yüzden n, üstündeki kopyasını azaltıyoruz -1, sonra nyığın üzerinde sola doğru başka bir kopya oluşturuyoruz , sonra da yeni deneme bölenini alıp altına koyuyoruz n. Böylece ilk tekrarda şunu anlıyoruz:

      4       
      3       
... 1 4 -1 ...
    0 0  0
      ^

Diğer yinelemelerde, bir 3sonraki test böleni ve benzeri ile değiştirilecektir (oysaki iki kopya nbu noktada her zaman aynı değerde olacaktır).

((-<)<(<!-)>>-_)

Bu modulo hesaplama. Döngüler pozitif değerler üzerinde sonlandırıldığı için, fikir pozitif bir değer elde edene kadar -ndeneme bölenini baştan başlamak ve tekrar tekrar kullanmaktır d. Bir kez yaptığımızda sonucu çıkarırız dve bu bize kalanı verir. Buradaki zor bit -n, yığının üstüne bir şey koymayıp ekleyen bir döngü başlatmamamızdır d: yığının tepesi negatifse döngü girilmez. Bunlar tersinir bir programlama dilinin sınırlamalarıdır.

Dolayısıyla bu sorunu aşmak niçin yığının tepesinden başlıyoruz , ancak yalnızca ilk yinelemede reddediyoruz. Yine, bu göründüğünden daha basit geliyor ...

(-<)

Yığının tepesi pozitif olduğunda (yani yalnızca ilk yinelemede), onu yok sayırız -. Ancak, tam olarak yapamayız (-)çünkü o zaman iki kez uygulanıncaya kadar döngüyü terk etmeyecektik -. Böylece bir hücreyi sola doğru hareket ettiriyoruz <çünkü orada pozitif bir değer olduğunu biliyoruz 1. Tamam, şimdi nilk yinelemeyi güvenilir bir şekilde ihmal ettik . Ancak yeni bir sorunumuz var: Teyp kafası şimdi ilk yinelemede diğerinden farklı bir konumda. Devam etmeden önce bunu pekiştirmemiz gerekiyor. Daha <sonra şerit kafasını sola hareket ettirir. İlk yinelemede durum:

        -4       
         3       
...   1  4 -1 ...
    0 0  0  0
    ^

Ve ikinci yinelemede (şimdiye bir dkere eklediğimizi unutmayın -n):

      -1       
       3       
... 1  4 -1 ...
    0  0  0
    ^

Bir sonraki koşullu bu yolları tekrar birleştirir:

(<!-)

İlk yinelemede, teyp kafası sıfıra işaret eder, bu yüzden bu tamamen atlanır. Diğer yinelemelerde, bant başı bir tane gösteriyor, bu yüzden bunu yapıyoruz, sola doğru hareket ediyoruz ve oradaki hücreyi arttırıyoruz. Hücrenin sıfırdan başladığını bildiğimiz için, her zaman pozitif olacaktır, böylece döngüyü terk edebiliriz. Bu, her zaman ana yığının solundaki iki yığının sonuna kadar kalmamızı ve şimdi geri hareket etmemizi sağlar >>. Sonra modulo döngüsünün sonunda yaparız -_. Sen zaten biliyorsun -. _XOR'nin ne ^olduğunu çıkarmaktır : yığının tepesi ave altındaki değer ise ile bdeğiştirilir . Biz ilk etkisiz yana olsa da, yerini ile suretle ekleyerek,ab-aa-_ab+ad çalışan toplamımızın içine.

Döngü sona erdikten sonra (bir pozitif değere ulaştık), teyp şöyle görünür:

        2       
        3       
... 1 1 4 -1 ...
    0 0 0  0
        ^

En soldaki değer herhangi bir pozitif sayı olabilir. Aslında, eksi bir yineleme sayısı. Şimdi başka bir kısa doğrusal bit var:

_<<]>:]<]]

Daha önce de söylediğim gibi d, gerçek kalanı ( 3-2 = 1 = 4 % 3) elde etmek için sonucu çıkarmamız gerekir , bu yüzden sadece bir _kez daha yaparız . Daha sonra, solda arttırdığımız yığını temizlememiz gerekiyor: bir sonraki böleni denediğimizde, ilk yinelemenin çalışması için tekrar sıfır olması gerekiyor. Böylece oraya taşınıyoruz ve bu pozitif değeri diğer yardımcı istifin üzerine itiyoruz <<]ve sonra diğer istif aracımızla birlikte diğer istif aracımıza geçiyoruz >. Biz yukarı çekin dile :ve üzerine geri itin -1ile ]ve sonra biz bizim koşullu yığının üzerine kalan taşımak <]]. Bu, deneme bölümü döngüsünün sonu: bu, sıfır kalanını alana kadar devam eder, bu durumda sola yığınnen büyük bölen (hariç n).

Döngü sona erdikten sonra, *<giriş ile 1tekrar yolları birleştirmeden hemen önce var . *Basitçe içine sıfır döner 1biz biraz da gerekir, ve sonra biz bölen taşımak <(biz girişi için aynı yığın üzerinde yapmayacak şekilde 1).

Bu noktada, üç farklı girdi türünün karşılaştırılmasına yardımcı olur. İlk olarak, n = 1bu deneme bölümü işlerinden hiçbirini yapmadığımız özel durum :

         0    
... 1 1 -1 ...
    0 0  0
         ^

O zaman, önceki örneğimizde n = 4bileşik sayı:

    2           
    1    2 1    
... 1 4 -1 1 ...
    0 0  0 0
         ^

Ve son olarak n = 3, bir asal sayı:

    3           
    1    1 1    
... 1 3 -1 1 ...
    0 0  0 0
         ^

Yani asal sayılar için, 1bu yığında bir tane var ve birleşik sayılar için, ya 0daha büyük olan bir ya da artı sayımız var 2. Bu durumu 0ya 1da aşağıdaki son kod parçasına ihtiyacımız var:

]*(:)*=<*

]sadece bu değeri sağa iter. Daha sonra *koşullu durumu büyük ölçüde basitleştirmek için kullanılır: en az anlamlı birayı değiştirerek, 1(prime) 0, 0(kompozit) pozitif değere çeviririz 1ve diğer tüm pozitif değerler hala pozitif kalır. Şimdi sadece 0pozitif ile pozitif arasında bir ayrım yapmamız gerekiyor . Başka kullandığımız yer orası (:). Yığının üstü ise 0(ve girdi bir asal ise), bu basitçe atlanır. Ancak, yığının tepesi pozitifse (ve girdi birleşik sayıysa) bu 1, onu şu şekilde değiştirir 0;1Asal sayılar için - sadece iki farklı değer. Tabii ki, bizim çıktı almak istediklerimizin tam tersi, ancak bu kolaylıkla başka biriyle sabitlenebilir *.

Şimdi geriye sadece tüm çevreleyen çerçeve tarafından beklenen yığınlar desenini restore etmektir: sağa yığının üstüne, olumlu değerine teyp kafası neden ve tek bir -1yığın sağda olduğunu . Bunun =<*için var. =iki bitişik yığının üstünü değiştirerek -1sonucun sağına hareket eder , örneğin 4tekrar giriş yapmak için :

    2     0       
    1     3       
... 1 4   1 -1 ...
    0 0 0 0  0
          ^

Sonra sola hareket ediyoruz <ve bu sıfırı olana çeviriyoruz *. Ve bu o.

Programın nasıl çalıştığını daha derine kazmak istiyorsanız, hata ayıklama seçeneklerinden yararlanabilirsiniz. -dBayrağı ekleyin ve "mevcut hafıza durumunu görmek istediğiniz yere yazın, örneğin bu şekilde yapın veya tüm programı tam olarak izlemek için -Dbayrağı kullanın . Alternatif olarak, adım adım hata ayıklayıcılı bir Stack Cats yorumlayıcısı içeren Timwi'nin Ezoterik Kullanımı'nı kullanabilirsiniz .


3
>:^]resmi Stack Cats logosu olmalıdır
Alex A.

14

Haskell, 54 bayt

import Data.Numbers.Primes
main=readLn>>=print.isPrime

Açıklayacak çok bir şey yok.


1
Wilson'ın teoremini kullanarak, aynı puanlama dış kütüphaneler olmadan (verimsiz olmasına rağmen) elde edilebilir:main=do n<-readLn;print$n>1&&mod(product[1..n-1]+1)n<1
Lynn

9
Daha kısa bile yapabiliriz: main=do n<-readLn;print$mod(product[1..n-1]^2)n>049 bayttır.
Lynn

4
@ Mauris: Güzel. Lütfen ayrı bir cevap olarak gönderin.
nimi

14

Ruby, 15 + 8 = 23 bayt

p$_.to_i.prime?

Örnek çalışma:

bash-4.3$ ruby -rprime -ne 'p$_.to_i.prime?' <<< 2015
false

Heheh, Ruby'de bir yerde bir yerleşik olacağını biliyordum, ama onu aramak için can atmıyordum, bu yüzden C + 1'de cevapladım.
Seviye Nehri St

@ steveverrill, bunu biliyordum çünkü Project Euler için büyük bir yardımdı.
Manatwork

14

JavaScript, 39 36 bayt

ETHproductions sayesinde 3 bayt kurtardı:

for(i=n=prompt();n%--i;);alert(1==i)

Asal bir değer için doğru, aksi takdirde false gösterir.

İçin döngü her dizi test i gelen n-1 kadar ı bir bölenin. Bulunan ilk bölen 1 ise bir asal sayıdır.


Önceki çözüm (39 bayt):

for(i=n=prompt();n%--i&&i;);alert(1==i)

Gereksiz bir test nasıl kaldı:

for(i=2,n=prompt();n%i>0&&i*i<n;i++);alert(n%i>0) //49: Simple implementation: loop from 2 to sqrt(n) to test the modulo.
for(i=2,n=prompt();n%i>0&&i<n;i++);alert(n==i)    //46: Replace i*i<n by i<n (loop from 2 to n) and replace n%i>0 by n==i
for(i=2,n=prompt();n%i&&i<n;i++);alert(n==i)      //44: Replace n%i>0 by n%i
for(i=2,n=prompt();n%i&&i++<n;);alert(n==i)       //43: Shorten loop increment
for(i=n=prompt();n%--i&&i>0;);alert(1==i)         //41: Loop from n to 1. Better variable initialization.
for(i=n=prompt();n%--i&&i;);alert(1==i)           //39: \o/ Replace i>0 by i

En iyi JavaScript cevabı zaten 40 bayt olduğu için sadece 39 byte'lık bir çözüm yolladım.


2
Programlama Bulmacaları ve Kod Golf'üne Hoş Geldiniz!
Dennis,

2
Mükemmel cevap! &&iAslında bu programda bir şey yapmaz, bu yüzden kaldırabilirsiniz.
ETHProductions,

Asal olmak n>1istemiyorsanız, yine de son koşula eklemelisiniz 1.
Titus

1
@Titus Giriş ise 1for döngüsü bir n%--ikere yapar: 1%0geri döner NaNve döngüyü durdurur. Ne zaman alertdenir izaten eşittir 0böylece 1==igetiri false.
Hedi

2
i <2 (ve bazı metinler)
Scheintod

13

Salyangoz, 122

Giriş unary olarak verilmelidir. Rakamlar yeni satırlar dışında herhangi bir karakter karışımı olabilir.

^
..~|!(.2+~).!~!{{t.l=.r=.}+!{t.!.!~!{{r!~u~`+(d!~!.r~)+d~,.r.=.(l!~u~)+(d!~l~)+d~,.l.},l=(.!.)(r!~u~)+(d!~!.r~)+d~,.r.!.

Bu 2B desen eşleştirme dilinde, program durumu yalnızca geçerli ızgara konumundan, eşleşen hücre kümesinden ve desen kodundaki konumdan oluşur. Aynı zamanda eşleşen bir meydanda seyahat etmek de yasa dışı. Zor, ancak bilgi depolamak ve almak mümkün. Eşleşen bir hücreye gitmeye karşı kısıtlama , tamamlandıktan sonra ızgarayı değiştirilmemiş bırakan geriye doğru izleme, teleporting ( t) ve iddialar ( =, !) ile aşılabilir .

25'in çarpanlara ayrılması

Tek bir bileşik sayı için çarpanlara ayırma, birbirine bitişik olmayan bazı hücre kümelerini işaretleyerek başlar (diyagramda mavi). Daha sonra, her sarı hücreden, program, bitişik mavi olanın her iki tarafında, iki taraf arasında ileri geri gidip gelmek üzere eşit sayıda mavi olmayan hücre olduğunu doğrular. Diyagram, bu deseni kontrol edilmesi gereken dört sarı hücreden biri için gösterir.

Açıklamalı kod:

^                         Match only at the first character
..~ |                     Special case to return true for n=2
!(.2 + ~)                 Fail for even numbers
. !~                      Match 1st character and fail for n=1
!{                        If the bracketed pattern matches, it's composite.
  (t. l=. r=. =(.,~) )+   Teleport to 1 or more chars and match them (blue in graphic)
                          Only teleport to ones that have an unmatched char on each side.
                          The =(.,~) is removed in the golfed code. It forces the
                          teleports to proceed from left to right, reducing the
                          time from factorial to exponential.
  !{                      If bracketed pattern matches, factorization has failed.
    t . !. !~             Teleport to a square to the left of a blue square (yellow in diagram)
    !{                    Bracketed pattern verifies equal number of spaces to
                          the left or right of a blue square.
      {              
        (r!~ u~)+         Up...
        (d!~!. r~)+       Right...
        d~,               Down...
        . r . =.          Move 1 to the right, and check that we are not on the edge;
                          otherwise d~, can fall off next iteration and create and infinite loop
        (l!~ u~)+         Up...
        (d!~ l~)+         Left...
        d ~,              Down...
        . l .             Left 1
      } ,                 Repeat 0 or more times
      l  =(. !.)          Check for exactly 1 unused char to the left
      (r!~ u~)+           Up...
      (d!~!. r~)+         Right...
      d ~,                Down...
      . r . !.
    }
  }
}

13

C, 67 bayt

i,n;main(p){for(scanf("%d",&i),n=i;--i;p=p*i*i%n);putchar(48+p%n);}

Aksi takdirde , basar !1( Peter Taylor'ın tanımına göre bir falsey değeri ) .0(n-1)!^2 == 0 (mod n)1

EDIT : Sohbet sırasında biraz tartışma yaptıktan sonra puts("!1"+p%n)biraz aldatılmış gözüküyor, bu yüzden değiştirdim. Sonuç bir bayt daha uzundur.

EDIT : Büyük girişler için düzeltildi.

Daha kısa çözümler

56 bayt : pawel.boczarski tarafından yapılan yorumlarda önerildiği gibi, komut satırındaki argümanların sayısını okuyarak unary girdi alabilirim:

p=1,n;main(i){for(n=--i;--i;p=p*i*i%n);putchar(48+p%n);}

gibi programı çağırmak

$ ./a.out 1 1 1 1 1
1                        <-- as 5 is prime

51 bayt : "Çıkış" a dönüş kodları aracılığıyla izin verirseniz:

p=1,n;main(i){for(n=--i;--i;p=p*i*i%n);return p%n;}

Çözümüm, yayınladığım çözümde olduğu gibi, tek başına temsil (komut satırı argümanlarının sayısı) kullanılarak daha kısa yapılabilir. Scanf aramalarında bazı baytları tıraş edebilirsiniz.
pawel.boczarski 12:15

puts("!1"+p%n)Değerler a+biçin nasıl yapabildin char*?
Outgolfer Erik,

Dize "!1"adrese başlarsa a, o zaman a+1dizeyi bulacaksınız "1".
Lynn,

Ah @Lynn, ben (evet, daha iyi bırakmak Ulama için olduğunu düşündüm o kadar strcat(const char*,const char*).)
Erik Outgolfer

Değiştirebilir p=p*i*i%nmisinizp*=i*i%n
Albert Renshaw

12

Python 3, 59 bayt

Şimdi input()komut satırı argümanları yerine kullanır . @Beta Decay sayesinde

n=int(input())
print([i for i in range(1,n)if n%i==0]==[1])

Kullanarak girdi almak input()çok daha kısa olurdu
Beta Decay

Teşekkürler, zaten input () kullanarak yazdım, ancak cevabımı yenilemeyi unuttum. Tekrar teşekkürler!
uno20001 11:15

4
52 byte: n=m=int(input()),print(all(n%m for m in range(2,n)))
John Lyon

1
Ciddi misin. Bir topal ikinci dereceden hızlanma için 25 fazla karakter harcamak? Burada baytlardan nefret ediyoruz . Her saatimizi, dakikamızı ve hayatımızın saniyesini on dokuzuncu bayttan kurtulmak için harcıyoruz. (Şaka yapıyorum. Ama programın uzunluğunu artıran zaman optimizasyonları yapmıyoruz.)
CalculatorFeline

2
Yerine n%i<1kullanın.
Outgolfer Erik, 17:16

12

APL, 40 13 bayt

2=+/0=x|⍨⍳x←⎕

R cevabım ile aynı algoritma ile deneme bölümü . xSTDIN ( ) ' den girişe atar ve kalanı x1'den her tam sayıya bölerek alırız x. Her kalan 0 ile karşılaştırılır, bu bize hangi tam sayıların bölündüğünü gösteren sıfırlardan oluşan bir vektör verir x. Bu, +/bölenlerin sayısını almak için kullanılarak toplanır . Bu sayı tam 2 ise, bu sadece bölenlerin 1 olduğu xve dolayısıyla xasal olduğu anlamına gelir .


12

Python 2, 44

P=n=1
exec"P*=n*n;n+=1;"*~-input()
print P%n

Gibi SP3000 Python cevap ama önler değişkeni sayarak girdi depolamak nkadar 1girdi değerine.


12

C ++ şablonunda metaprogramlama. 166 131 119 bayt.

Kod, sabit bir asal ise derlenir ve bileşik veya 1 ise derlenmez.

template<int a,int b=a>struct t{enum{x=t<a,~-b>::x+!(a%b)};};
template<int b>struct t<b,0>{enum{x};};
int _[t<1>::x==2];

(sonuncusu hariç tüm yeni satırlar "gerçek" sürümde elenir).

"Derleme başarısızlığının" metaprogramlama dili için bir falsey dönüş değeri olduğunu düşünüyorum. Bağlanmadığına dikkat edin (bu nedenle, onu beslediğiniz takdirde, bağlama hataları alırsınız) tam bir C ++ programı olarak.

Test edilecek değer, son "satır" daki tamsayıdır.

canlı örnek .

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.