모래 시계 그리기


32

프로그래밍 101의 작업에서 다시 한 번 영감을 얻은 또 다른 과제가 있습니다.

입력:

  • 양의 정수 n >= 3. (이상해야한다)

산출:

  • n첫 번째 줄에는 n별표가 있고 모든 새 줄에는 이전 줄보다 두 개의 별표가 있습니다. 별표 1 개를 칠 때까지 거기에서 모든 새로운 줄에는 별표로 돌아갈 때까지 줄보다 두 개의 별표가 있습니다 n. 스페이스 나 스페이스와 같은 것은 별표를 정렬하는 데 사용되어 실제로 모래 시계처럼 보입니다.

일반적인 규칙:

  • 후행 줄 바꿈은 허용되지만 사용할 필요는 없습니다.
  • 들여 쓰기는 필수입니다.
  • 이것은 코드 골프이므로 바이트 단위의 최단 답변이 이깁니다.
  • 이 과정은 C ++로 진행되므로 C ++로 솔루션을보고 싶어합니다.

테스트 사례 (n = 5) :

*****
 ***
  *
 ***
*****

이에 따라 편집, 감사 :-)
Sickboy


3
@Oliver OP "별표 삼각형 그리기"라고 것을 고려할 때 ,이 과제를 복제라고 부르는 것이 공정하다는 것은 전적으로 확신 할 수 없습니다. 그래도 분명히 관련이 있습니다.
Sherlock9

19
여기에있는 모든 사람이 전체 컨텍스트를 알고있는 것은 아니기 때문에 OP는 원래 "별표 삼각형 그리기"를 게시하고이 과제를 추가 과제로 편집했습니다. 우리는 그들에게 그 부분을 제거하고 다른 도전을하도록 지시했습니다. 이 도전은 중복 이 아닙니다 . OP는 많은 대표 사용자를 수행하고 있으며 일부 개조도 권장합니다.
DJMcMayhem

2
@JDL : 아니요. 왜 그런가요? 아, 이제 네가 네모의 의미를 이해 했어 ... :-D
Sickboy

답변:


20

, 6 바이트

G↘←↗N*

간단하다. 폴리 그리기 G를 의에 *입력 찍은 측면 길이와 N의 측면이 아래쪽 및 오른쪽으로 수평 왼쪽 위로 및 우측 이동 엄버 :

*   *
 * *
  *
 * *
*****

그런 다음 아웃 라인을 자동 완성하고 채 웁니다.

*****
 ***
  *
 ***
*****

온라인으로 사용해보십시오!


하아, 꽤 멍청이입니다!
CT14.IT 2016 년

6
이 언어는 매우 흥미 롭습니다! 나는 지금부터 이것을 매우 자세히 볼 것이다 : p.
Adnan

전에이 언어를 보지 못했지만 ... 흥미로워 요! 어떻게 든 젤리와 결합하면 얻을 수 있을지 궁금합니다.
Esolanging Fruit

12

파이썬 2, 57 바이트

N=n=input()
exec"print('*'*max(n,2-n)).center(N);n-=2;"*n

전체 프로그램. 한 줄씩 이동하여 중앙에 올바른 수의 별표를 인쇄합니다.

재귀 함수는 더 길었습니다 (67 바이트).

f=lambda n,p='':p+n*'*'+'\n'+(1%n*' 'and f(n-2,p+' ')+p+n*'*'+'\n')

또는

f=lambda n,p='':1/n*(p+'*\n')or f(n-2,p+' ').join([p+n*'*'+'\n']*2)

나는 대체하려고 제안하고 싶었다 max와 함께 abs,하지만 내가 가진 모든는 abs(n-1)+1추가 괄호가 필요하기 때문에 더 인
njzk2

@ njzk2을 수행하여 파 렌스를자를 수 '*'*-~abs(n-1)있지만 길이는 '*'*max(n,2-n)입니다.
xnor

거기에 def f(n,s=''):r=s+'*'*n+'\n';return 1/n*r or r+f(n-2,s+' ')+r61 바이트,하지만 여전히 이상입니다. 선두 줄 바꿈 def f(n,s='\n'):r=s+'*'*n;return 1/n*r or r+f(n-2,s+' ')+r이 있어도 여전히 58 바이트입니다.
Dennis

