Reindent Java / C / C ++ / etc. código

10

Escriba un programa que agregue o elimine espacios en blanco para formatear bien el código. Reglas sobre cómo debería verse el código cuando haya terminado:

  • Ninguna línea debe contener más de uno de {y }.
  • A {siempre debe ser lo último en una línea.
  • A }siempre debe ser lo único en una línea (además del espacio en blanco que viene antes).
  • La cantidad de espacios en blanco delante de cada línea debe ser un múltiplo fijo del recuento de anidamiento actual. (Puede usar cualquier cantidad de sangría que desee, siempre que no cambie).
  • No se debe insertar o eliminar ningún espacio en blanco que no contribuya a satisfacer una de estas reglas.

El recuento de anidamiento para la primera línea es 0. El recuento de anidamiento de cualquier otra línea es el recuento de anidamiento de la línea anterior, más uno si la línea anterior contiene a {, menos uno si la línea actual contiene a }.

{y }dentro de los literales de cadena y los comentarios no cuentan en las reglas anteriores. Un literal de cadena es texto encerrado entre comillas simples o dobles, donde las comillas simples o dobles con un número impar de barras invertidas inmediatamente antes de ellas no se interpretan como el final del literal de cadena. Un comentario es texto encerrado en /*y */, o texto que va desde //el final de la línea. En una línea de marcadores de inicio de comentarios múltiples, solo cuenta el primero. Los comentarios no se analizan dentro de los literales de cadena.

Ejemplos

    main() {printf("Hello!"); // I don't care about the world...
        }

becomes:

main() {
    printf("Hello!"); // I don't care about the world...
}




int main(){
    puts("a");
        puts("b");
}

becomes:

int main(){
    puts("a");
    puts("b");
}


main()
{ printf("{"); /* }
} */
     printf("}//}"); ///*
    }

becomes:

main()
{
    printf("{"); /* }
} */
    printf("}//}"); ///*
}


int test[] = {1, 2, 3};

becomes:

int test[] = {
    1, 2, 3
}
;
tbodt
fuente
Los comentarios no son para discusión extendida; Esta conversación se ha movido al chat .
Dennis

Respuestas:

6

JavaScript (ES6), 376 373 378 393 bytes

Este fue ... todo el desafío ...

Avíseme si hay algún problema con la salida, aunque no pude encontrar nada , no puedo encontrar nada más.

Versión sin golf

Golfé el código mientras lo escribía, así que veamos cómo va esto ...

ETHproductions
fuente
me parece bien
tbodt
Leí el código mientras lo escribía, lo que significa que eres un verdadero golfista ...
Erik the Outgolfer
4

Javascript (ES6), 260 259 bytes

Analiza la entrada carácter por carácter. Utiliza sangría de 4 espacios.

s=>s.replace(/[^]/g,(x,n)=>(p=s[n-1],a=!l&!c&!e,l|x!='/'?a&x=='*'&p=='/'?c=x:!c&!e&x=='"'?(l^=1,x):x==`
`?(i=e=0,x):a&x=='}'?d--&&i?`
`+x:i=x:a&x=='{'?s[i=!++d,n+1]==`
`?x:x+`
`:i?x:x==' '?'':' '.repeat(!c*d*4,i=1)+x:p==x?e=x:!e&p=='*'?(c=0,x):x),d=i=l=c=e=0)

Esto sigue siendo un WIP y básicamente se probó solo con los ejemplos proporcionados. Si encuentra algún error, hágamelo saber en los comentarios.

El estado del analizador está completamente descrito por las siguientes variables:

  • d → profundidad de anidamiento actual
  • i → marca que indica que estamos ubicados 'dentro' del código (es decir, después de los espacios iniciales de la línea)
  • l → cadena de bandera literal
  • c → bloque de bandera de comentario
  • e → indicador de comentario de línea

Versión con sangría obligatoria

s => s.replace(
  /[^]/g,
  (x, n) => (
    p = s[n - 1],
    a = !l & !c & !e,
    l | x != '/' ?
      a & x == '*' & p == '/' ?
        c = x
      :
        !c & !e & x == '"' ?
          (l ^= 1, x)
        :
          x == `\n` ?
            (i = e = 0, x)
          :
            a & x == '}' ?
              d-- && i ? `\n` + x : i = x
            :
              a & x == '{' ?
                s[i = !++d, n + 1] == `\n` ? x : x + `\n`
              :
                i ?
                  x
                :
                  x == ' ' ? '' : ' '.repeat(!c * d * 4, i = 1) + x
    :
      p == x ?
        e = x
      :
        !e & p == '*' ? (c = 0, x) : x
  ),
  d = i = l = c = e = 0
)

Casos de prueba

Arnauld
fuente