Zainspirowany http://xkcd.com/710/ tutaj jest kod do tego golfa.
Wyzwanie
Mając dodatnią liczbę całkowitą większą niż 0, wydrukuj sekwencję gradobicia dla tej liczby.
Sekwencja gradobicia
Więcej szczegółów można znaleźć w Wikipedii .
- Jeśli liczba jest parzysta, podziel ją przez dwa.
- Jeśli liczba jest nieparzysta, potrój ją i dodaj jeden.
Powtarzaj to z liczbą wygenerowaną, aż osiągnie 1. (jeśli będzie kontynuowana po 1, przejdzie w nieskończoną pętlę 1 -> 4 -> 2 -> 1...
)
Czasami najlepszym sposobem wyjaśnienia jest kod, więc oto fragment z Wikipedii
function collatz(n)
show n
if n > 1
if n is odd
call collatz(3n + 1)
else
call collatz(n / 2)
Ten kod działa, ale dodaję dodatkowe wyzwanie. Program nie może być podatny na przepełnienia stosu . Musi więc albo używać iteracji, albo rekurencji ogonowej.
Ponadto punkty bonusowe za to, czy potrafi obliczać duże liczby, a język nie ma jeszcze tego zaimplementowanego. (lub jeśli ponownie zaimplementujesz obsługę dużych liczb za pomocą liczb całkowitych o stałej długości)
Przypadek testowy
Number: 21
Results: 21 -> 64 -> 32 -> 16 -> 8 -> 4 -> 2 -> 1
Number: 3
Results: 3 -> 10 -> 5 -> 16 -> 8 -> 4 -> 2 -> 1
Ponadto kod golfowy musi zawierać pełne dane wejściowe i wyjściowe użytkownika.
Odpowiedzi:
x86, 1337 znaków
źródło
int 23h
.Befunge
źródło
LOLCODE: 406 CHARAKTERZ
TESTD UNDR JUSTIN J. MEZA'S INTERPRETR . KTHXBYE!
źródło
Python -
95645146 charOczywiście nie powoduje przepełnienia stosu.
źródło
input
nie obsługuje plikueval
.n=input()*2
Perl
Postanowiłem być trochę antykonkurencyjnym i pokazać, jak normalnie zakodowałbyś taki problem w Perlu.
Na końcu znajduje się również 46 (łącznie) wpis do code-golfa.
Te pierwsze trzy przykłady zaczynają się od tego nagłówka.
Prosta wersja rekurencyjna
Prosta wersja iteracyjna
Zoptymalizowana wersja iteracyjna
Teraz pokażę, jak można zrobić ten ostatni przykład z wersją Perla wcześniejszą niż 5.10.0
Reper
Po pierwsze, IO zawsze będzie wolną częścią. Więc jeśli faktycznie przetestowałeś je w stanie, w jakim są, powinieneś uzyskać mniej więcej taką samą prędkość z każdego z nich.
Aby to przetestować, otworzyłem uchwyt pliku do
/dev/null
($null
) i edytowałem wszystkie,say $n
aby zamiast tego czytaćsay {$null} $n
. Ma to na celu zmniejszenie zależności od IO.Po uruchomieniu go 10 razy, oto reprezentatywne przykładowe wyjście:
Na koniec prawdziwy wpis dotyczący golfa w kodowaniu:
Łącznie 46 znaków
Jeśli nie musisz drukować wartości początkowej, możesz usunąć 5 dodatkowych znaków.
41 znaków łącznie
31 znaków dla rzeczywistej części kodu, ale kod nie będzie działał bez
-n
przełącznika. Więc uwzględniam cały przykład w mojej liczbie.źródło
$i + 1
jest zawsze dodatek (odpowiedź na wpis na blogu). UżywanieSub::Call::Recur
jest również optymalizacją. W przeciwnym razie użyłbym@_=$n;goto &Collatz
. (Jest 10-20% wolniej, jeśli zmieniszstate @next
namy @next
Haskell, 62 znaki
637683,86,97,137Dane wejściowe użytkownika, wydrukowane dane wyjściowe, używają stałej pamięci i stosu, działają z dowolnie dużymi liczbami całkowitymi.
Przykładowy przebieg tego kodu z 80-cyfrową liczbą wszystkich „jedynek” (!) Jako danych wejściowych jest całkiem fajny.
Oryginalna, tylko funkcjonalna wersja:
Haskell 51 znaków
Kto @ & ^ # potrzebuje warunków warunkowych?
(edit: byłem "sprytny" i użyłem poprawki. Bez tego kod spadł do 54 znaków. edit2: spadł do 51 przez wyodrębnienie
f()
)źródło
c 1=[1];c n=n:(c$div(n
mod2*(5*n+2)+n)2)
- 41 znaków, wykorzystuje to fakt, że jest to k * (3n + 1) + (1-k) * n / 2, gdzie k = n mod 2Golfscript: 20 znaków
Jest to równoważne z
źródło
21
z~
spowoduje, że program użyć numeru z stdin(eval):1:in
initialize ": metody niezdefiniowanejleftparen' for nil:NilClass (NoMethodError)
przy wymianie21
z~
.echo 21 | ruby golfscript.rb collatz.gs
pne 41 znaków
Myślę, że tego rodzaju problemy
bc
zostały wymyślone dla:Test:
Właściwy kod:
bc
obsługuje liczby doINT_MAX
cyfrEdit: artykuł Wikipedia wspomina to hipoteza została sprawdzona dla wszystkich wartości do 20x2 58 (ok. 5.76e18 ). Ten program:
testy 2 20 000 +1 (ok. 3,98e6 020 ) w 68 sekund, 144 404 cykli.
źródło
cat /dev/urandom | tr -dc '0-9' | head -c 10000 | bc collatz-conjecture.bc
bc
Perl: 31 znaków
Edytowano, aby usunąć 2 niepotrzebne spacje.
Edytowano, aby usunąć 1 niepotrzebną spację.
źródło
MS Excel, 35 znaków
Zaczerpnięte prosto z Wikipedii :
Wystarczyło skopiować / wkleić formułę 111 razy, aby uzyskać wynik dla liczby początkowej 1000;)
źródło
C: 64 znaki
Z obsługą dużych liczb całkowitych: 431 (konieczne) znaków
Uwaga : nie usuwaj
#include <stdlib.h>
bez przynajmniej prototypowania malloc / realloc, ponieważ nie będzie to bezpieczne na platformach 64-bitowych (64-bitowe void * zostanie przekonwertowane na 32-bitowe int).Ten nie był jeszcze intensywnie testowany. Przydałoby się też trochę tłuszczu.
Poprzednie wersje:
(usunięto 12 znaków, ponieważ nikt nie postępuje zgodnie z formatem wyjściowym ...: |)
źródło
Kolejna wersja asemblera. Ten nie jest ograniczony do liczb 32-bitowych, może obsługiwać liczby do 10 65534, chociaż format „.com” używany przez MS-DOS jest ograniczony do liczb 80-cyfrowych. Napisany dla asemblera A86 i wymaga do działania boxu Win-XP DOS. Składa się do 180 bajtów:
źródło
dc - 24 znaki
2528dc
jest dobrym narzędziem dla tej sekwencji:Również 24 znaki według wzoru z wpisu Golfscript :
57 znaków do spełnienia specyfikacji:
źródło
Schemat: 72
Używa rekurencji, ale wywołania są rekurencyjne, więc myślę, że zostaną zoptymalizowane pod kątem iteracji. W niektórych szybkich testach nie udało mi się znaleźć liczby, dla której i tak stos się przepełnia. Na przykład:
(C 9876543219999999999000011234567898888777766665555444433332222 7777777777777777777777777777777798797657657651234143375987342987 5398709812374982529830983743297432985230985739287023987532098579 058095873098753098370938753987)
... działa dobrze. [to wszystko jeden numer - właśnie złamałem go, żeby zmieścił się na ekranie.]
źródło
Mathematica 45
50znakiźródło
OddQ[#]
zOddQ@#
zaoszczędzić 1 char.c[n_]:=NestWhileList[If[OddQ@#,3#+1,#/2]&,n,#>1&]
Ruby, 50 znaków, brak przepełnienia stosu
Zasadniczo bezpośrednie ripowanie rozwiązania Python firmy Makapuf :
Ruby, 45 znaków, przepełni się
Zasadniczo bezpośrednie ripowanie kodu podanego w pytaniu:
źródło
n.odd??
zdefiniowany. Jest to również podatne na przepełnienie stosu z dużymi liczbami.p n=[n/2,n*3+1][n%2]
źródło
Python 45 Char
Zgoliłem węgiel z odpowiedzi makapufa.
źródło
TI-BASIC
Nie najkrótsze, ale nowatorskie podejście. Z pewnością znacznie zwolni przy dużych sekwencjach, ale nie powinno się przepełniać.
źródło
Haskell: 50
źródło
c 1=[1];c n=n:(c$[n
Div2,3*n+1]!!(n
Mod2))
, 44 znakinie najkrótsze, ale eleganckie rozwiązanie garderoby
źródło
C #: 216 znaków
w długiej formie:
Nowa wersja, akceptuje jeden numer jako dane wejściowe podane w wierszu poleceń, bez sprawdzania poprawności danych wejściowych.
173154 znaków.w długiej formie:
Jestem w stanie ogolić kilka postaci, wyrywając pomysł z tej odpowiedzi, aby użyć pętli for zamiast chwili. 150 znaków.
źródło
Ruby, 43 znaki
bignum obsługiwane, z podatnością na przepełnienie stosu:
... i 50 znaków, obsługiwane bignum, bez przepełnienia stosu:
Uznanie dla Jordanii. Nie wiedziałem o „p” jako zamienniku puts.
źródło
nroff 1
Biegnij z
nroff -U hail.g
1. wersja groffa
źródło
groff -U hail.g
a otrzymasz PostScript! :-)Scala + Scalaz
I w akcji:
Scala 2.8
Obejmuje to również końcowe 1.
Z następującym niejawnym
można to skrócić do
Edycja - 58 znaków (w tym wejście i wyjście, ale bez numeru początkowego)
Można zmniejszyć o 2, jeśli nie potrzebujesz nowych linii ...
źródło
F #, 90 znaków
Lub jeśli nie używasz F # interaktywnego do wyświetlania wyniku, 102 znaki:
źródło
Common Lisp, 141 znaków:
Testowe uruchomienie:
źródło
Program frm Jerry Coffin ma przepełnienie liczb całkowitych, spróbuj tego:
testowane z
Liczba poniżej 100 milionów z najdłuższym łącznym czasem zatrzymania to 63728127, z 949 krokami.
Liczba poniżej 1 miliarda z najdłuższym całkowitym czasem zatrzymania to 670 617 279, z 986 krokami.
źródło
unsigned long long
.ruby, 43 lata, prawdopodobnie spełniający wymagania we / wy
Biegnij z
ruby -n hail
źródło
C #: 659 znaków z obsługą BigInteger
Ungolfed
źródło