에 관하여 저를 가르치는 일 center. 지금까지 그 존재를 알지 못했습니다.
DLosc

11

V , 12 바이트

Àé*hòl3Äjxx>

온라인으로 사용해보십시오!

V의 2D 특성의 장점을 과시하기 때문에 이와 같은 과제를 좋아합니다. 설명. 먼저, n 개의 별표 문자열을 만들어야합니다 . 그래서 우리는 이렇게합니다 :

À           " Arg1 times:
 é          " Insert the following single character:
  *         " '*'

참고로, 이것은 @ai*<esc>vim과 직접 동일 하며 레지스터 @a는 "arg1"로 사전 초기화됩니다. 숫자 입력이 훨씬 편리합니다.

그런 다음로 캐릭터를 오른쪽으로 이동합니다 h. 재미있는 부분은 다음과 같습니다.

ò           " Until an error is thrown:
 l          "   Move one character to the right. This will throw an error on anyline with only one asterisk in it
  3Ä        "   Make 3 copies of this line
    j       "   Move down one line
     xx     "   Delete two characters
       >    "   Indent this line once.

기술적으로이 마지막 부분은

òl3Äjxx>>ò

들여 쓰기 명령이 실제로 있기 때문 >>입니다. V는 불완전한 명령이 현재 행에 적용되는 것으로 가정하고, ò루프를 위해 두 번째 문자를 암시 적으로 채 웁니다 .


10

C ++ 메타 템플릿, 186 바이트

내 C 답변 의 명시 적 공식으로 Metatemplates가 경쟁하고 있습니다!

template<int N,int X=N*N+N-1>struct H{enum{I=X/(N+1)-N/2,J=X%(N+1)-N/2-1};S s{(J==-N/2-1?'\n':((I>=J&I>=-J)|(I<=J&I<=-J)?'*':' '))+H<N,X-1>().s};};template<int N>struct H<N,-1>{S s="";};

언 골프 드 :

using S=std::string;

template <int N, int X=N*N+N-1>
struct H{
 enum{I=X/(N+1)-N/2,J=X%(N+1)-N/2-1};
 S s{(J==-N/2-1 ? '\n' : ( (I>=J&I>=-J)|(I<=J&I<=-J) ?'*':' '))+H<N,X-1>().s};
};

template <int N> struct H<N,-1> {S s="";}; 

용법:

std::cout << H<5>().s;

비경쟁

재미를 위해서만 :

//T: Tuple of chars
template <char C, char...Tail> struct T { S r=S(1,C)+T<Tail...>().r; };

//specialization for single char
template <char C> struct T<C> { S r=S(1,C); };

//M: Repeated char
template <int N, char C> struct M { S r=S(N,C); };

//U: concatenates T and M
template <class Head, class...Tail> struct U { S r=Head().r+U<Tail...>().r; };

//specialization for Tail=M
template <int N, char C> struct U<M<N,C>> { S r{M<N,C>().r}; };

//specialization for Tail=T
template <char...C> struct U<T<C...>> { S r=T<C...>().r; };

//finally the Hourglass
template <int N, int I=0> struct H {
 S s=U<
       M<I,' '>,
       M<N,'*'>,
       T<'\n'>
      >().r;
 S r{s + H<N-2,I+1>().r + s};
};

//specialization for recursion end
template <int I> struct H<1,I> {
 S r=U<
       M<I,' '>,
       T<'*','\n'>
      >().r;
};

용법:

std::cout << H<5>().r;

2
C ++의 가장 긴 부분으로 PHP를 꺾은 +1
matsjoyce

7

PowerShell v2 +, 54 바이트

param($n)$n..1+2..$n|?{$_%2}|%{" "*(($n-$_)/2)+"*"*$_}

입력 걸린다 $n(홀수을 보장)을 두 범위를 구성 $n..1하고 2..$n그 다음 사용하고 그들을 함께 연결해 Where-Object만 이상한 사람을 선택 |?{$_%2}. 그것들은 루프로 공급됩니다. 각 반복마다 적절한 수의 공간을 구성하고 적절한 수의 별표로 문자열 연결합니다. 이러한 문자열은 파이프 라인에 남아 Write-Output있으며 프로그램 완료시 암시 적 삽입 개행을 통해 출력됩니다 .

