Numerando contornos hierárquicos


18

Escreva um programa que use uma string em que cada linha seja composta pelo caractere 0recuado por algum número de espaços. A linha superior não é recuada e todas as outras linhas serão recuadas no máximo por mais um espaço do que a linha imediatamente antes dela.

Nenhuma linha terá espaços à direita, mas você pode opcionalmente assumir que há uma nova linha à direita.

Por exemplo, a entrada pode ser algo como isto:

0
 0
  0
  0
 0
0
 0
 0
 0
  0
0
 0
  0
  0

Sua tarefa é numerá-la como um esboço hierárquico , usando números inteiros positivos crescentes como cabeçalhos de linha. Esta seria a saída para o exemplo:

1
 1
  1
  2
 2
2
 1
 2
 3
  1
3
 1
  1
  2

Observe como todo nível de indentação hierárquica tem seu próprio conjunto de números crescentes, mesmo que eles subam apenas um.

Na saída, não deve haver espaços à direita, mas opcionalmente pode haver uma nova linha à direita.

Escreva um programa completo que aceite a string de entrada via stdin ou linha de comando ou escreva uma função que aceite a string como argumento. Imprima o resultado ou retorne-o como uma sequência.

O código mais curto em bytes vence.

Exemplos

Se a sequência vazia for inserida, a sequência vazia deverá ser gerada.

O próximo exemplo mais trivial é a entrada

0

que deve se tornar

1

Exemplo grande - Entrada:

0
 0
  0
 0
  0
 0
  0
  0
   0
   0
    0
     0
     0
     0
     0
    0
   0
    0
    0
  0
0
 0
  0
 0
  0
  0
  0
  0
  0
  0
  0
  0
  0
  0
  0
   0
    0
     0
  0
   0
0
0
0
 0
  0
   0
    0
     0
      0
      0
     0
    0
   0
  0
 0
  0
  0
   0
   0
0
0

Resultado:

1
 1
  1
 2
  1
 3
  1
  2
   1
   2
    1
     1
     2
     3
     4
    2
   3
    1
    2
  3
2
 1
  1
 2
  1
  2
  3
  4
  5
  6
  7
  8
  9
  10
  11
   1
    1
     1
  12
   1
3
4
5
 1
  1
   1
    1
     1
      1
      2
     2
    2
   2
  2
 2
  1
  2
   1
   2
6
7

Respostas:


2

Pitão, 18 bytes

V.z+PNhX0=Y>lN+0Y1

Esta é uma tradução exata da resposta do @ Sp3000 . Eu tentei muitas abordagens e variações diferentes, mas não consegui reduzi-lo, por isso estou marcando essa CW.

Demonstração.


8

Python 2, 77

S={'0':0}
for w in input().split('\n'):S[w]+=1;S[' '+w]=0;print w[:-1]+`S[w]`

Como a resposta do Sp3000 , mas com um dicionário. O dict Sarmazena o número atual para cada nível de aninhamento '0', ' 0', ' 0'e assim por diante. Para cada linha na entrada, aumente o nível de aninhamento correspondente e redefina o nível de aninhamento um mais alto para 0.


6

Python 2, 86 85 81 bytes

S=[]
for r in input().split("\n"):S=([0]+S)[-len(r):];S[0]+=1;print r[:-1]+`S[0]`

(-5 bytes graças a @xnor)

Recebe entrada como uma string via STDIN, por exemplo

'0\n 0\n  0\n  0\n 0\n0\n 0\n 0\n 0\n  0\n0\n 0\n  0\n  0'

Como alternativa, aqui está uma função para 5 bytes extras:

def f(I,S=[]):
 for r in I.split("\n"):S=([0]+S)[-len(r):];S[0]+=1;print r[:-1]+`S[0]`

Eu descobri que você pode salvar alguns caracteres, tendo em cada linha como uma série de espaços para que você pode imprimir esses espaços diretamenteS=[]\nfor w in input()[:-1].split('0\n'):S=([0]+S)[~len(w):];S[0]+=1;print w+`S[0]`
xnor

Na verdade, é um pouco mais curto para tomar a linha diretamente: S=[]\nfor w in input().split('\n'):S=([0]+S)[-len(w):];S[0]+=1;print w[:-1]+`S[0]` .
Xnor

@xnor Obrigado mais uma vez - que é muito mais simples :)
SP3000

4

CJam, 25 bytes

LqN/{0+I,<))_IW@toNo+}fI;

Como minha resposta em Python , isso usa uma matriz para armazenar qual número cada nível de indentação tem. Uma diferença, no entanto, é que isso usa t(conjunto de matrizes) para substituir o 0 em cada linha pelo número que queremos.

Experimente online .


3

JavaScript ES6, 83 81 bytes

f=(z,a=[])=>z.replace(/ *0/g,e=>e.replace(0,a.fill(0,l=e.length)[--l]=a[l]+1||1))

Isso usa uma matriz que mantém o número atual para cada nível de indentação. Tudo o que passou nesse nível é redefinido para 0 usando fill(). EDIT: 2 bytes salvos graças à dica do vihan1086.

O snippet de pilha abaixo pode ser usado para teste porque é um pouco desmantelado e usa a sintaxe ES5 com melhor suporte. A segunda função é um polyfill, fill()pois não há uma maneira curta de fazê-lo sem o ES6.

f=function(z){
  a=[]
  return z.replace(/ *0/g,function(e){
    return e.replace(0,a.fill(0,l=e.length)[--l]=a[l]+1||1)
  })
}

if(!Array.prototype.fill){
  Array.prototype.fill = function(val, start){
    var res = this;
    for(var i = start; i<this.length; i++){
      res[i] = val;
    }
    return res;
  };
}

run=function(){document.getElementById('output').innerText=f(document.getElementById('input').value)};document.getElementById('run').onclick=run;run()
<textarea id="input" rows="15" cols="10">
0
 0
  0
  0
 0
0
 0
 0
 0
  0
0
 0
  0
  0</textarea>
<pre id="output" style="display:inline-block; vertical-align:top; margin:0"></pre><br />
<button id="run">Run</button>


1

Python - 191

def p(s,i,v,n=1):
    while i<len(s)and s[i]and'0'not in s[i][:v]:
        if s[i][v]=='0':s[i]=' '*v+str(n);n+=1;i+=1
        else:i=p(s,i,v+1)
    return(s,i)[v!=0]
z=lambda r:'\n'.join(p(r.split('\n'),0,0))

A função é z.


0

Pip -rn , 31 27 bytes

{Wl#<alPU0l@>:-#aaR0++@l}Mg

Entrada de stdin. Experimente online!

Explicação

                             g is list of lines of stdin (-r flag); l is []
                             Note that l is a global variable
{                       }Mg  Map this function to each a in g:
 Wl#<a                        While l is less in length than a:
      lPU0                     Push a 0 to (the front of) l
                              (This handles increasing the indent)
          l@>:                Slice and assign back to l...
              -#a              ... its last len(a) elements
                              (This handles decreasing the indent)
                 aR0          In a, replace 0 with
                      @l       the first element of l
                    ++         incremented in-place
                              The function returns the above expression
                             The resulting list from map is printed, newline-separated
                              (-n flag)
Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.