Pomóż Notwen symulować grawitację!


9

Notwen chce badać kinematykę ciał wyrzucanych z dużych wysokości w jednolite pole grawitacyjne, ale niestety nie ma technicznej możliwości wejścia na wystarczająco wysokie miejsca i obserwowania obiektów podczas upadku. Ale kto nie chce widzieć postępu w nauce, więc ... Pomóżmy Notwen zbudować symulator grawitacji!

Tło fizyczne

Obiekt spadł z wysokości h( bez prędkości początkowej ) w jednolitym polu grawitacyjnym, pomijając efekty atmosferyczne, takie jak przeciąg lub wiatr, zwiększa prędkość i przyspiesza z czasem w kierunku ziemi. To „tempo zmian” prędkości w jednostce czasu nazywa się przyspieszeniem grawitacyjnym . W pobliżu powierzchni Ziemi jest w przybliżeniu równag9.8ms2, ale do celów tego wyzwania wykorzystamy tę wartość 10ms2, co oznacza, że ​​w ciągu jednej sekundy obiekt zwiększa swoją prędkość o około 10ms. Zastanów się nad wysokościąh, która jest wielokrotnością 100m i wyobraź sobie, że dzielisz tę wysokość na równe przedziały 100metrów długości. Notwen chce zmierzyć, ile czasu zajmuje upuszczenie obiektu przez każdy z tych przedziałów, więc to też zamierzamy obliczyć. Współczesna kinematyka - pomijanie szczegółów technicznych - mówi nam, że:

Δhk=vktk+12gtk2
gdzie ΔhkΔh=100m dla wszystkich wartości k w naszym przypadku, vk to prędkość początkowa na początku naszego kth interwał i tk jest czasem trwania kth przedział czasu (w celach informacyjnych indeksowanie rozpoczyna się od 0 z v0=0). My też to wiemyvk ma następujące wyrażenie:
vk=2g(Δh0+Δh1++Δhk1)=2gkΔh
Otrzymujemy liczbowo vk=2000kms i podłączenie do pierwszego równania i rozwiązywanie tk daje
(*)tk=25(k+1k)s
Zatem obiekt podróżuje pierwszy przedział (k=0) w 4.4721s, drugi przedział (k=1) w 1.8524si tak dalej ( wklejanie z większą liczbą wartości).

Wyzwanie

Dane wejściowe: wysokośćh z którego obiekt jest wyrzucany jako: dodatnia liczba całkowita wielokrotność 100, h lub liczba interwałówN=h100 (więc albo 700 lub 7 oznaczałoby to h=700m) - który zależy od Ciebie.

Wyjście: animacja artystyczna ASCII spadającego obiektu spadającego z wysokościh (szczegóły poniżej).

Struktura ramki wyjściowej musi być następująca:

  • Nznaki nowej linii poprzedzające „tło”, reprezentowane przez co najmniej jeden znak spacji (np @.). Co najmniej jedna z postaci ziemi musi leżeć na pionie, na który spadnie przedmiot.
  • Inny znak niebędący spacją reprezentujący obiekt (np. X), Inny niż ten, który wybrałeś dla podłoża.
  • Opcjonalnie znak na początku każdej linii reprezentujący oś pionową lub wykonaną ścianęNlinie. Każda ilość wiodących i końcowych spacji jest w porządku, o ile są one spójne między ramkami, a także dowolna ilość odstępów między ścianą a obiektem. Przykłady prawidłowych ramek obejmują 1 (dlah=700m lub N=7):
    | X                                       >
    |                             @           >   A
    |                                         >
    |        or            or           or    > 
    |               O                         >
    |                                         >
    |                                         >
    @@@             ^           -----            &&&
    

Obiekt musi zaczynać się w pierwszej linii pierwszej klatki, a następnie po t04.47sdane wyjściowe powinny zostać opróżnione, a program powinien wyświetlać obiekt w tym samym pionie, ale w następnym wierszu w drugiej ramce; następnie pot11.85swynik powinien zostać ponownie wyczyszczony, a program powinien wyświetlać obiekt na tej samej pionie, ale w następnym wierszu w trzeciej ramce i tak dalej, aż obiekt osiągnie linię tuż nad ziemią. Przykład:

Przykład animacji

Zasady

  • Wyjściem powinien być tekst napisany na interaktywnej (spłukiwalnej) konsoli, GIF, osobny plik dla każdej klatki lub inna rozsądna technika wydruku.
  • Każda ramka powinna całkowicie zastąpić ostatnią ramkę i znajdować się w tym samym miejscu.
  • Można założyć, że czas wymagany przez kompilator / tłumacz na wydrukowanie tekstu jest nieistotny, a minimalna dozwolona precyzja obliczania pierwiastków kwadratowych wynosi 2 miejsca po przecinku.
  • Możesz przyjmować dane wejściowe i dostarczać dane wyjściowe dowolną standardową metodą , zwracając uwagę, że te luki są domyślnie zabronione. To jest, więc spróbuj wykonać zadanie w najmniej bajtach, którymi możesz zarządzać w wybranym języku .

1: Nie jestem pewien, co stanowi prawidłową ramkę, ponieważ chcę pozwolić na to, co najbardziej odpowiada twojemu rozwiązaniu i nie próbuję dodawać zbędnych elementów do wyzwania. Jeśli coś jest niejasne, zapytaj w komentarzach.

Odpowiedzi:


3

JavaScript (ES7) + CSS + HTML, 340 bajtów

f=n=>{o.style.height=n+'em';x.style.animationDuration=(n*20)**.5+'s';o.appendChild(x,x.remove())}
pre{position:relative;border:1px solid;height:5em;overflow:hidden}span{position:absolute;top:0;animation:x 10s cubic-bezier(0.33,0,0.67,0.33)both}@keyframes x{to{top:100%}}
<input type=number value=5 oninput=f(this.value)><pre id=o><span id=x>X

Jeśli moje sumy są prawidłowe, czas trwania animacji to 20N. a następnie sześcienny bezier CSS zajmie się resztą.


2

Węgiel drzewny , 28 bajtów

Nθ↓θ⁴Fθ«J²ιPXR⌊×φ×₂²⁰⁻₂⊕ι₂ι 

Wypróbuj online! Link jest do pełnej wersji kodu. Uwaga: końcowe miejsce. Możesz obserwować opóźnienie na TIO, ale nie możesz oglądać animacji, więc musisz to sobie wyobrazić z wyjścia. Pobiera Njako dane wejściowe. Wyjaśnienie:

Nθ

Wejście N.

↓θ⁴

Wydrukuj ścianę i ziemię, aby kształt wydruku był spójny.

Fθ«

Pętla w każdym przedziale.

J²ιPX

Umieść Xna odpowiedniej wysokości.

R⌊×φ×₂²⁰⁻₂⊕ι₂ι

Wydrukuj bieżącą zawartość obszaru roboczego i poczekaj odpowiedni czas (skrócony do najbliższej milisekundy).

 

Zastąp Xspacją.


2

Perl 6 , 81 bajtów

{say "\e[s{"\n"x$_}-";map {say "\e[u{" \n"x 4.9e-6*$_²}o";sleep .01},^452*.sqrt}

„Wypróbuj online!”, Ale TIO nie obsługuje animacji.

Wyjaśnienie

Wybrałem nieco inne podejście (i myślę, że jest na lepsze, choć nie wiem na pewno). Zamiast przespać czasy podane przez wzór w PO, rysuję odpowiednią sytuację „co 10 ms” (± błędy wywołane przezsleep ).

Oznacza to, że jest 100 klatek na sekundę, więc jeśli oznaczymy numer klatki przez k, to musi być t=k/100. A ponieważ dzielimy odległość pionową na bloki 100 metrów, możemy zapisać wysokość jakoh=100n, gdzie nto liczba bloków (podana jako dane wejściowe). Wysokość podróżowała w czasiet jest dany przez h=solt2)/2), więc liczba przejechanych bloków wynosi

n=110012)solt2)=12)sol×10-6k2)4,905×10-6k2).
Możemy to odwrócić, aby uzyskać całkowitą liczbę klatek potrzebnych do renderowania:
k=n4,905×10-6452×n.