PS C:\Tools\Scripts\golfing> 3,5,7|%{.\draw-an-hourglass.ps1 $_;""}
***
 *
***

*****
 ***
  *
 ***
*****

*******
 *****
  ***
   *
  ***
 *****
*******

7

파이썬, 78 바이트

들여 쓰기 만하면됩니다.

f=lambda n,i=0:n>1and' '*i+'*'*n+'\n'+f(n-2,i+1)+' '*i+'*'*n+'\n'or' '*i+'*\n'

용법:

print f(5)

6

C, 114 109 바이트

i,j;k(n){for(i=-n/2;i<=n/2;++i)for(j=-n/2;j<=n/2+1;++j)putchar(j==n/2+1?10:(i>=j&i>=-j)|(i<=j&i<=-j)?42:32);}

언 골프 :

i,j;
k(n){
 for(i=-n/2;i<=n/2;++i)
  for(j=-n/2;j<=n/2+1;++j)
   putchar(j==n/2+1?10:(i>=j&i>=-j)|(i<=j&i<=-j)?42:32);
}

이전 재귀 솔루션 :

p(a,c){while(a--)putchar(c);}
f(n,i){p(i,32);p(n,42);p(1,10);}
g(n,i){if(n>1)f(n,i),g(n-2,i+1);f(n,i);}
h(n){g(n,0);}

5

자바 스크립트 (ES6), 66 바이트

f=(n,s="*".repeat(n))=>n>1?s+`
`+f(n-2).replace(/^/gm," ")+`
`+s:s

여기서 아이디어는 이전에서 각 모래 시계를 생성하는 것입니다. 모든 줄의 시작 부분에 공백을 추가하고 n별표를 추가하고 추가하십시오 .


4

05AB1E , 21 20 19 17 바이트

카루소 컴퓨팅 덕분에 2 바이트 절약

;ƒ'*¹N·-×Nð×ì})û»

온라인으로 사용해보십시오!

설명

;ƒ                   # for N in [0 ... floor(input/2)+1]
  '*                 # push an asterisk
    ¹N·-×            # repeat the asterisk input-N*2 times
         Nð×ì        # prepend N spaces
             }       # end loop
              )      # wrap stack in a list
               û     # palendromize
                »    # join with newlines

Ir"*"×.pRû-이 멀리있어, 내가 얼마나 멀리 떨어져 있는지 깨달았을 때 손바닥으로 얼굴을 가리고, 당신이 대답을 보았고,이 예제를 사용 하여이 언어로 반복을 배우려고합니다. 감사!
매직 문어 Urn

4
실제로 한 번만 도울 수 있습니다 ;ƒ'*¹N·-×Nð×ì})û». 새로운 palindromize 명령을 사용하십시오. -2 바이트
매직 문어 Urn

@carusocomputing : 감사합니다! 나는 palendromize 명령에 대해 몰랐습니다 (문서를 새로 고치지 않았습니다). 매우 유용한. :)
Emigna

레거시에서도 9 바이트 . 난 꽤 내장 매크로 있는지 있지만 ÅÉ.c아마 사용할 수 없었던 아직 시간이 기록했다. :)
Kevin Cruijssen

4

MATL , 12 바이트

Q2/Zv&<~42*c

온라인으로 사용해보십시오!

설명

이 차종은의 사용 최근에 추가 된 대칭 범위 기능.

Q     % Input n implicitly. Add 1
      % STACK: 6
2/    % Divide by 2
      % STACK: 3
Zv    % Symmetric range
      % STACK: [1 2 3 2 1]
&<~   % Matrix of all pairwise "greater than or or equal to" comparisons
      % STACK: [1 1 1 1 1
                0 1 1 1 0
                0 0 1 0 0
                0 1 1 1 0
                1 1 1 1 1]
42*   % Multiply by 42 (ASCII code of '*')
      % STACK: [42 42 42 42 42
                 0 42 42 42  0
                 0  0 42  0  0
                 0 42 42 42  0
                42 42 42 42 42]
c     % Convert to char. Implicitly display, with char 0 shown as space
      % STACK: ['*****'
                ' *** '
                '  *  '
                ' *** '
                '*****']

