Геометрический вызов

23

Все любят геометрию. Так почему бы нам не попробовать и написать код в гольф? Эта задача включает в себя прием букв и цифр и создание фигур в зависимости от этого.

Вход

Вход будет в форме (shapeIdentifier)(size)(inverter).

Но что такое shapeIdentifier, размер и инвертор?

Идентификатор фигуры - это идентификатор типа фигуры, который вы будете создавать с помощью *s. Ниже приведены идентификаторы формы:

  • s - Площадь
  • t - треугольник

Размер будет между 1-20, и это размер фигуры.

Инвертор определяет, будет ли форма перевернутой, что обозначается буквой а +или а -. Обратите внимание: s3-== (равно), s3+потому что квадраты симметричны. Однако t5-! = (Не равно) t5+.

Конечные пробелы в выходных данных допустимы, а начальные пробелы - нет.

Примеры вывода

Input: s3+
Output:
***
***
***

Input: t5+

Output:
  *
 ***
*****

Input: t3-
Output:
***
 *

Особые заметки

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

Размер треугольника - это размер основания, если инвертор есть, +и размер вершины, если инвертор есть -.

intboolstring
источник
3
Как человек, который изучает геометрию прямо сейчас (и готовится к финалу по геометрии), я могу сказать со 100% уверенностью: геометрия абсолютно, совсем не весело ... D:
Эшвин Гупта

Ответы:

9

Pyth, 40 36 34 32 байта

-1 байт @isaacg

JstPz_W}\+zjl#m.[J*\*-J*}\tzyd;J

Точка с запятой внутри лямбды - теперь глобальное значение лямбда-переменной, функция, которая сохраняет один байт.

                         Implicit: z = input
JstPz                    J = size.
_W }\+z                  Reverse if "+" in z
j l# m                J  Join the nonempty lines in map lambda d:... over range(J)
      .[J            ;   Pad the following with spaces (;) to length J
         *\*               "*", this many times:
            -J*}\tzyd        J if "t" not  in z,
                             otherwise the correct number for a triangle.

Попробуй это здесь .

Тестовый пакет .

lirtosiast
источник
1
Слишком долго, но выиграл у Джапта на 15 байтов? Я не могу дождаться, чтобы увидеть, как это будет в гольфе :)
ETHproductions
Отличное решение! Вы можете сохранить байты, заменяя qez\+с }\+z, потому что +может появиться только в последней позиции.
Исаак
6

Pyth, 38 байт

JsPtzj?}\szm*\*JJ_W}\-zm.[J*\*hyd;/hJ2

Тестирование

В основном так просто, как это получается. Хотелось бы объединить некоторую логику для двух фигур, но в настоящее время она разделена.

isaacg
источник
5

JavaScript (ES6), 142 146 147

Редактирование 1 байта сохранено thx @ETHproductions Редактирование 2 байта sve thx @ user81655

i=>([,a,b]=i.match`.(.+)(.)`,Array(l=i<'t'?+a:-~a/2).fill('*'.repeat(a)).map((r,i)=>l-a?(' '.repeat(i=b<'-'?--l:i)+r).slice(0,a-i):r).join`
`)

Тест (запустить в FireFox)

F=i=>(
  [,a,b]=i.match`.(.+)(.)`,
  Array(l=i<'t'?+a:-~a/2).fill('*'.repeat(a))
  .map((r,i)=>l-a?(' '.repeat(i=b<'-'?--l:i)+r).slice(0,a-i):r)
  .join`\n`
)

function test() { O.textContent=F(I.value) }

test()
Input: <input id=I oninput="test()" value="t11-"/>
<pre id=O></pre>

edc65
источник
\d-> ., поскольку там гарантированно будет ровно одна нецифровка до и после
ETHproductions
@ETHproductions верно, спасибо
edc65
Ницца. Я думаю, что это оптимальный алгоритм в JS, не могу найти более короткий.
ETHproductions
i.match(/.(.+)(.)/)->i.match`.(.+)(.)`
user81655
@ user81655 хороший совет, спасибо
edc65
5

Python 2, 106 байт

s=raw_input()
n=int(s[1:-1])
for i in[range(1,n+1,2),n*[n]][s<'t'][::2*('+'in s)-1]:print('*'*i).center(n)

На выходе получается идеальный прямоугольник с каждой строкой, дополненной конечными пробелами, что, я полагаю, хорошо, основываясь на комментариях в ОП.

Примечание: я до сих пор не уверен, inputразрешено ли в Python 2 для подобных проблем ...

Sp3000
источник
4

Japt, 62 60 55 52 51 байт

V=Us1 n;U<'t?Vo ç*pV):0oV2 £S²pY iY'*pV-X})·z2*!Uf-

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

