ASCII Art «Flight Simulator»


24

РЕДАКТИРОВАТЬ

Похоже, что после моей опечатки в первоначальном посте произошла некоторая путаница, в которой для определения плоскости использовалась строчная буква o, а затем - заглавная. К сожалению, эта ошибка не была обнаружена в Песочнице. Так как многие члены написали ответы с обоими, и так как опечатка была моей ошибкой, я позволю использовать прописные или строчные буквы o в определении плоскости. Я добавил новое правило для этого.

Задний план

Мне нравятся ascii art анимации, как я их называю, так что вот еще одна. Я не думаю, что это слишком сложно реализовать, поэтому надеюсь получить короткие и интересные ответы.

Всем товарищам по сообществу

Если вы улучшили свой ответ, пожалуйста, измените количество байт на

старый счетчик байтов новый счетчик байтов

так что мы можем видеть ваш прогресс. Благодарность!

Вызов

Вот самолет ASCII

--O--

Вот взлетно-посадочная полоса

____|     |____

Самолет начинается на 5 новых линий выше взлетно-посадочной полосы. Чтобы предотвратить любые столкновения между метрической и имперской системами и сделать это действительно международным вызовом, я не буду упоминать метры или футы. Пример:

        --O--




____|     |____

Самолет должен приземлиться точно в середине взлетно-посадочной полосы, как показано ниже:

____|--O--|____

вход

Начальное горизонтальное положение плоскости определяется целочисленным вводом, который используется для ссылки на кончик левого крыла, т.е. он находится в диапазоне от 0 до 10 включительно.

Выход

Каждый этап полета самолетов должен быть показан. Пример ниже (input = 10):

          --O--




____|     |____

         --O--



____|     |____

        --O--


____|     |____

       --O--

____|     |____

      --O--
____|     |____

____|--O--|____

Для простоты мы игнорируем законы перспективы. Взлетно-посадочная полоса остается того же размера, как вы приближаетесь.

правила

  • Обновление Середина плоскости может быть в верхнем или нижнем регистре o, но какой бы ни был выбран, он должен быть согласован во всем коде. Если ваш язык не поддерживает символы, указанные выше, не стесняйтесь использовать альтернативные символы только ascii.
  • Самолет спускается на 1 строку за кадр.
  • Самолет может двигаться только на 1 пробел влево или вправо каждый раз, когда он спускается на одну линию. Он не должен двигаться по каждой линии спуска. Пока он заканчивается на взлетно-посадочной полосе, это зависит от вас, когда он движется вправо или влево. Ты пилот!
  • Обработка ошибок не требуется. Вы можете предположить, что входные данные всегда будут действительными целыми числами от 0 до 10 включительно.
  • Вывод должен состоять только из символов, показанных выше (если ваш язык не поддерживает их, см. Первое отредактированное правило) и должен быть одинакового размера, т.е. должен начинаться с 6 строк в высоту и 15 символов в ширину. Высота может уменьшаться по мере продвижения, как в примере выше.
  • Программа или функция в порядке, но должны выдавать результат, как показано выше.
  • Лидирующие / завершающие пробелы / переводы строк меня устраивают.
  • Пожалуйста, не стесняйтесь очищать экран между выходными кадрами, если хотите. Это не требование.
  • Стандартные лазейки, как обычно, запрещены (хотя я не думаю, что есть много людей, которые бы помогли с этим вызовом).
  • Это кодовый гольф, поэтому самый короткий ответ, очевидно, является победителем и, вероятно, получит большинство голосов, но не обязательно будет принят как лучший ответ, если какое-то действительно интересное решение придет на каком-то неожиданном языке, даже если оно длиннее. Не стесняйтесь публиковать все, что соответствует правилам, пока это работает.

Реализованная справочная реализация в Python 2 доступна на Попробуй онлайн! так что вы можете увидеть, как он выглядит для разных входных значений.


Я не думаю , что это Колмогорова- сложность как выход зависит от входа
овс

Спасибо за разъяснения @ovs. Я удалю этот тег тогда.
ElPedro