좋은! 멋진 기능입니다. 이것은 내 V 답변에 가까운 유일한 답변이므로 이제 1-2 바이트를 제거하는 데 집착합니다. : D
DJMcMayhem

@DJMcMayhem Heh, 나는 이것에 대한 바이트 수를 줄일 수 있다고 생각하지 않습니다
Luis Mendo

그래, 나도 할 수 없을 것 같아 아마 하하하 ... 어쨌든 몇 분의 4 바이트 젤리 해답이 있습니다
DJMcMayhem

4

PHP, 95 바이트

for($c=str_pad,$m=$n=$argv[1];$n<=$m;$n+=$d=$d>0||$n<2?2:-2)echo$c($c('',$n,'*'),$m,' ',2)."
";

배열에 행을 저장하고 모든 것을 출력하는 대신 for 루프는 1까지 내려간 다음 원래 숫자로 돌아갑니다.


3

C ++ 11, 93 바이트

#include<string>
using S=std::string;S f(int n,int i=0){S s=S(i,32)+S(n,42)+'\n';return n>1?s+f(n-2,i+1)+s:s;}

약간 골퍼되지 않음 :

std::string f(int n,int i=0){
 auto s=std::string(i,' ') + std::string(n,'*') + '\n';
 return n>1 ? s+f(n-2,i+1)+s : s;
}

용법:

std::cout << f(5);

좋은! 1 바이트 ASCII를 가정하고 대체하여 저장할 수 있습니다 '\n'으로 10:
쿠엔틴


3

R, 77 바이트

M=matrix(" ",n<-scan(),n);for(i in 1:n)M[i:(n-i+1),i]="*";cat(M,sep="",fill=n)

그 다음을 통해 출력한다 문자 매트릭스 작성 cat하여, fill=n반드시 선이 제대로 정렬하고 있습니다. 소자 열 먼저 행렬에 저장된 참고 (즉 처음 두 요소가 M[1,1]M[2,1]아닌 M[1,2]).


3

자바 7, 170165 164 바이트

5 바이트를 절약 한 @Hypino에게 감사합니다.
1 바이트를 절약 한 Kevin에게 감사합니다.

String c(int n,int x){String s,c,t=c=s=" ";int i=0;for(;i++<n;s+="*");for(i=x;i-->=0;c+=" ");for(i=x;i-->0;t+=" ");return(n=n-2)>=0?s+"\n"+c+c(n,++x)+"\n"+t+s:"*";} 

당신은 제거하여 2 바이트를 저장할 수 있습니다 s=에서 s=s+"\n"변경하여 2 개 바이트 return(n=--n-1)return(n=n-2)4 바이트의 총.
Hypino

안녕. 할 수 있습니다 골프 두 부분 : String s="",c="",t="";String s,c,t=s=c="";( -2 바이트 ), 그리고 return(n=n-2)>=0?s+"\n"+c+c(n,++x)+return n-1>0?s+"\n"+c+c(n-2,++x)+( -2 바이트 다시)
케빈 Cruijssen

그러나 @KevinCruijssen 패턴은 변경 후 예상대로되지 않습니다 n=n-2-> n-1>0n은 함수의 다른 인수에 사용해야하기 때문에.
Numberknot

@Numberknot 나는 알고있다, 그러나 나는 또한 변화 nn-2그 부분에. return(n=n-2)>=0 ... n로 변경되는 return n-1>0 ... n-2것은 여전히 ​​짧습니다. 추신 : 바이트를 저장해 주셔서 감사하지만 편집에서 코드를 변경하지 않았습니다. ;)
Kevin Cruijssen

@Numberknot Umm .. 당신은 여전히 ​​내 두 번째 팁을 잊었다. 어쨌든, 여기에 짧은 변형은 다음과 같습니다 String c(int n,int x){String s,c=s="";int i=0;for(;i++<n;s+="*");for(i=x;i-->0;c+=" ");return n>1?s+"\n "+c+c(n-2,x+1)+"\n"+c+s:"*";}포함하지 않는 t( ideone 테스트 - 133 바이트 )
케빈 Cruijssen

3

PHP-95 바이트

$c=2;for($i=$a=$argv[1];$i<=$a;$i-=$c*=$i<2?-1:1)echo str_pad(str_repeat("*",$i),$a," ",2)."
";