Первое, что нам нужно сделать, это выяснить, насколько большой должна быть наша форма. Это довольно просто:

      // Implicit: U = input string, S = space
V=    // Set variable V to
Us1   // everything after the first char of U,
n;    // converted to a number. This turns e.g. "12+" into 12.

Теперь мы организуем форму вывода:

U<'t?      // If U comes before "t" lexicographically (here, if the first char is "s"),
Vo         //  make a list of V items,
ç*pV)      //  and set each item to V asterisks.
:0oV2      // Otherwise, create the range [0, V) with steps of 2 (e.g. 7 -> [0,2,4,6]),
£       }) //  and map each item X and index Y to:
S²pY       //   Repeat 2 spaces Y times. This creates a string of Y*2 spaces.
iY'*pV-X   //   At position Y in this string (right in the middle), insert V-X asterisks.
·          // Join with newlines.

К настоящему времени мы позаботились о размере и форме вывода. Осталось только вращение. Треугольники в настоящее время направлены вверх, поэтому нам нужно перевернуть их, если третий символ +:

!Uf-    // Take the logical not of U.match("-").
        // If U contains "-", this returns false; otherwise, returns true.
2*      // Multiply by two. This converts true to 2, false to 0.
z       // Rotate the list 90° that many times.
        // Altogether, this turns the shape by 180° if necessary.

И с неявным выводом наша работа здесь завершена. :-)

ETHproductions
источник
4

Python 2, 235 193 167 157 байт

Обновить:

Сделал некоторую значительную оптимизацию, используя списки и str.center (). У меня такое чувство, что я могу сделать еще кое-что, собираюсь по-новому взглянуть на это позже.

Обновление 2

Сохранено 10 байт с предложениями Sherlock9. Большое спасибо! :)

d=raw_input()
x=int(d[1:-1])
o="\n".join("*"*x for i in range(x))if d<"t"else"\n".join(("*"*i).center(x)for i in range(x,0,-2))
print o[::-1]if"+"in d else o

Старый ответ

d=raw_input()
x=int(d[1:-1])
if "s" in d:
 for y in range(x):
    o+="*"*x+"\n"
 o=o[:-1]
else:
 b=0
 while x+1:
    o+=" "*b+"*"*x+" "*b+"\n"
    x-=2
    b+=1
 o=o[:-1]
 if d[-1]=="+":
    o=o[::-1]
print o

Довольно простой подход. Запись строки в строку в строке, которую я вывожу в конце. Треугольники всегда рисуются перевернутыми и при необходимости переворачиваются. Тот факт, что вы можете умножить строку на целое число, сэкономил мне много байтов!

Я постараюсь сыграть в эту игру чуть позже, в то же время буду признателен за предложения, так как я еще не очень разбираюсь в этом.

редактировать: играли в него много с помощью комментариев и кражи расчета размера из одного из других ответов на python. Я думаю, что больше всего я могу сделать с этим алгоритмом.

Denker
источник
Как ты считал? При использовании wcэтого дает мне количество байтов 235. Я ошибаюсь?
მოიმო
1
Это действительно 235 байтов. Совет по игре в гольф: используйте табуляцию вместо двух пробелов, что допустимо в Python 2 и будет сбрасывать 5 байтов.
Дверная ручка
Также вам не нужно использовать raw_input, используя inputэкономит 4 байта. Кроме того, вам не нужны скобки во второй строке, это и вообще не использование переменной x(использование if"s"in d) экономит вам еще 9 байтов.
მოიმო
2
@DenkerAffe при подсчете в окне вычитайте 1 байт для каждой новой строки - в окнах - 2 байта, а в других
edc65
1
Во-первых, вы можете убрать []скобки в каждом вызове joinфункции. Во-вторых, if d<"t"elseкороче и работает потому что "s3+"<"t"<"t3+"в Python. В-третьих, else"\n".joinи .center(x)for. Нет места. Это не обязательно. В- четвертых, print o[::-1]if"+"in d else oкогда я переставить вещи для двух байтов (один пробел между ]и ifи другой между ifи "+".
Sherlock9
3

JavaScript, 220 байт.

