Piega una stringa in un triangolo


22

Data una stringa la cui lunghezza è divisibile per 4, crea un triangolo come mostrato di seguito.

Se la stringa è abcdefghijkl, il triangolo sarebbe:

   a
  b l
 c   k
defghij

Se la stringa è iamastringwithalengthdivisiblebyfour, il triangolo sarebbe:

         i
        a r
       m   u
      a     o
     s       f
    t         y
   r           b
  i             e
 n               l
gwithalengthdivisib

Se la stringa è thisrepresentationisnotatriangle, il triangolo sarebbe:

        t
       h e
      i   l
     s     g
    r       n
   e         a
  p           i
 r             r
esentationisnotat

Gli appunti

  • La stringa sarà composta solo da caratteri da aa z.
  • Gli spazi bianchi e le righe iniziali / finali sono consentiti purché la forma non sia spezzata.
  • È consentito un elenco di stringhe come output.

Questo è . Vince la risposta più breve in byte. Si applicano scappatoie standard .

Risposte:


7

Carbone , 25 22 21 byte

≔÷Lθ⁴λ↙…θλ→✂θλ±λ↖✂θ±λ

Provalo online! Il collegamento è alla versione dettagliata del codice. Basta tagliare la stringa in tre parti e stamparle nelle direzioni appropriate. Modifica: 3 byte salvati utilizzando divisione e divisione di numeri interi. Ho salvato un ulteriore byte usando CycleChopinvece che Sliceper la testa della stringa. Modifica: il carbone ora supporta il disegno di testo arbitrario lungo il bordo di un poligono, semplificando il codice a 12 byte:

GH↙→→↖⊕÷Lθ⁴θ

Provalo online! Il collegamento è alla versione dettagliata del codice.


Cosa fanno gli s?
Erik the Outgolfer,

@EriktheOutgolfer Questo è il nuovo operatore Slice.
Neil,

: | Oops intendeva fare in modo che PolygonHollow lo facesse, GH↙→→↖⊕÷Lθ⁴θfunzionerà la prossima volta che spingerò Charcoal
solo ASCII il

6

05AB1E , 23 byte

ćsIg4÷GćsÁćsŠN·<ú«s}».C

Provalo online!

Spiegazione

ć                        # extract head of input
 s                       # swap the remaining string to top of stack
  Ig4÷G                  # for N in [1...len(input)/4-1] do:
       ć                 # extract head
        sÁ               # swap remaining string to top of stack and rotate right
          ć              # extract head
           sŠ            # reorder stack as tail, head, remaining
             N·<ú        # prepend N-1 spaces to tail
                 «s      # concatenate with head and swap remaining string to top
                   }     # end loop
                    ».C  # join by newlines and center

6

JavaScript (ES6), 119 117 108 105 byte

s=>(l=s.length/4,S=' ',g=([c,...s],p)=>S.repeat(l)+c+(l--?p+s.pop()+`
`+g(s,p?p+S+S:S):s.join``))(s+S,'')

Formattato e commentato

s => (                            // given the input string s:
  l = s.length / 4,               // l = length of side edge - 1
  S = ' ',                        // S = space (defining S costs 6 bytes but saves 7)
  g = (                           // g = recursive function which takes:
       [c,                        //   - c = next character
           ...s],                 //   - s = array of remaining characters
                  p) =>           //   - p = middle padding string
    S.repeat(l) + c + (           // append left padding + left character
      l-- ?                       // if side edges are not complete:
        p + s.pop() + '\n' +      //   append middle padding + right character + Line Feed
        g(s, p ? p + S + S : S)   //   and do a recursive call with updated middle padding
      :                           // else:
        s.join``                  //   append all remaining characters and stop recursion
    )                             //   (this is the bottom edge)
  )(s + S, '')                    // initial call to g()

Casi test


4

C #, 260 byte

namespace System{using static Console;class P{static void Main(){var d=ReadLine();int e=d.Length/4,x=e,y=0,g=0,i=0;Action<int,int>a=(p,q)=>{SetCursorPosition(p,q);Write(d[g++]);};for(;i<e;i++)a(x--,y++);for(i=0;i<e*2;i++)a(x++,y);for(i=0;i<e;i++)a(x--,y--);}}}

Volevo davvero usare SetCursorPosition.

Ungolfed:

namespace System {
    using static Console;