대신 실제 줄 바꿈을 사용하여 바이트를 저장했습니다. "\r"


2

Pyth, 22 바이트

j+J.e+*dk*b\*_:1hQ2_PJ

STDIN에 정수를 입력하여 결과를 인쇄하는 프로그램.

온라인으로 사용해보십시오

작동 원리

j+J.e+*dk*b\*_:1hQ2_PJ  Program. Input: Q
              :1hQ2     Range from 1 to Q+1 in steps of 2. Yields [1, 3, 5, ..., Q]
             _          Reverse
   .e                   Enumnerated map with b as elements and k as indices:
      *dk                 k spaces
         *b\*             b asterisks
     +                    Concatenate the spaces and asterisks
  J                     Store in J
                    PJ  All of J except the last element
                   _    Reverse
 +                      Concatenate J and its modified reverse
j                       Join on newlines
                        Implicitly print

2

C, 195191 바이트

조금 더 작아야한다

x,y,i;f(n){for(i=0;i<n;i+=2,puts("")){for(y=n-i;y<n;y+=2,putchar(32));for(x=i;x++<n;putchar(42));}for(i=n-2;~i;i-=2,puts("")){for(y=n-i+2;y<n;y+=2,putchar(32));for(x=i-1;x++<n;putchar(42));}}

우리는 그것을 테스트 할 수 있습니다 여기 ideone에


2

C, 79 바이트

h(m,n,k){for(n=m++,k=n*m;--k;putchar(k%m?abs(k%m-m/2)>abs(k/m-n/2)?32:42:10));}

카운트 다운 변수 k를 행 및 열 인덱스로 분할합니다 . 열 인덱스가 0 (행의 마지막 문자)이면 줄 바꿈 문자 (10)를 출력합니다. 그런 다음 행과 열 인덱스가 중앙 별표 주위에 오도록 조정합니다. 그런 다음 abs(x) < abs(y)공백을 출력하기위한 짧은 조건입니다.


2

루비, 55 54 바이트

f=->n,s=0{puts a=' '*s+?**n;(f[n-2,s+1];puts a)if n>1}

?**n공장; 거기에는 공간이 필요하지 않습니다.
가치 잉크

2

자바 7, 156 바이트

상당히 간단합니다. 와 함께 선 n, 별과 함께 j, 공백 s및로 방향을 추적 d합니다. 나는 보드에 비 재귀 Java 답변을 원했지만 조금 짧아도 아프지 않습니다. :)

String f(int n){String o="";int j=n,s=0,i,d=0;for(;n-->0;o+="\n"){for(i=0;i++<s;)o+=" ";for(i=0;i++<j;)o+="*";d+=j<2?1:0;j+=d<1?-2:2;s+=d<1?1:-1;}return o;}

줄 바꿈으로 :

String f(int n){
    String o="";
    int j=n,s=0,i,d=0;
    for(;n-->0;o+="\n"){
        for(i=0;i++<s;)
            o+=" ";
        for(i=0;i++<j;)
            o+="*";
        d+=j<2?1:0;
        j+=d<1?-2:2;
        s+=d<1?1:-1;
    }
    return o;
}

2

APL, 19 바이트

' *'[1+∘.≤⍨(⊢⌊⌽)⍳⎕]

테스트:

      ' *'[1+∘.≤⍨(⊢⌊⌽)⍳⎕]
⎕:
      5
*****
 *** 
  *  
 *** 
*****

설명:

                 ⎕   ⍝ read number  
                ⍳    ⍝ 1..N
           ( ⌊ )     ⍝ at each position, minimum of
            ⊢        ⍝ 1..N
              ⌽      ⍝ and N..1 (this gives 1..N/2..1)
       ∘.≤⍨          ⍝ outer product with ≤
     1+              ⍝ add 1 to each value
' *'[             ]  ⍝ 1→space, 2→asterisk

1+있는 APL을 제거 하고 사용 하십시오 ⎕IO←0.
Adám

2

하스켈, 84 바이트

f n|l<-div n 2,k<-[-l..l]=putStr$unlines[[" *"!!(fromEnum$abs x<=abs y)|x<-k]|y<-k]

좋은 해결책! 그러나 나는 확신 당신이 필요하지 않습니다 해요 putStr당신은 제거 할 수 fromEnum같은 .
ბიმო