q=s=>+s.slice(1,s.length-1);f=s=>s[0]=="s"?("*".repeat(q(s))+"\n").repeat(q(s)):Array.apply(0,Array(-~(q(s)/2))).map((_,n)=>(s[s.length-1]=="-"?~~(q(s)/2)-n:n)).map(n=>(" ".repeat(q(s)/2-n)+"*".repeat(n*2+1))).join("\n")

Бежать с f(input here)

Попробуй это здесь!

Квадраты имеют завершающие символы новой строки, а треугольники - нет. Объяснение:

q=s=>+s.slice(1,s.length-1);                                                                                                                                                                                                 Define a function, q, that takes returns the argument, without the first and last character, casted into an integer.
                            f=s=>                                                                                                                                                                                            Define a function, f, that takes one argument, s. (This is the main function)
                                 s[0]=="s"?                                                                                                                                                                                  If the first character of s is "s" then...
                                           ("*".repeat(q(s))     )                                                                                                                                                           Repeat the "*" character q(s) times.
                                           (                +"\n")                                                                                                                                                           Append a newline to that
                                                                  .repeat(q(s))                                                                                                                                              Repeat that q(s) times.
                                                                               :                                                                                                                                             Else... (the first character of s isn't "s")
                                                                                Array.apply(0,Array(          ))                                                                                                             Create an array of length...
                                                                                Array.apply(0,Array(-~(q(s)/2)))                                                                                                             floor(q(s)/2)+1
                                                                                                                .map((_,n)=>                                   )                                                             Map each element, _ with index n to...
                                                                                                                .map((_,n)=>(s[s.length-1]=="-"?              ))                                                             If the last element of s is "-" then...
                                                                                                                .map((_,n)=>(s[s.length-1]=="-"?~~(q(s)/2)-n  ))                                                             floor(q(s)/2)-n
                                                                                                                .map((_,n)=>(s[s.length-1]=="-"?            : ))                                                             Else...
                                                                                                                .map((_,n)=>(s[s.length-1]=="-"?             n))                                                             Just n
                                                                                                                                                                .map(n=>                                        )            Map each element into...
                                                                                                                                                                .map(n=>(" ".repeat(q(s)/2-n)                   )            Repeat " ", q(s)/2-n times.
                                                                                                                                                                .map(n=>(                   )+"*".repeat(n*2+1)))            Append "*", repeated 2n+1 times.
                                                                                                                                                                .map(n=>(" ".repeat(        )+"*".repeat(n*2+1))).join("\n") Join with newlines
Loovjo
источник
Длина вашей первой строки составляет 338 символов. Мне требуется один монитор с половиной для отображения.
Исана
1
Я не буду нажимать на случайную ссылку tinyurl, но проверьте еще раз. В любом случае, старайтесь избегать полос прокрутки в окнах кода, это усложняет чтение.
Исана
1
@Loovjo Я думаю, он имеет в виду первую строку объяснения. Я обычно делаю отступы от своего объяснения, а не от стиля для ответов JavaScript, поэтому вам не нужно прокручивать, чтобы увидеть половину.
user81655
@ user81655 Да, я имел ввиду в объяснении. Теперь я понимаю путаницу!
Исана
3

Python 2, 157 132 байта

def f(s):
 S=int(s[1:-1])
 for n in([range(1,S+2,2),range(S,0,-2)]['-'in s],[S]*S)['s'in s]:
  print "{:^{S}}".format('*'*n,S=S)

Первая попытка показала, что +/-конец не обязателен, избавившись от этого, позвольте мне сбрить кучу

Идея здесь состоит в том, чтобы создать список, который можно добавить в общий вывод. Сложнее всего было отделить длину от входа.

wnnmaw
источник
Для получения длины я использовал x=int(d[1]if len(d)<4 else d[1:3])d как строку ввода. Это на 5 байт короче вашего решения. Вы все еще далеко впереди моего python-ответа, но постарайтесь понять, что вы там сделали, и победить вас в следующий раз! :)
Денкер
1
На самом деле x=int(d[1:-1])это намного короче, только что видел это в другом ответе Python.
Денкер
@DenkerAffe, по какой-то причине я помню, что инвертор был необязательным, так что это не сработало, но, думаю, я только что сделал это
wnnmaw
2

Сетчатка , 102 85 байт

Подсчет байтов предполагает, что исходный код закодирован как ISO 8859-1.

\d+
$0$*:¶
^((\w)+):(:+)
$1$2$3$2¶$0
m`s$|:t

)`(.+)¶-(\D*)
-$2¶$1
m`^.

G`.
T`ts:` *

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