Обычно принятие идет к ответу, который лучше всего соответствует объективному критерию выигрыша. Вы можете получить некоторые ошибки, если вы примете другой, более длинный ответ.
Уровень Река St

Спасибо @LevelRiverSt. Есть ли мета-пост, чтобы прояснить это? Если нет, то, возможно, лучше не принимать никакого ответа.
ElPedro

Между прочим, я принял более длинный ответ и отдал должное более короткому ответу без каких-либо проблем со стороны сообщества. Предыдущий вызов . Пожалуйста, смотрите мой комментарий к результатам в конце вопроса. Было ли это неправильно?
ElPedro

Ответы:


5

TI-BASIC, 61 байт

Input A
A
For(B,1,5
ClrHome
Output(5,1,"----/     /----
Output(B,Ans,"--O--
Ans+6-median({5,7,Ans
End

Знаете ли вы онлайн-переводчик или скачать (для Linux) для тестирования? +1 за ответ при условии, что это работает :)
ElPedro

Проверьте TilEm. Это единственный, кого я мог получить на работу.
Джулиан Лакнет

2
+1 за вопрос к тому, у кого, возможно, был другой ответ. Обязательно ознакомлюсь с TilEm и спасибо за совет.
ElPedro

8

TI-BASIC, 62 байта

:Input A
:A
:For(N,3,8
:ClrHome
:Output(8,1,"----I     I----
:Output(N,Ans,"--O--
:Ans+(Ans<6)-(Ans>6
:End

Обратите внимание, что TI-BASIC не поддерживает _ или | и поэтому я заменил на заглавную I и -. Это не должно влиять на количество байтов.


ОК, я на Linux. Можете ли вы порекомендовать загрузку, которую я получу, чтобы проверить это? Кстати, я предполагаю, что это работает, пока я не найду переводчика, так что +1 :)
ElPedro

К сожалению нет. На моем компьютере с Windows 10 установлены и Wabbitemu, и TilEm, но я тестирую код на физическом TI-84 +. Извините
Золотое

Нет проблем! Просто спрашиваю :)
ElPedro

Из-за большого количества редактирования кода, самый быстрый чередовался между этим постом и Джулианом Лахнетом, пока мы оба не пришли к 60-байтовому выводу, после чего я добавил clrhome и сделал счетчик байтов 62
Golden Ratio

3
TI-Basic ?! Ницца!
Дэйв Кантер

6

Python 2, 107 байт

n=input();h=5
while h:print' '*n+'--O--'+'\n'*h+'____|     |____\n';n-=cmp(n,5);h-=1
print'____|--O--|____'

Попробуйте онлайн

Просто жестко кодирует последнюю строку для посадки самолета. Скорее всего, его можно сыграть в гольф, повторно использовав детали до или интегрировав в петлю.


5

Perl, 94 байта

93 байта кода + -pфлаг.

$\="____|     |____
";$p="--O--";for$i(-5..-1){print$"x$_.$p.$/x-$i;$_+=5<=>$_}$\=~s/ +/$p/}{

Попробуйте онлайн!


@ETHproductions Надеюсь, вам понравится }{$"возиться с подсветкой синтаксиса).
Дада

3

JavaScript (ES6), 108 байт

f=(a,b=5)=>b?" ".repeat(a)+`--O--${`
`.repeat(b)}____|     |____

`+f(a<5?a+1:a-1,b-1):"____|--O--|____"

Попробуй это

использование

Просто позвоните fс указателем самолета.

f(2)

Выход

  --O--




____|     |____

   --O--



____|     |____

    --O--


____|     |____

     --O--

____|     |____

    --O--
____|     |____

____|--O--|____

Вы можете добавить фрагмент <s> закуски </ s> стека
Kritixi Lithos

Каждый раз, когда я задаю вопрос, первым ответом является Javascript! +1
ElPedro

Эй, было бы неплохо, если бы люди разместили либо Tryitonline (не знаю, возможно ли это с помощью Javascript), либо другое решение по сравнению с 10 примером, показанным выше. Можете ли вы опубликовать вывод, например, из 2 вместо? :)
ElPedro

@ElPedro, вы можете выполнять JavaScript в консоли браузера, но также есть несколько онлайн-консолей. Я добавлю ссылку. Я также изменю пример.
Люк

Спасибо. Нет проблем. Я в старом Javascript, где вам нужна веб-страница для его выполнения. Думаю, мне нужно идти в ногу со временем :) Больше серверов в эти дни. Респект за быстрый и классный ответ.
ElPedro

3

Scala, 224 181 байт

РЕДАКТИРОВАТЬ : Я понятия не имел, что вы могли бы сделать, "string"*nчтобы повторить это n раз! Скала продолжает поражать меня. Пропуск if(t>0)вместо if(t==0)был ошибкой новичка. Спасибо за советы, Сума !


def?(x:Int,t:Int=5):Unit={var(p,o)=("--o--","")
o=s"____|${if(t>0)" "*5 else p}|____\n"
for(i<-0 to t)o=if(i!=0&&i==t)" "*x+p+o else "\n"+o
println(o)
if(t>0)?(x-(x-4).signum,t-1)}

Оригинальные замечания:

Я подумал, что было бы интересно попробовать рекурсивное решение. Я относительно новичок в Scala, поэтому я уверен, что это далеко не оптимально.


Возможно, вы захотите прочитать Советы по игре в гольф в
скале

Вам не нужно :Unit=. Пропуск знака равенства установит тип возвращаемого значения в Unit.
corvus_192

Кроме того, почему вы не инициализировали oв первой строке? И так iкак всегда> = 0, вы можете изменить i!=0&&i==tна i>0&i==t(3-я строка).
corvus_192

2

Пакет, 230 байтов

@echo off
set/ax=10-%1
set s=          --O--
for /l %%i in (0,1,4)do call:l %%i
echo ____^|--O--^|____
exit/b
:l
call echo %%s:~%x%%%
for /l %%j in (%1,1,3)do echo(
echo ____^|     ^|____
echo(
set/a"x-=x-5>>3,x+=5-x>>3

xэто количество пробелов, которые нужно удалить из начала строки s, поэтому я вычитаю параметр из 10. Последняя строка - это ближайший пакет, который должен x-=sgn(x-5).


2

sed, 181 байт + 2 для -nrфлагов

s/10/X/
:A
s/^/ /;y/0123456789X/-0123456789/;/[0-9]/bA;s/ -/P\n\n\n\n\n____|P|____/
:B
h;s/P([\n|])/--O--\1/;s/P/     /;s/^ *_/_/;p;/^_/q;x;s/\n//
/^ {5}$/bB;/ {6}/s/  //;s/^/ /;bB

Ungolfed

# Add leading spaces
s/10/X/
:A
    s/^/ /
    y/0123456789X/-0123456789/
/[0-9]/bA

s/ -/P\n\n\n\n\n____|P|____/

:B
    # Place plane in appropriate spot
    h
    s/P([\n|])/--O--\1/
    s/P/     /
    s/^ *_/_/
    p
    /^_/q
    x

    # Movement
    s/\n//
    /^ {5}$/bB
    # move left one extra, since we'll move right next line
    / {6}/s/  // 
    s/^/ /
bB

Использование: $ echo 2 | sed -nrf flightsim.sed


2

Retina , 86 83 байта

.+
$* --O--¶¶¶¶¶¶____|     |____
{*`$
¶
2D`¶
 ( {5})
$1
}`^ {0,4}-
 $&
 +
--O--
G`_

Попробуйте онлайн!

Вероятно, есть какое-то сжатие, которое я мог бы использовать на ВПП, и пустое пространство над ним, но все, что я пробовал, оказалось дороже, чем открытый текст (в Retina ¶ это новая строка, так что вы можете увидеть начальное состояние в виде открытого текста на вторая линия).


2

Scala , 177, 163, 159, 137 байт.

def p(x:Int,t:Int=5,a:String="\n"):String=a+(if(t>0)
" "*x+"--O--"+"\n"*t+"____|     |____\n"+p(x-(x-4).signum,t-1)else"____|--O--|____")

На основании другого ответа , со значительными сокращениями.


2

Perl 6 , 97 90 81 байт

{say "{"{" "x 15}\n"x 5}____|     |____"~|("\0"x$^h+$_*(17-$h/5)~"--O--") for ^6}

Вопреки тому, как это выглядит, он выводит версию * в нижнем регистре --o--, как это разрешено обновленным описанием задачи.

Попробуйте онлайн!

Как это работает

Битовые строковые операторы FTW!

{                                                  # Lambda accepting horizontal index $h.
    say                                            # Print the following:
        "{ "{ " " x 15 }\n" x 5 }____|     |____"  # The 15x6 background string,
        ~|                                         # bitwise-OR'd against:
        (
            "\0"                                   # The NULL-byte,
            x $^h + $_*(17 - $h/5)                 # repeated by the plane's offset,
            ~ "--O--"                              # followed by an OR mask for the plane.
        )
    for ^6                                         # Do this for all $_ from 0 to 5.
}

Это работает потому, что побитовые строковые операторы используют значения кодовой точки символов в заданной позиции в двух строках, чтобы вычислить новый символ в этой позиции в выходной строке.
В этом случае:

space  OR  O   =  o
space  OR  -   =  -
any    OR  \0  =  any

Для верхнего регистра Oмы могли бы использовать ~^(строковое поразрядное XOR) с плоской маской \r\ro\r\r(+4 байта для обратной косой черты):

space  XOR   o  =  O
space  XOR  \r  =  -
any    XOR  \0  =  any

Формула для смещения плоскости, h + v*(17 - h/5)была упрощена из:

  v*16         # rows to the vertical current position
+ h            # columns to the horizontal starting position
+ (5 - h)*v/5  # linearly interpolated delta between horizontal start and goal

1

Python 2 , 160 байт

i,s,p,l,r,c,x=input(),' ','--O--','____|','|____',0,4
while x>=0:print'\n'.join([s*i+p]+[s*15]*x+[l+s*5+r])+'\n';c+=1;x-=1;i=((i,i-1)[i>5],i+1)[i<5]
print l+p+r

Попробуйте онлайн!

Вот эталонная реализация, упавшая до 160 с 384. Я думаю, что путь еще впереди. Просто опубликовано для удовольствия и для поощрения лучшего ответа Python.


Вы можете соревноваться в своем собственном соревновании (см. Этот мета-пост ).
Дада

Вы можете просто сделать while-~x?
FlipTack

Кроме того, я думаю , что вы можете написать немного , где вы либо добавить или вычесть из , iкакi+=(i<5)-(i>5)
FlipTack

1

Befunge-93, 136 130 байт

&5>00p10p55+v
:::00g>:1-\v>:"____|     |_"
>:1-\v^\+55_$"--O--"10g
^\*84_$>:#,_10g::5v>:#,_@
<_v#!:-1g00+`\5\-`<^"____|--O--|____"

Попробуйте онлайн!

объяснение

&                          Read the plane position.
 5                         Initialise the plane height.
  >                        Begin the main loop.

   00p                     Save the current height.
      10p                  Save the current position.
         55+:              Push two linefeed characters.

         "____|     |_"    Push most of the characters for the airport string.
:::                        Duplicate the last character three times to finish it off.

   00g>:1-\v               Retrieve the current height, and then push
      ^\+55_$                that many copies of the linefeed character.

             "--O--"       Push the characters for the plane.

>:1-\v              10g    Retrieve the current position, and then push
^\*84_$                      that many copies of the space character.

       >:#,_               Output everything on the stack in reverse.

            10g::          Retrieve the current position and make two copies to work with.
                 5v        If it's greater than 5
                -`<          then subtract 1.
           +`\5\           If it's less than 5 then add 1.

        g00                Retrieve the current height.
      -1                   Subtract 1.
 _v#!:                     If it's not zero, repeat the main loop.

^"____|--O--|____"         Otherwise push the characters for the landed plane.
>:#,_@                     Output the string and exit.

1

Рубин, 94 байта

->a{5.times{|i|puts" "*a+"--O--#{?\n*(5-i)}____|     |____

";a+=5<=>a};puts"____|--O--|____"}

Печатает положение самолета с последующими символами новой строки и затем аэропортом. Затем он перемещает плоскость на 1, -1 или 0, в зависимости от его положения относительно 5.

После повторения 5 раз он печатает самолет в аэропорту.


1

8-е , 177 172 байта

: f 5 >r 5 repeat over " " swap s:* . "--O--" . ' cr r> times "____|     |____\n\n" . over 5 n:cmp rot swap n:- swap n:1- dup >r while "____|--O--|____\n" . 2drop r> drop ; 

Слово fожидает целое число от 0 до 10.

использование

4 f

объяснение

: f \ n --
  5 >r     \ Push vertical distance from airport to r-stack
  5 repeat 
    \ Print plane
    over " " swap s:* . "--O--" . 
    \ Print airport 
    ' cr r> times "____|     |____\n\n" . 
    \ Now on the stack we have:
    \ distanceFromLeftSide distanceFromAirport
    over      \ Put distance from left side on TOS 
    5 n:cmp   \ Compare left distance and 5. Return
              \ -1 if a<b, 0 if a=b and 1 if a>b
    rot       \ Put distance from left side on TOS   
    swap n:-  \ Compute new distance from left side 
    swap n:1- \ Decrement distance from airport
    dup >r    \ Push new airport-distance on the r-stack  
  while 
  "____|--O--|____\n" .  \ Print final step
  2drop r> drop          \ Empty s-stack and r-stack
;

1

Mathematica, 111 байт

If[#<1,"____|--O--|____"," "~Table~#2<>"--O--"<>"
"~Table~#<>"____|     |____

"<>#0[#-1,#2+#2~Order~5]]&[5,#]&

Анонимная функция. Принимает число в качестве ввода и возвращает строку в качестве вывода. Возможно, будет дальше в гольф.


1

QBIC , 93 91 84 байта

:{X=space$(a)+@--O--`┘a=a-sgn(a-5)~t>-1|?X[t|?]t=t-1?@____|`+@     `+_fB|\_xB+A+_fB

Удалил несколько байтов, заменив объявление X $; оптимизирован цикл FOR, который печатает расстояние над землей. Приведенное ниже объяснение относится к старой версии, но в основном работает так же.

Для тестирования (и эстетики) у меня была немного другая версия, на 103 байта:

:{_z.5|_CX=Y[a|X=X+@ `]X=X+@--O--`
a=a-sgn(a-5)
~u>0|?X';`[u|?]u=u-1?@____|`+@     `+_fC|\_xC+_tB+_fC

Они функционально идентичны. Второе дополнение имеет то, что экран очищается между кадрами и останавливается на 0,5 секунды между кадрами.

Образец вывода

Обратите внимание, что я добавил две новые строки между кадрами. Самый лучший код выше не добавляет пустые строки между кадрами, более прохладный очищает экран.

Command line: 10


          --O--




____|     |____


         --O--



____|     |____


        --O--


____|     |____


       --O--

____|     |____


      --O--
____|     |____


____|--O--|____

объяснение

Так как я чувствую, что это затрагивает многие вещи, которые мне действительно нравятся в QBIC, и дает хорошее представление о том, как некоторые из его функций работают под капотом, я немного упустил объяснение. Обратите внимание, что QBIC по своей сути является интерпретатором QBasic для Codegolf. Код QBIC входит - код QBasic выходит (и впоследствии выполняется).

:{      get the starting offset (called 'a') from the command line, and start a DO-loop

----  cool code only  ----
_z.5|_C At the start of a DO-loop, pause for half a second and clear the screen
---- resume golf-mode ----

---- #1 - The tip of the left wing is anywhere between 0 and 10 positions to the right.
----       Create the plane with the spacing in X$
X=Y          Clear X$
[a|          For each point in the current offset
X=X+@ `]     Add a space to X$
    - Every capital letter in QBIC references that letter+$, a variable of type String
    - @ and ` start and end a string literal, in this case a literal space.
    - ] ends one language construct (an IF, DO or FOR). Here, it's NEXT
X=X+@--O--`  Create the actual plane
    - @ and `once again create a string literal. Every literal that is created in this
      way is assigned its own capital letter. This is our second literal, so the body of
      our plane is stored in B$ (A$ contains the space, remember?)

---- #2 Adjust the offset for the next iteration      
a=a-sgn(a-5) The clever bit: We have an offset X in the range 0 - 10, and 5 attempts to 
             get this to be == 5. X - 5 is either positive (X = 6 - 10), negative 
             (X = 0 - 4) or 0 (X=5). sgn() returns the sign of that subtraction 
             as a 1, -1 or 0 resp. We then sub the sign from 'a', moving it closer to 5.

---- #3 Draw the plane, the empty airspace and the landing strip             
~u>0|     Are we there yet?
    - ~ is the IF statement in QBIC
    - It processes everything until the | as one true/false expression
    - All the lower-case letters are (or better, could be) references to numeric 
      variables. Since QBasic does not need to post-fix those, they double as 'natural' 
      language: ignored by QBIC and  passed as literal code to the QBasic beneath.
    - The lower-case letters q-z are kinda special: at the start of QBIC, these 
      are set to 1 - 10. We haven't modified 'u' yet, so in the first DO-loop, u=5

?X';`     If we're still air-borne, print X$ (our plane, incl. spacers)
    - ? denotes PRINT, as it does in QBasic.
    - ' is a code literal in QBIC: everything until the ` is not parsed, but 
      passed on to QBasic.
    - In this case, we want a literal ; to appear after PRINT X$. This suppresses 
      QBasic's normal line-break after PRINT. This needs to be a code literal 
      because it is the command to read a String var from the command Line in QBIC.
[u|?]     FOR EACH meter above the ground, print a newline
u=u-1     Descent 1 meter
?@____|`  Print the LHS of the landing strip
+@     `  plus 5 spaces
+_fC|     plus the LHS reversed.
\         ELSE - touchdown!
_x        Terminate the program (effectively escape the infinite DO-loop)
    - the _x command has an interesting property: ULX, or Upper/Lowercase Extensibility. 
      Writing this command with an uppercase _X does something similar, yet different. 
      The _x command terminates, and prints everything found between _x and | before 
      quitting. Uppercase _X does not look for |, but only prints something if it is 
      followed by a character in the ranges a-z and A-Z - it prints the contents of 
      that variable.
C+B+_fC   But before we quit, print C$ (the LHS of the landing strip) and the plane, 
          and the LHS flipped.

---- #4 QBIC has left the building
- Did I say _x looks for a | ? Well, that gets added implicitly by QBIC at the end of 
  the program, or when one ( ']' ) or all ( '}' ) opened language constructs are closed.
- Also, all still opened language constructs are automatically closed at EOF.
- Had we stored anything in Z$, that would also be printed at this time.

1

SmileBASIC, 109 105 байт

G$="_"*4INPUT X
FOR I=0TO 4?" "*X;"--O--";CHR$(10)*(4-I)?G$;"|     |";G$X=X-SGN(X-5)?NEXT?G$;"|--O--|";G$

1

PHP 7, 139 байт

все еще ужасно долго

for($x=$argv[1],$d=6;$d--;$x+=5<=>$x)for($i=$p=-1;$i++<$d;print"$s
")for($s=$i<$d?" ":"____|     |____
";!$i&++$p<5;)$s[$x+$p]="--O--"[$p];

принимает входные данные из аргумента командной строки; беги с -r.

сломать

for($x=$argv[1],                        // take input
    $y=6;$y--;                          // loop height from 5 to 0
    $x+=5<=>$x)                             // post increment/decrement horizontal position
    for($i=$p=-1;$i++<$y;                   // loop $i from 0 to height
        print"$s\n")                            // 3. print
        for($s=$i<$y?" ":"____|     |____\n";   // 1. template=empty or runway+newline
            !$i&++$p<5;)$s[$x+$p]="--O--"[$p];  // 2. if $i=0, paint plane
Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.