To wystarcza do napisania funkcji. Do wyrenderowania potrzebny jest jeden argument, liczba bloków, tjn. Po pierwsze say "\e[s{"\n"x$_}-". To drukuje sekwencję ucieczki ANSI o nazwie Save Cursor , a następnie drukujennowe linie, a następnie drukuje myślnik (podłoże) i nową linię. (Wykorzystuje to fajną funkcję podwójnych cudzysłowów w Perlu 6: możesz wstawić wynik dowolnego kodu bezpośrednio do ciągu, pisząc ten kod w nawiasach klamrowych.)

Następnie tworzymy sekwencję od 0 do 452n(automatycznie obcinany do liczby całkowitej) za pomocą ^452*.sqrti odwzorowujemy go. W każdej iteracji drukujemy sekwencję Unsave Cursor ANSI (która ustawia kursor w pozycji, w której był ostatnio zapisywany), piszemy4.9×10-6k2)ciągi „spacja + nowa linia” (ponownie automatycznie obcinane) i na koniec osymbol oznaczający obiekt. Następnie śpimy przez 10 ms, spłukujemy i powtarzamy.

Ze względu na automatyczne obcinanie, po prostu robi to właściwe i przesuwa „o” dopiero po każdych pełnych 100 m upadku.

wynikowa animacja


1

Haskell, 145 bajtów

import Control.Concurrent
a!b=[a..b]>>"\n"
f h=mapM(\k->putStr("\27[2J"++1!k++'O':k!h++"-")>>threadDelay(round$4472135*(sqrt(k+1)-sqrt k)))[1..h]

Musi być uruchomiony w terminalu ANSI. Dane wejściowe to liczba interwałów.

threadDelayParametr jest w nanosekundach, więc literał 4472135jest krótszy niż 2*sqrt 5*10^6. Niestety 46**4 = 4477456nie mieści się w wymaganej precyzji.


1

Python 2 , 117 120 123 bajtów

-3 bajty Dzięki „Don't be a x-triple dot” i „Jonathan Frech”

import time
h=input()
for k in range(h):print'\33[2J'+'\n'*k+'O'+'\n'*(h-k)+'^';time.sleep(2*5**.5*((k+1)**.5-k**.5))

Wypróbuj online!

wprowadź opis zdjęcia tutaj


1
+1 ode mnie, dobre rozwiązanie! Czy użycie rzeczywistego niedrukowalnego znaku nie zaoszczędziłoby kilku bajtów chr(27)?
Pan Xcoder,

@ Don'tbeax-tripledot A jeśli ktoś nie dostanie samej postaci, '\33'powinien być jeszcze krótszy.
Jonathan Frech

Również 2*5**.5jest 20**.5.
Jonathan Frech

@JonathanFrech Pierwiastek kwadratowy z 20 zastąpiony przez 4,47
mdahmoune

@mdahmoune Cóż ... Jeśli ta dokładność jest wystarczająco dobra, to tak.
Jonathan Frech

1

C # (.NET Core) , 201 , 180 + 13 = 193 bajtów

Wymaga użycia systemu; dla 13 dodatkowych bajtów.

O dziwo, Console.Clear () nie działa dla mnie na TIO. Działa to jednak doskonale w aplikacji konsolowej pod VS2017.

EDYCJA: Dzięki Embodiment of Ignorance za skrócenie pętli, wskazując moje niepotrzebne przypisywanie zmiennych i niepotrzebne przy użyciu System.Threading; instrukcja (pozostałość po kopiowaniu VS) i wskazująca, że ​​podstawa była wymagana! Do tej pory łącznie 8 bajtów grało w golfa z dodatkiem ziemi. Ty Ty!

x=>{for(var j=x;j>0;System.Threading.Thread.Sleep((int)(4470*(Math.Sqrt(x-j+1)-Math.Sqrt(x-j--))))){Console.Clear();Console.Write("X".PadLeft(x-j+1,'\n').PadRight(x+1,'\n')+"-");}}

Wypróbuj online!

Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.