Я попробую сыграть в гольф еще немного позже.

Мартин Эндер
источник
Notepad ++ говорит, что ваш код составляет 89 байт, а не 85. Я использовал кодировку ISO-8859-1 и выбрал Правка> Преобразование EOL> Формат UNIX / Linux, чтобы использовать \nвместо \r\n. Base64 контента: XGQrCiQwJCo6wrYKXigoXHcpKyk6KDorKQokMSQyJDMkMsK2JDAKbWBzJHw6dAoKKWAoLispwrYtKFxEKikKLSQywrYkMQptYF4uCgpHYC4KVGB0czpgICo=(прямое копирование из Notepad ++). Как ни странно, любое онлайн-решение дает мне 85 байт ... Хум ...
Исмаэль Мигель
@IsmaelMiguel Должно быть что-то не так с тем, как Notepad ++ считает . Это определенно один байт в ISO 8859-1 (со значением 182).
Мартин Эндер
2

Серьезно, 54 байта

,#i's=`≈;'**@½≈";#dXdXεj' +"£n`@`≈;'**n`@Iƒ('-=WXa0WXü

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

,#i                                                    Take input, push chars separately
   's=                                   Iƒ            IF the first char is "s":
                                `      `@                run the quoted function
                                 ≈;'**n                  make list of n strings of n *'s
      `                       `@                       ELSE run the quoted function:
       ≈;                                                make two copies of int n
         '**                                             use one to make string of n *'s
            @½≈                                          cut the other in half (e.g. 5->2)
               "           "£n                           run n/2 times the quoted function:
                ;#                                        copy the string as list of chars
                  dXdX                                    discard the last 2 *'s
                      εj                                  join back into string
                        ' +                               prepend a space
                                           ('-=WX 0WX  IF the third character is "-":
                                                 a       invert the stack
                                                     ü pop and print the entire stack

@Mego: Видишь это #dXdXεj? STRING SLICING ????

quintopia
источник
2

ES6, 178 172 159 байт

s=>(p=s.match(/d+|./g),u=n=+p[1],m=n+1>>1,t=' '.repeat(n)+'*'.repeat(n),v=s<'t'?0:p[2]<'-'?(u=m,1):-1,[...Array(s<'t'?n:m)].map(_=>t.substr(u,u,u+=v)).join`
`)

Это работает из-за интересного наблюдения, которое я сделал. Если вы повторяете nпробелы и nзвездочки, вы получаете (например, для n=5) это:

     *****

Теперь возьмем подстроки с одинаковым началом и длиной:

     |*****| (5)
    | ***| (4)
   |  *| (3)

Эти подстроки являются именно теми строками, которые нам нужны t5 .

Редактировать: Сохранено 6 байтов благодаря @ edc65.

Редактировать: Сохранено 13 байтов благодаря сокрытию u+=vв третьем аргументе, substrчто позволяет мне упростить инициализацию.

Нил
источник
@ThomasKwa Да, после того, как я установил tкод обработки, оказалось, что wи uстало эквивалентом и это спасло мне достаточно байт , чтобы взять меня обратно до 178!
Нил
[,b,c]=s.matchи позже s<'t'... следует сохранить несколько байтов (только Firefox)
edc65
@ edc65 Просто не сохранив совпадение, sя могу использовать, s<'t'что сэкономило мне 6 байтов, спасибо.
Нил
2

MATL , 48 байтов

' *'jt4Y2m)U1$l't'Gm?2MQ2/:1L3$)R!P!R'+'Gm?P]]Q)

Использует текущую версию (10.1.0) языка / компилятора.

Код принимает входные символы в любом порядке: все s11+, 11s+и даже 1+s1бы допустимые входные строки.

РЕДАКТИРОВАТЬ (30 июля 2016 г.): связанный код заменяется 1L3$)на, Y)чтобы соответствовать последним изменениям языка

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

объяснение

' *'        % push string. Will be indexed into to obtain final result
j           % input string
t           % duplicate
4Y2         % predefined literal string '0123456789'
m           % logical index of digits in input string
)           % index into input string to obtain substring with digits
U           % convert to number
1$l         % generate square of ones with that size
't'         % push character 't'
G           % push input string
m           % true if input string contains 't'
?           % if so...
  2M        % push argument of call to function `l`, i.e. square size
  Q2/       % add 1 and divide by 2. Call result T
  :         % generate vector [1, 2, ... T]
  1L        % predefined literal representing Matlab's `:` index
  3$)       % two dimensional index. Transforms square into rectangle
  R         % remove (set to zero) lower-left corner
  !P!       % flip horizontally
  R         % remove lower-left corner. This gives inverted triangle
  '+'       % push character '+'
  G         % push input
  m         % true if input contains '+'
  ?         % if so...
    P       % flip vertically
  ]         % end if
]           % end if
Q           % add 1. This gives array of values 1 and 2
)           % index string ' *' with this array to produce char array
            % implicitly display that char array