2

PHP ,104 88 바이트

for(;$i++<$argn;$a.='**',$i++>1?$o=$s.$o:1)$o.=$s=str_pad("*$a",$argn,' ',2)."
";echo$o;

온라인으로 사용해보십시오!

이것은이 도전에서 PHP의 최저 점수를이기는 것은 아니지만 너무 버려서 버릴 수는 없습니다.

좋아, 그래서 나는이 도전에서 PHP에 대해 (긴하지 않은) 최저 점수가 되려고 골프를 쳤지 만 여전히 미쳤다는 사실은 바뀌지 않습니다.

$ echo 7|php -nF hour.php
*******
 *****
  ***
   *
  ***
 *****
*******

83? 또한 허, PHP도 마찬가지입니다. 여기서 유용하지는 않습니다.
ASCII 전용

@ASCII 전용 쥐! 해야 할 일이 더있는 것 같습니다! lol
640KB



@ASCII 전용 p, 잘 했어요! 그것은 올바른 접근 방식입니다!
640KB

1

그루비, 66 바이트

{n->((n..1)+(2..n)).each{if(it%2>0){println(("*"*it).center(n))}}}

사용해보십시오 : https://groovyconsole.appspot.com/script/5145735624392704

설명 :

((n..1)+(2..n)) -n으로 역 회색 [n,..,1,..,n]

.each{if(it%2>0){...} -홀수 요소를 반복합니다.

println(("*"*it).center(n)) -n 개의 별을 중심에두고 개행에 각각 인쇄하십시오.


.each코드 블록이 될 수 있습니다 {it%2&&println(("*"*it).center(n))}.
manatwork

1

PHP, 191 바이트

$b=[];for($i=$a=$argv[1]+1;$i>0;$i--){$i--;if($i<=1){$c=str_pad("*",$a," ",2)."\n";break;}$b[]=str_pad(str_repeat("*",$i),$a," ",2)."\n";}echo implode("",$b).$c.implode("",array_reverse($b));

다음과 같이 실행 php -f golf_hourglass.php 15

# php -f golf_hourglass.php 15
***************
 *************
  ***********
   *********
    *******
     *****
      ***
       *
      ***
     *****
    *******
   *********
  ***********
 *************
***************

그 배후의 아이디어는 상단 절반 (싱글 앞 부분 *)을 만든 다음 상단 부분을 두 번 에코하지만 두 번째는 역순으로 에코하는 것입니다.


나는 이것이 더 나은이 작업을 시작 생각for(;$i<$a=$argv[1];$i+=2){$t=str_pad(str_pad("",$i+1,"*"),$a," ",2)."\n";$i?$s.=$t:$r=$t;}echo strrev($s)."\n".$r.$s;
요 르그 Hülsermann을

for(;$i<$a=$argv[1];$i++){$t=str_pad(str_pad("",$i+1+$i%2,"*"),$a," ",2)."\n";$i%2?$s.=$t:$s=$t.$s;}echo$s;이것은 더 낫다
Jörg Hülsermann

6 바이트를 절약하려면 implode ()를 join ()으로 바꿉니다.
Alex Howansky

\n바이트를 저장하려면 실제 줄 바꾸기 로 바꾸십시오.
Alex Howansky

1

파이크, 22 19 바이트

F-ed*ih\**+)2%'X_OX

여기 사용해보십시오!

F          )        -    for i in range(input)
 -                  -        Q-i
  e                 -       floor(^/2)
   d*               -      ^*" "
          +         -     ^+V
     ih             -       i+1
       \**          -      ^*"*"
            2%      -   ^[::2]
              'X_   - splat(^),
                       reversed(^)
                 OX - splat(^[:-1])

1

C, 117 바이트

void p(c,n){while(n--)putchar(c);}void h(n){for(int i=n;i>=-n;i-=i==1?4:2){p(32,(n-abs(i))/2);p(42,abs(i));p(10,1);}}

언 골프

void printNum(c, n) {
  while (n--)
    putchar(c);
}

void hourGlass(n) {
  for (int i = n; i >= -n; i-=i==1?4:2) {
    printNum(32, (n - abs(i)) / 2);
    printNum(42, abs(i));
    printNum(10, 1);
  }
}
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.