    class P {
        static void Main() {
            var d = ReadLine();
            int e = d.Length / 4, x = e, y = 0, g = 0, i = 0;
            Action<int, int> a = (p, q) => { SetCursorPosition(p, q); Write(d[g++]); };
            for (; i < e; i++)
                a(x--, y++);
            for (i = 0; i < e * 2; i++)
                a(x++, y);
            for (i = 0; i < e; i++)
                a(x--, y--);
        }
    }
}

Perdonate la mia ignoranza, ma qual è lo scopo dell'azione nella vostra soluzione? È solo meno byte di una funzione nulla?
confuso e

1
@confusedandamused Sono abituato a scrivere risposte a singola funzione, quindi non ho nemmeno considerato di mettere la funzione normalmente, ma sarà più breve.
Liefde:

3

Mathematica, 164 byte

(b=Length[c=Characters@#];k=Column[#,Alignment->Center]&;T=Table;k@{#&@@c,k@T[""<>{c[[i+2]],T[" ",2i+1],c[[-i-1]]},{i,0,(a=b/4)-2}],""<>T[c[[i]],{i,a+1,b/2+1+a}]})&


ingresso

[ "Iamastringwithalengthdivisiblebyfour"]


Sappiamo tutti che [[1]]può essere sostituito con #&@@.
user202729,

1
siete tutti dolcetti così intelligenti!
J42161217


Quando ti ritrovi a fare @(...), fai [...]invece invece. E non ho ancora testato, ma probabilmente puoi salvare un altro byte dando Columnun nome (o forse anche per Column[#,Alignment->Center]&evitarlo q) e quindi inserendo tutte le restanti variabili nel primo argomento dell'esterno Column(per salvare le parentesi circostanti).
Martin Ender,

3

Python 3 , 120 byte

Primo golf, ho pensato che avrei potuto imparare un po 'di Python lungo la strada.

a=input()
l=len(a)//4
print(l*" "+a[0])
for i in range(1,l):print((l-i)*" "+a[i]+(2*i-1)*" "+a[4*l-i])
print(a[l:3*l+1])

Provalo online!

Spiegazione:

Il primo carattere viene stampato da solo dopo gli len(a)//4spazi, quindi ivengono stampati il primo e l'ultimo carattere a partire dal secondo, separati da 2*i - 1spazi.

Infine, viene stampata la sottostringa rimanente.


Benvenuti in PPCG! Puoi imparare da questa soluzione .
Leaky Nun,

Un possibile golf qui è quello di dichiarare p=print, e quindi semplicemente usare pper i tre printche usi.
FlipTack,

Inoltre, poiché la lunghezza della stringa è sempre divisibile per quattro, //(divisione del pavimento) può essere sostituita con /.
FlipTack,

A proposito, il codice che hai collegato per provare online non è lo stesso del codice nella tua risposta.
FlipTack il

3

GNU sed , 178 158 132 + 1 = 133 byte

+1 byte per -rflag.

s/(.)(.*)(.)/ \1\n\2;\3/
:
s/( *)(.\n.)(.*)(...);(.*)(.)/\1\2\1  \6\n\3;\4\5/m
t
:A
s/(.*\n)( *)(.*);/ \2;\1\2\3/m
tA
s/. (.)$/\1/gm

Provalo online!

Spiegazione

Nelle revisioni precedenti ho usato molti byte relativi a matematica, casi speciali e pulizia, anche se intuitivamente ero sicuro che potevano essere evitati. Da allora sono riuscito a farlo, principalmente.

Supponiamo di avere l'input abcdEFGHIJKLMnop. Le lettere EFGHIJKLMsaranno la parte inferiore del triangolo, quindi le ho scritte in maiuscolo come aiuto visivo.

Per prima cosa prepariamo l'input mettendo il primo carattere su una propria riga (preceduto da uno spazio) e inserendo un cursore ( ;) prima dell'ultimo carattere:

s/(.)(.*)(.)/ \1\n\2;\3/

Ora abbiamo:

 a
bcdEFGHIJKLMno;p

Ora, in un ciclo, faremo alcune cose sull'ultima riga: 1. Copia gli spazi dalla riga precedente e inseriscili dopo il primo carattere, più due; 2. Sposta l'ultimo carattere a destra dopo gli spazi, seguito da una nuova riga; e 3. Spostare il cursore di tre caratteri a sinistra.

:
  s/( *)(.\n.)(.*)(...);(.*)(.)/\1\2\1  \6\n\3;\4\5/m
  t

Ecco il risultato di ogni iterazione:

 a
b   p
cdEFGHIJKL;Mno

 a
b   p
c     o
dEFGHI;JKLMn

 a
b   p
c     o
d       n
EF;GHIJKLM

Puoi vedere la piramide che inizia a prendere forma. Puoi anche vedere a cosa serviva il cursore: in ogni iterazione si spostava di tre caratteri a sinistra e quando non ci sono più tre caratteri alla sua sinistra, interrompe il ciclo, che succede proprio quando abbiamo raggiunto il "fondo" della piramide.

Ora eseguiremo un'operazione simile ma al contrario. In un ciclo, copieremo gli spazi dall'inizio della riga con il cursore all'inizio della riga precedente, più uno, nel processo spostando il cursore su quella riga.

:A
  s/(.*\n)( *)(.*);/ \2;\1\2\3/m
  tA

Ecco un paio di iterazioni e il risultato finale:

 a
b   p
c     o
 ;d       n
EFGHIJKLM

 a
b   p
  ;c     o
 d       n
EFGHIJKLM

...

    ; a
   b   p
  c     o
 d       n
EFGHIJKLM

Ora abbiamo finito tutti, ad eccezione di alcuni personaggi extra: A ;e spazio extra sulla prima riga e due spazi nel "mezzo" della piramide sulle tre righe successive. Una semplice sostituzione si libera di loro:

s/. (.)$/\1/gm

Tutto fatto!

    a
   b p
  c   o
 d     n
EFGHIJKLM


2

Python 2 , 100 97 96 byte

  • Jacoblaw ha salvato 1 byte: la divisione intera non è necessaria
a=input()+" "
k=j=len(a)/4
while j:print j*" "+a[0]+(2*(k-j)-1)*" "+a[-1];a=a[1:-1];j-=1
print a

Provalo online!

Spiegazione:

Una cosa intelligente che ho fatto qui è riempire l'input con uno spazio alla fine, in modo che il primo carattere si accoppi con esso e questo possa essere inserito nel loop (e poiché sono ammessi gli spazi bianchi finali)

abcdefghijkl[space]   
To print [0] [-1]            Output=>[spaces]a[another_calculated_spaces(=0 here)][space]
Strip at both ends(a[1:-1])  
bcdefghijkl                
To print [0] [-1]            Output=>[spaces]b[another_calculated_spaces]l
Strip at both ends(a[1:-1])
and so on.

Il numero di loop da seguire è associato len(word)//4. Nel passaggio finale, viene stampata l'intera stringa rimanente (costituisce la base del triangolo). Gli spazi seguono un modello semplice; la prima serie di spazi continua a diminuire di 1, mentre la seconda serie di spazi aumenta di 2.


1
Riesci a radere via un byte non facendo divisione intera? Dal momento che asarà sempre un multiplo di 4. //->/
jacoblaw

Grazie, sono sorpreso che non stia generando
officialaimm,

1
Questo perché in Python 2, la divisione è intera per impostazione predefinita. È stato forgiato in Python 3.
CalculatorFeline

2

C 225 byte

p(c){putchar(c);}S(n){while(n--)p(' ');}main(int c,char**v){int i= strlen(v[1]),n=i/4,r;char*s=v[1],*e=&s[i-1];S(n);p(*s++);p('\n');for (r=1;r<n;r++){S(n-r);p(*s++);S(2*r-1);p(*e--);p('\n');}e++;while (s!=e)p(*s++);p('\n');}

ha spiegato

p(c){putchar(c);}        // p is alias for putchar
S(n){while(n--)p(' ');}  // S prints n spaces
main(int c,char**v){
    int i= strlen(v[1]), // counter
        n=i/4,           // num rows in figure - 1
        r;               // current row 
    char*s=v[1],         // start char
        *e=&s[i-1];      // end char
    S(n);p(*s++);p('\n');// print first row
    for (r=1;r<n;r++){ 
        S(n-r);p(*s++);S(2*r-1);p(*e--);p('\n'); // print middle rows
    }
    e++;while (s!=e)p(*s++);p('\n'); // print last row
}

2

C #, 172 byte

int i=0,n=s.Length;var p="";p=new string(' ',n/4)+s[i]+"\r\n";for(i=1;i<n/4;i++){p+=new string(' ',n/4-i)+s[i]+new string(' ',i*2-1)+s[n-i]+"\r\n";}p+=s.Substring(i,n/2+1);

Provalo online!


1

Ottava, 87 byte

@(s,x=(n=nnz(s))/4)[[' ';flip(diag(s(1:x))')]' [' ';diag(s(n:-1:n-x+2))];s(x+1:n-x+1)];

* In una macchina Windows il codice sopra riportato produce il risultato corretto, tuttavia in tio ho aggiunto del codice per correggerlo.

Spiegazione:

[' ';flip(diag(s(1:x))')]'        %left side
[' ';diag(s(n:-1:n-x+2))]         %right side
s(x+1:n-x+1)                      %bottom side

Provalo online!


1

Haskell , 136 byte

i#x=x<$[1..i]
f s|let h=div l 4;l=length s=unlines$[(h-i)#' '++(s!!i):(2*i-1)#' '++[(s++" ")!!(l-i)]|i<-[0..h-1]]++[drop h$take(l-h+1)s]

Provalo online!


1

PHP> = 7,1, 122 byte

for(;$i*2<$w=strlen($a=$argn)/2;$e=$a[-++$i])echo str_pad(str_pad($a[$i],$i*2).$e,$w+1," ",2),"
";echo substr($a,$i,$w+1);

PHP Sandbox online

PHP> = 7,1, 124 byte

for(;$i*2<$w=strlen($a=$argn)/2;$e=$a[-++$i],$s.=$s?"  ":" ")echo str_pad("",$w/2-$i)."$a[$i]$s$e
";echo substr($a,$i,$w+1);

PHP Sandbox online


1

AWK , 129 byte

{n=split($0,a,"")
printf"%"(w=n/4+1)"s\n",a[++i]
for(;++i<w;)printf"%"(w-i+1)"s%"2*i-2"s\n",a[i],a[n-i+2]
$0=substr($0,i,i+w-1)}1

Provalo online!

Dovrei pensare che questo potrebbe essere giocato un po 'di più, semplicemente non vedendolo.


1

Retina , 99 byte

^(.)(?=(....)+)
$#2$*  $1¶$#2$* 
( ( *).)(.*)(.)$
$1 $4¶$2$3
+`(( +).¶ ( *).)(.*)(.)$
$1$2  $5¶$3$4

Provalo online! Spiegazione: I primi due stadi generano le prime due righe, ma successivamente non è necessario alcun involucro speciale e ogni riga successiva può essere generata automaticamente:

thisrepresentationisnotatriangle

        t
       hisrepresentationisnotatriangle

        t
       h e
      isrepresentationisnotatriangl

        t
       h e
      i   l
     srepresentationisnotatriang

...

        t
       h e
      i   l
     s     g
    r       n
   e         a
  p           i
 r             r
esentationisnotat

1

Java 8, 213 byte

s->{int n=s.length()/4,i;String r=s(n)+s.charAt(0)+"\n";for(i=1;i<n;r+=s(n-i)+s.charAt(i)+s(i*2-1)+s.charAt(n*4-i++)+"\n");return r+s.substring(i,n*2+i+1);}String s(int n){String r="";for(;n-->0;r+=" ");return r;}

Spiegazione:

Provalo qui.

s->{                           // Method (1) with String parameter and String return-type
  int n=s.length()/4,          //  The length of the input divided by 4
      i;                       //  And an index-integer
  String r=                    //  Result-String which starts as:
           s(n)                //   Trailing spaces
           +s.charAt(0)+"\n";  //   + the first character and a new-line
  for(i=1;i<n;                 //  Loop from `1` to `n`
      r+=                      //   And append the result-String with:
         s(n-i)                //    Trailing spaces
         +s.charAt(i)          //    + the character of the left diagonal line
         +s(i*2-1)             //    + center spaces
         +s.charAt(n*4-i++)    //    + the character of the right diagonal line
         +"\n"                 //    + a new-line
  );                           //  End of loop
  return r                     //  Return the result-String
         +s.substring(i,n*2+i+1);
                               //   + the bottom part of the triangle
}                              // End of method (1)

String s(int n){               // Method (2) with integer parameter and String return-type
  String r="";                 //  Result-String
  for(;n-->0;r+=" ");          //  Append the result-String with `n` spaces
  return r;                    //  Return the result-String
}                              // End of method (2)

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.