Луис Мендо
источник
1

C 259 байт

#define x(y);)putchar(y)
#define m(n)for(n=0;n++<
#define T {m(q)i x(32);m(q)s-i*2 x(42);puts("");}
main(q,v,i,s)char**v;{s=atoi(v[1]+1);if(*v[1]=='s')m(i)s*s x(42)&&!(i%s)&&puts("");else if(strchr(v[1],'+'))for(i=s/2+1;i-->0;)T else for(i=-1;i++<s/2+1;)T}

ungolfed

main(q,v,i,size)char**v; // neat way of declaring variables
{
    size=atoi(v[1]+1);
    if(*v[1]=='s')
    {
        for(i=0;i++<size*size;)
        {
            putchar(42); // returns 42 (true)
            if(!(i%size))
                puts("");
        }
    }
    else if(strchr(v[1],'+')) // if finds plus sign
    {
        for(i=size/2+1;i-->0;) // iterate the height of the triangle
        {
            for(q=0;q++<i;)putchar(32); // conveniently i is the number os spaces before each line
            for(q=0;q++<size-i*2;) putchar(42);
            puts("");
        }
    }
    else for(i=-1;i++<size/2+1;) // does the same as above but inverted order
    {
        for(q=0;q++<i;)putchar(32);
        for(q=0;q++<size-i*2;)putchar(42);
        puts("");
    }
}

Предложения и критика очень приветствуются.

Линс Ассассино
источник
1

Руби, 99

->s{n=s[1,2].to_i
n.times{|i|d=(s.ord-115)*(s[-1]<=>?,)*(n-1-i*2)
d<1&&puts((?**(n+d)).center(n))}}

Вычисляет квадрат или треугольник высоты nи средней ширины n , выравнивая наклон сторон (таким образом, рассчитанная ширина треугольника составляет 2n-1 в основании, 1 на кончике.) Но он печатает только те строки, которые не превышают nсимволов.

разряженный в тестовой программе

f=->s{                         #take a string as an argument
  n=s[1,2].to_i                #take 2 characters starting at index 1 and convert to a number for the size
  n.times{|i|                  #iterate through n rows    
    d=                         #calculate how many stars "MORE THAN" n we need on a row
    (s.ord-115)*               #ascii code for 1st character of string - 115 : s-->0, t-->1
    (s[-1]<=>?,)*              #compare last character of input with comma character - --> +1 + --> -1
    (n-1-i*2)                  #row number * 2: 0 at centre, positive above it, negative below it
    d<1&&                      #only output if d is nonpositive (i.e we need less than n or exactly n stars)
    puts((?**(n+d)).center(n)) #print n+d stars, centred in a field of n characters padded by whitespace
  }
}

f[gets.chomp]
Уровень реки St
источник
1

Джольф, 37 байт, неконкурентный

Я добавил функции после того, как этот вызов был опубликован, так что это не может рассматриваться для принятия. Это закодировано в ISO-8859-7. Попробуйте все контрольные примеры здесь .

onFiΒ€ioSgiγ?='sn―sΒ'*―TΒ1'*?='-SZiγγ

Часть 1: разбор строки

onFiΒ€ioSgi
on          set n to
  Fi         the first entity of i (the shape identifier)
    Β       set Β (beta) to
     €i      the "inside" of i (in this case, the size) as a number
       oS   set S to
         gi  the last entity of i (the inverter)

Часть 2: получение результата

γ?='sn―sΒ'*―TΒ1'*
γ                 set γ (gamma) to the result of the following expression
 ?='sn             if n is the character s,
      ―sΒ'*         then return a pattern "s" (a square) made with "*"s
           ―TΒ1'*    otherwise, return a pattern "T" (triangle) that is centered and
                     has a scale factor of 1, made with "*"s

Часть 3: инвертирование результата

?='-SZiγγ
?='-S     if S is a "-"
     Ziγ   return γ, inverted across its lines
        γ  otherwise, return γ untouched
Конор О'Брайен
источник