La matemática es un hecho. La programación no es


175

En matemáticas, un signo de exclamación a !menudo significa factorial y viene después del argumento.

En la programación, un signo de exclamación a !menudo significa negación y viene antes del argumento.

Para este desafío solo aplicaremos estas operaciones a cero y uno.

Factorial
0! = 1
1! = 1

Negation
!0 = 1
!1 = 0

Tome una cadena de cero o más !, seguido de 0o 1, seguido de cero o más !( /!*[01]!*/).
Por ejemplo, la entrada puede ser !!!0!!!!o !!!1o !0!!o 0!o 1.

Los !'s antes de 0o 1son negaciones y los !' s después son factoriales.

El factorial tiene mayor prioridad que la negación, por lo que los factoriales siempre se aplican primero.
Por ejemplo, !!!0!!!!realmente significa !!!(0!!!!), o mejor aún !(!(!((((0!)!)!)!))).

Salida de la aplicación resultante de todos los factoriales y negaciones. La salida siempre será 0o 1.

Casos de prueba

0 -> 0
1 -> 1
0! -> 1
1! -> 1
!0 -> 1
!1 -> 0
!0! -> 0
!1! -> 0
0!! -> 1
1!! -> 1
!!0 -> 0
!!1 -> 1
!0!! -> 0
!!!1 -> 0
!!!0!!!! -> 0
!!!1!!!! -> 0

El código más corto en bytes gana.


18
Pero 0! = 1 !, entonces, ¿cuál es el punto de manejar múltiples factoriales?
boboquack

30
@boboquack Porque ese es el desafío.
Aficiones de Calvin

11
<? = '1'; ... correcto el 75% del tiempo en php.
aslum

10
Puede que me equivoque aquí, pero ¿no se puede eliminar ningún número con ningún factorial después de que simplemente se elimine y se reemplace con 1? Me gusta 0 !!!! = 1 !! = 0 !!!!!!!! = 1 !!! = 1! = 0! = 1, etc.
Albert Renshaw

2
@AlbertRenshaw Eso es correcto.
Aficiones de Calvin

Respuestas:


43

Mathematica, 25 17 bytes

Input[]/.!x_:>1-x

Toma información de un aviso del usuario. Asume el entorno de cuaderno de Mathematica para la impresión implícita. Para convertirlo en un script de línea de comandos, envuélvalo Print[...]o para que sea una función sin argumentos (que luego toma la entrada del indicador), agregue &.

Mathematica tiene los dos operadores requeridos (con la precedencia requerida), por lo que podemos simplemente "evaluar" la entrada (que se realiza automáticamente por Input[]), pero el operador de negación lógica no funciona en enteros (por lo que permanecerá sin evaluar). Si !xqueda algo en el resultado, lo reemplazamos con 1-x.

Un par de datos divertidos sobre la evaluación:

  1. En realidad, Mathematica también tiene el operador factorial doble !!, que computa n*(n-2)*(n-4)*..., pero se aplica 0o 1todavía da 1, por lo que no importa que 0!!!!!realmente se analice como ((0!!)!!)!.
  2. Aunque Mathematica se va !0y no se !1evalúa, sí sabe que !es autoinverso, por lo que cancelará automáticamente todos los pares de guía !. Después de la ToExpressionque estamos siempre quedamos con uno de 0, 1, !0, !1.

3
¿Desde cuándo se permitió un fragmento REPL por defecto?
LegionMammal978

2
@ LegionMammal978 Aparentemente desde diciembre de 2015, pero sigo olvidándolo. Para ser justos, no es un "fragmento" en el sentido de que no supone que la entrada ya esté almacenada en algún lugar de la memoria. Y asumir que el entorno del cuaderno no es muy diferente de tener un lenguaje con salida implícita.
Martin Ender

Por curiosidad, ¿podría proporcionarse un metaenlace? (Intentar encontrar información allí es estresante, otro problema más del formato de preguntas y respuestas SE ...)
LegionMammal978

@ LegionMammal978 ya está en la respuesta.
Martin Ender

Solución ksh pura x=${x/[01]!*/1};echo $(($x)): no se permite publicar una respuesta adecuada :(
DarkHeart

28

[Bash] + utilidades Unix, 21 17 bytes

sed s/.!!*$/1/|bc

Esto debe guardarse en un archivo y ejecutarse como un programa. Si intentas ingresar el comando directamente desde la línea de comando, ¡no funcionará porque! se expande debido a que la sustitución del historial se habilita en el modo interactivo de bash. (Alternativamente, puede desactivar la sustitución del historial con set +H).

El caso de prueba funciona:

for x in 0 1 '0!' '1!' '!0' '!1' '!0!' '!1!' '0!!' '1!!' '!!0' '!!1' '!0!!' '!!!1' '!!!0!!!!' '!!!1!!!!'; do ./excl <<<"$x"; done

0
1
1
1
1
0
0
0
1
1
0
1
0
0
0
0

La versión anterior funciona, esta no
vacas graznan

Usé el enlace TIO
vacas graznan

@ KritixiLithos Funcionó bien cuando lo probé en mi caja de Linux. Aparentemente, el problema era que TIO requiere una nueva línea al final de la línea de entrada simulada. Es una situación confusa, así que saqué el enlace TIO. Si desea probarlo, aquí está el enlace nuevamente (pero asegúrese de incluir una nueva línea al final de la entrada si cambia la entrada para probarlo): tio.run/nexus/bash#@1@cmqJQrK @ nqKilom @ oX5OU / P @ / ...
Mitchell Spector

2
Pero, ¿y si alguien ha corrido mkdir -p 's/.!!'{bunch,of,different,directories}\$/1? Luego obtendrá Pathname Expansion y Sed intentará leer directorios como si fueran archivos, en lugar de leer la entrada estándar, ¡y no generará nada! :)
Comodín

1
@Wildcard Estoy completamente de acuerdo. En los guiones de producción, siempre uso citas en situaciones como esta. (En este caso, en realidad pondría comillas dobles alrededor del argumento para sed, en lugar de simplemente escapar de *. Es más fácil de leer que usar barras invertidas, y evita la posibilidad de perder algún carácter especial.)
Mitchell Spector

22

Retina , 20 15 14 bytes

Gracias a Leo por guardar 1 byte.

0!
1
!!

^1|!0

Pruébalo en línea!

Explicación

0!
1

Conviértete 0!en 1. No nos interesan otros !s finales , el número resultante es el mismo que si hubiéramos aplicado todos los factoriales.

!!

Cancelar pares de negaciones. Esto también puede cancelar algunos factoriales, pero eso es irrelevante.

^1|!0

Cuente el número de coincidencias de esta expresión regular, que es o 1o 0y da el resultado deseado.


Solución alternativa para el mismo bytecount: \d.+...
vacas graznan

@KritixiLithos Encontré una manera de evitarlo por completo.
Martin Ender

Puede eliminar el ^antes!0
Leo

17

Suciedad , 14 12 9 bytes

e`\0!~\!_

Pruébalo en línea!

Explicación

Esto hace coincidir la entrada con un patrón, imprimiendo 1por coincidencia y 0sin coincidencia.

e`\0!~\!_
e`         Match entire input against this pattern:
    !      not
  \0       a sole 0
     ~     xor
      \!   exclamation mark
        _  followed by this pattern matched recursively.

La idea es esta. Si la entrada comienza con un dígito, entonces la parte recursiva \!_siempre falla y \0!tiene éxito a menos que tengamos un solo 0. Su xor tiene éxito a menos que la entrada sea única 0. Si la entrada comienza con a !, \0!siempre tiene éxito, y \!_tiene éxito si la coincidencia recursiva tiene éxito. Su xor tiene éxito exactamente cuando la coincidencia recursiva falla, lo que lo niega.


16

Brainfuck, 85 72 (84) bytes

,[>-[-----<->]<++[>++++[-<++++>]+<[[+],[[-]>-<]]]>[<<+[-->]>[<],>-]<]<+.

para volver numéricamente, o

,[>-[-----<->]<++[>++++[-<++++>]+<[[+],[[-]>-<]]]>[<<+[-->]>[<],>-]<]-[-----<+>]<--.

para texto ASCII. > también puede tener el prefijo para evitar el ajuste de memoria.

Pruébalo en línea!


Loops over the input.
On 1, ends.
On "!", toggles bool a stored as 0 or 255.
On "0", toggles if there is no trailing bit, then ends.

Memory labels  | BOOL | INPUT | FLAG |

,                   first input 
[                     # loop on INPUT
  >-[-----<->]<++     subtract 49 == "1"

  [                     # case not "1"
    >++++[-<++++>]      add 16 since 49 take 16 == "!"

    +                   set FLAG
    <                   move to INPUT
    [                     # case "0"
      [+],                clear and new INPUT
      [                     # case "0!"
        [-]>-<              clear INPUT and FLAG
      ]
    ]
  ]

  >                   move to FLAG
  [                     # case "!" or "0" without tail
    <<+[-->]>[<]        not the BOOL
    ,                   take new input
    >-                  clear FLAG
  ]
  <                   move to INPUT
]

+.                    return 0 or 1

O para la respuesta de texto, reemplace la última línea con

-[-----<+>]<--.       add 49 for "0" or "1" conversion and return

14

Brainfuck - camino a muchos bytes (232 bytes)

Claramente, el idioma equivocado para ganar en código golf. Principalmente noté la falta de alguien usando este esolang. Hay un buen intérprete en línea bf interpeter o puedes ver lo que hace el programa usando este visualizador bf .

>>>>>,[>+++[<---------------->-]<<<<<<[-]+>[-]>>>>[-[<<[>+<<<<->>>[<<+>>-] ]<<[>>+<<-]<[>>+<<[-]]>>>>>[-]]<<<<<[>>>++<<<-]>+>>>>[-]]<<<<-[>>+<<[-]]>>>>,]<<->[<[-]+>[-]]<<[<[-]>>[<<+>>[-]]+<<[->>-<<]>-]>>[-]+++[<++++++++++++++++>-]<.

3
¡¡Tu hombre loco!!
Almo

Me encanta, ¿puedes hacer eso en malbolge? XD
Stefan Nolde

Información: a continuación hay soluciones mucho más cortas.
user202729

14

Python, -44- 42 bytes

¡Ahorré 2 bytes gracias a Zgarb!

lambda x:(x[-1]=='0')^len(x.rstrip('!'))%2

Paso a paso:

  1. x[-1]!='0'
    si xtermina con 1o !xno termina con 0, la parte factorial debe tener valor 1, de lo contrario0
  2. ^len(x.rstrip('!'))%2
    explotar la propiedad de xor como un "condicional no". La condición en este caso es si la longitud de !s inicial es impar. Sin embargo, .rstripno elimina el número de la cadena, por lo que la longitud calculada se compensa en 1, por lo tanto, la condición se invierte
  3. El desplazamiento por 1 en el paso 2 se corrige cambiando !=a ==en el paso 1. Zgarb sugirió usar un operador de comparación de diferencias en lugar de aplicar otra inversión, ahorrando 2 bytes.

Pruébalo en línea!


Falla en una entrada de !!0; Actualmente está volviendo 1.
Value Ink

@ValueInk debería estar funcionando ahora
busukxuan

1
lambda x:(x[-1]=='0')^len(x.rstrip('!'))%2evita la inversión extra.
Zgarb

15
tachado 44 todavía es regular 44
Rɪᴋᴇʀ

3
Creo que está afirmando que un 44 tachado en la fuente utilizada no parece tachado ... :) La parte tachada se superpone con la parte horizontal de los 4.
JeffC

13

JavaScript (ES6), 43 41 29 bytes

s=>+eval(s.replace(/.!+$/,1))

Método no regex ( 41 31 bytes)

A continuación se muestra mi enfoque inicial. Es un poco más interesante, pero significativamente más largo aún un poco más, incluso después de una optimización significativa por parte de Neil (10 bytes guardados) .

f=([c,...s])=>1/c?c|s>'':1-f(s)

Casos de prueba


Sólo puedo guardar 10 bytes desde su método no regulares, por lo que es todavía demasiado largo: f=([c,...s])=>1/c?c|s>'':1-f(s).
Neil

@Neil Dado que de todos modos es mucho mejor que mi primer intento, me tomé la libertad de incluir su sugerencia.
Arnauld

Ja, tuve la misma idea pero la jugaste mejor. :)
Devsman

11

Jalea , 5 bytes

VeMḂ$

Pruébalo en línea!

Función monádica esperando una cadena. Las entradas con !s iniciales hacen 1que se imprima a STDOUT en el camino, por lo que el enlace TIO que doy es un arnés de prueba que imprime los pares de entrada-salida debajo de la primera línea de salida.

¿Cómo?

VeMḂ$ - Monadic link: string
V     - eval the string
          - the implicit input of 0 causes !...! to evaluate to 1 (which gets printed),
          - the result is the evaluation of the rest: "0"=0; "0!"=1; "1"=1; "1!"=1; ...
 e    - exists in?
    $ - last two links as a monad:
  M   -     Maximal indexes - the "0" and "1" characters are greater than "!",
                            - so this results in a list of one item [i] where
                            - i is the 1-based index of the 0 or 1 character.
   Ḃ  -     %2 (vectorises) - [i%2], so a 0 if we need to logically negate and a 1 if not
                            - hence we check equality with e rather than inequality.

10

05AB1E , 9 bytes

Código:

.V¹'!ÜgG_

Utiliza la codificación CP-1252 . Pruébalo en línea! o Verifique todos los casos de prueba!

Explicación:

.V         # Evaluate the input as 05AB1E code. This computes the factorial part.
   '!Ü     # Remove trailing exclamation marks..
  ¹        # ..from the first input
      g    # Get the length of the resulting string
       G   # Do the following length - 1 times:
        _  #   Negate the number

10

Retina , 13 bytes

Un enfoque algo extraño, pero es corto y funciona.

0$
!1
!!

^\d

Con las dos primeras líneas reemplazamos un final 0con !1: con este reemplazo ahora sabemos que la parte de nuestra cadena desde el dígito en adelante es igual a 1.

En las siguientes dos líneas, elimine los pares de !: la doble negación se borra a sí misma, y ​​ya tomamos en cuenta el factorial con el paso anterior.

Última línea, haga coincidir un dígito al comienzo de la cadena y devuelva el número de coincidencias: si se han eliminado todas las negaciones, encontraremos una coincidencia (y, como dijimos antes, sabemos que es igual a 1), si todavía hay una negación que esto no coincidirá.

Pruébalo en línea!


1
¿No sería necesariamente el dígito final siempre un 1? En ese caso, podría usar en 1lugar de \d.

1
@ ais523 no, porque la primera parte solo reemplazará un 0 final, por lo que, por ejemplo, la entrada 0!permanecerá sin cambios hasta la última línea
Leo

1
¡Una solución realmente encantadora, buen trabajo! :)
Martin Ender

10

Ruby, 12 + 1 = 39 24 15 13 bytes

Usa la -nbandera. ¡Gracias a @GB por -9 bytes!

p~/!*$|0$/%2

Como solo verifica la longitud, puede eliminar el cero final, en lugar de marcar "! 0" primero y un solo cero después de eso.
GB

@GB esa es una idea maravillosa! Sin embargo, encontré una solución que es aún más corta modificando mi expresión regular para buscar la posición 0 o el final de la línea
Value Ink

Entonces podrías simplemente comprobar el final '!' o cero o final de línea: p ~ /! + $ | 0 $ | $ /% 2 son solo 14 bytes.
GB

Y luego "0 $ | $" podría convertirse en "0? $" Para guardar otro byte.
GB

1
¡Mejor aún !*$es más corto por dos!
Value Ink

9

Perl , 20 bytes

19 bytes de código + -pbandera.

s/\d!+/1/;$_=0+eval

Pruébalo en línea!

Declaraciones de negación de Perl undefo 1, lo que el uso 0+de numerify el resultado 0+undefrendimientos 0. Además de eso, no hay mucho que decir sobre el código.


2
Acabo de escribir exactamente esto. Tener un +1.
primo

@primo ¡Me alegra ver que por una vez no estoy 20 bytes detrás de ti! Gracias :)
Dada

8

C, 68 62 61 53 bytes

c;e(char*a){for(c=1;*a<34;a++)c^=1;c=a[1]?c:*a&1^!c;}

Exprimí algunos bytes más con algunos abusos

Pruébalo en línea!


1
Creo que puede eliminar el intde la función y puede cambiar el *a==33a *a<34.
vacas graznan

Por desgracia *a%2es más corto que*a-48
vacas graznan

Gracias por el consejo. También pude eliminar a otro personaje al quitar los corchetes alrededor del retorno y asignarlo.
Ahemone

Estoy bastante seguro de que for(;*a<34;a++)puede acortarse para for(;*a++<34;)ahorrar 1 byte
Albert Renshaw

Desafortunadamente no, como la declaración condicional siempre se ejecutará y, por lo tanto, empujará el puntero demasiado lejos para la desreferencia de retorno.
Ahemone

6

Perl 6 , 32 28 23 bytes

{m/(\!)*(1|0.)*/.sum%2}

Cómo funciona

{                     }  # A lambda.
{m/            /      }  # Match the lambda argument against the regex:
   (\!)*                 #   Zero or more `!`.
                         #     (First capture will be an array with one element per negation).
        (1|0.)*          #   A `1`, or a `0` and another character, zero or more times.
                         #     (Second capture will be a one-element array if the factorial
                         #     part evaluates to 1, and an empty array otherwise.)
                .sum     # Add the lengths of the two captures,
                    %2   # and return that sum modulo 2.

6

Haskell , 39 bytes

f('!':b)="10"!!read[f b]
f[a]=a
f _='1'

Define una función f, que toma una cadena y devuelve un carácter. Pruébalo en línea!

Explicación

Hay tres casos: la entrada comienza con !, la entrada tiene longitud 1 y todo lo demás.

f('!':b)=    -- If input has head '!' and tail b,
 "10"!!      -- we index into the string "10"
  read[f b]  -- using f b converted to int. This essentially inverts f b.
f[a]=        -- If input has only one character, we know it's a digit,
 a           -- so we can just return it.
f _=         -- In all other cases, we know the input is a digit followed by !s,
 '1'         -- so we can return '1'.

Cambiar de cadena a entero como el tipo de retorno: f('!':b)=[1,0]!!f b;f"0"=0;f _=1.
nimi

6

Befunge, 24 bytes

~"!"-:#v_$1+
*+2%!.@>0~`

Pruébalo en línea!

Esto comienza contando el número de !caracteres leídos de stdin. El primer carácter que no !sea ​​un será un 0o 1, pero en el proceso de prueba !habremos restado 33, haciéndolo 15 o 16. Luego leemos un carácter más, que será un !o EOF, y compare si eso es menor que 0 (es decir, EOF).

Tomando esos tres puntos de datos (el conteo de exclamación ( c ), el valor del dígito, ( d ) y la condición de fin de archivo ( e )) podemos calcular el resultado de la siguiente manera:

!((c + d*e) % 2)

Multiplicar el valor del dígito por la condición de fin de archivo significa que se convertirá a cero si el dígito fue seguido por a !, lo que le da el mismo valor de módulo 2 que a 1(que recuerde se ha convertido a 16). Pero antes de aplicar el módulo 2, agregamos el recuento de exclamación inicial, que efectivamente alterna el resultado del módulo 2 tantas veces como sus !prefijos. Y finalmente no somos el resultado ya que nuestros valores de referencia para 0y 1son lo opuesto a lo que necesitamos.

Mirando el código con más detalle:

~                Read a character from stdin.
 "!"-            Subtract 33 (ASCII for '!').
     :  _        Make a duplicate and check if zero (i.e. is it a '!').
         $1+     If so, drop the duplicate, increment a counter, and repeat.
       v         Otherwise move to the second line, leaving the digit value on the stack.
       >0~`      Read one more character and check if less than 0 (i.e. EOF).
*                Multiple by the digit value, making it zero if not followed by EOF.
 +               Add to the exclamation count.
  2%             Modulo 2 the result.
    !            Then not that value.
     .@          And finally write to stdout and exit.

6

Haskell , 27 bytes

f('!':b)=1-f b
f"0"=0
f _=1

Pruébalo en línea!

Cada encabezado !complementa la salida para el resto de la expresión, hecha como 1-. Seguimos volteando hasta que alcanzamos un dígito. Si el resto es justo "0", el resultado es 0. De lo contrario, es un 1o es seguido por uno o más !, por lo que el resultado es 1.


5

Ruby, 22 21 20 bytes

->s{(s=~/!*$|0$/)%2}

Explicación:

  • Primer caso, tengo un '!' al final, retírelos, obtenga la longitud del módulo 2.
  • Segundo caso, no '!', Si el último carácter es cero, elimínelo, obtenga la longitud del módulo 2
  • Si el último carácter es 1, regrese al primer caso

(-1 byte robando la idea de @Value Ink)


Impresionante, miré este rompecabezas durante 10 minutos pero no tuve mucho tiempo y luego lo olvidé. Ahora lo vi de nuevo en preguntas activas y estaba encantado de ver un enfoque tan agradable.
akostadinov

4

Jalea , 8 bytes

œr”!LḂ=V

Pruébalo en línea!

Esta es una función (enlace monádico) que toma un argumento y regresa a través de su valor de retorno. (También a menudo escribe basura en la salida estándar como un efecto secundario, pero eso no nos importa).

Explicación

œr”!LḂ=V
œr”!      Take {the input}, with all trailing ! deleted
    L     Take the length of this
     Ḃ    Take the parity of that length
      =   Return 0 if unequal, 1 if equal to:
       V    the value of {the input} when eval'ed as a niladic Jelly program

Primero, tenga en cuenta que, como la entrada siempre consiste en un número de !, seguido de un dígito, seguido de más !, que si eliminamos el final !y tomamos la longitud, terminaremos con uno más el número de líderes !en el programa. Tomar la paridad de esto devolverá 0 si hubo un número impar de !, o 1 si hubo un número par de !. Comparar con 0 es una función "no", mientras que comparar con 1 es la función de identidad; por tanto, œr”!LḂ=pone en práctica con eficacia el "tratamiento conduce !NO operadores como" parte de la pregunta.

En cuanto a la segunda mitad, el manejo de factoriales !es una operación factorial en Jelly, por lo que si el programa no tiene liderazgo !, podemos resolver el problema directamente con un simple eval( V). Si el programa no tiene que conduce !, aquellos se interpretarán como tomar el factorial de 0 (posiblemente varias veces), produciendo un valor de retorno de 1, que será impreso en la salida estándar y se desecha una vez que se ve un dígito; por lo tanto, no tienen impacto en el valor de retorno de la función que es mi presentación a la pregunta.


Muy buena y gran explicación.
ElPedro

4

Python, 38 bytes

lambda s:(s[1::2]>s[::2])^ord(s[-1])%2

TryItOnline!

Una función sin nombre que toma una cadena de entrada sy devuelve un entero 0o 1.

s[1::2] es un segmento de la cadena de entrada que comienza en el índice 1 y tiene un tamaño de paso de dos:
'Like this' -> 'ieti'

s[::2] es similar pero comienza en el índice predeterminado de 0:
'Like this' -> 'Lk hs'

La prueba (s[1::2]>s[::2])verifica si el índice basado en 0 de '0'o '1'es impar, es decir, si necesitamos complementar.
Esto funciona porque el orden de las cadenas se verifica lexicográficamente con cualquier cadena no vacía mayor que la cadena vacía, y con el orden ASCII, por lo tanto '1'>'0'>'!'. Este es un byte más corto que el más simple s.index(max(s))%2.

Las ord(s[-1])%2comprobaciones para ver si el último carácter no es un '0'(para entrada válida), y los resultados en un número entero (mientras que la misma longitud (s[-1]!='0')devolvería un booleano).
Esto funciona porque el último carácter de la entrada, s[-1]será a '0', '1'o '!'que tenga los puntos de código ASCII 48, 49 y 33 respectivamente, que son 0, 1 y 1 módulo 2.

El ^realiza entonces una bitwise operación O exclusiva sobre los dos valores anteriores, devolver un número entero desde una entrada, la correcta, es un número entero. Si la izquierda es True, se devuelve el complemento de la derecha, si la izquierda es False, se devuelve la derecha, según sea necesario.


4

Java 7, 105 82 81 bytes

int a(char[]a){int b=0,c=0;for(;a[b++]<34;c^=1);return(b<a.length?1:a[b-1]&1)^c;}

Pruébalo en línea!

Antigua solución regex-ish

int a(String a){a=a.replace("0!","1").replaceAll("1.*","1");int b=a.length()-1;return b%2^a.charAt(b)&1;}

2
c^=1Es super inteligente. Es un operador no utilizado si alguna vez he visto uno.
Addison Crump

3

CJam , 12 11 bytes

r_W='0=!\~;

Pruébalo en línea! Conjunto de pruebas (imprime un 1para cada caso de prueba correcto).

r      e# Read input.
_W='0= e# Duplicate and check whether the string ends in '0'. This is the
       e# only case in which the factorial part results in 0.
!      e# Negate this to get the actual result of the factorial part.
\      e# Swap with the input.
~      e# Evalute the input as CJam code. The leading `!` will apply the logical
       e# negations to the factorial result. The 0 or 1 will then push a junk value
       e# which is potentially negated a few times as well, by the factorials.
;      e# Discard the junk value.


3

Brainfuck, 115 bytes

>,[->++++[<-------->-]<[--------------->,[<[-]+>-]<<[->-[>+<+]>[-<+>]<<]>>++++++[-<++++++++>]<.>>+<]>-[<<+>,>[-]]<]

Pruébalo en línea!

Sin golf:

% 0: inverter count
% 1: result
% 2: if/else flag; tmpspace in inner loop 0

>1,[
    ->2++++[<-------->-]<1 subtract 33 (!)
    [ 
        % we've reached the number
        ---------------
        % now it's either 0 or 1

        % check next char; If it's not 0 then it's '!'
        % 0! = 1! = 1!...! so we only need to determine if at least one ! exists
        >2,
                [<[-]+>-]<1

        % apply inversions
        <0
        [->1
            % invert cell 1 once each iteration
                       % cell 1 is 0 or 1
            -          % cell 1 is 255 or 1
            [>+<+]     % cell 1 is 0; cell 2 is 1 iff cell 1 should be 1
            >2[-<+>]<1 % cell 1 is 1 or 0
        <0]

        % print result
        >1>++++++[-<++++++++>]<1.

        >>2+< % tape={0 r 0 1}
    ]
    >2-[ % we haven't seen the number yet
        <<0+>1,>2 % add to inverter count
        [-]
    ]<1
]

2

Lote, 62 bytes

@set/ps=
@set s=%s:0!=1%
@set s=%s:!!=%
@cmd/cset/a%s:1!=1%

Toma entrada en STDIN. En realidad, Batch entiende !correctamente los mensajes iniciales para este desafío, pero !es necesario tratar los mensajes finales , que requieren tres pasos:

  • Cambiar 0!a1
  • Eliminar pares de !!(esto también es seguro para la !!s antes del dígito)
  • Eliminar cualquier resto restante !(que ahora solo puede ser después de a 1)

2

sed, 36 33 31 bytes

Sed puro, sin bc / shell utilidades. Funciona en GNU sed <4.3; 33 bytes en BSD y GNU 4.3+.

s/.!!*$/1/
:
s/!0/1/
s/!1/0/
t

Lo suficientemente directo si está familiarizado con sed; comentado para aquellos que no son:

# Since 0! == 1! == 1 and factorial has precedence, just collapse any trailing "!" 
s/.!!*$/1/
# Define an anonymous label
:
# Invert 0 if needed
s/!0/1/
# Invert 1 if needed
s/!1/0/
# If a change was made, go back to the anonymous label.
t

Prueba:

% cat 109248.sed
s/.!!*$/1/
:l
s/!0/1/
s/!1/0/
tl
% wc -c 109248.sed
      33 109248.sed
% cat cases
0
1
0!
1!
!0
!1
!0!
!1!
0!!
1!!
!!0
!!1
!0!!
!!!1
!!!0!!!!
!!!1!!!!
% sed -f 109248.sed cases
0
1
1
1
1
0
0
0
1
1
0
1
0
0
0
0
% gsed -f 109248.sed cases
0
1
1
1
1
0
0
0
1
1
0
1
0
0
0
0
%

IIRC algunas versiones (¿todas?) De le sedpermiten usar la cadena nula como nombre de etiqueta. Si puede hacer que eso funcione aquí, le ahorraría dos bytes. En realidad, no estoy seguro de que la etiqueta sea necesaria; a menos que me haya perdido algo, la primera línea es idempotente, por lo que es posible que pueda volver al inicio del programa en lugar de necesitar una etiqueta.

@ ais523 Yo también lo pensé, pero evidentemente no funciona en las versiones BSD. La página de manual dice "Si no se especifica una etiqueta, bifurca hasta el final del script", e incluso eso no funcionaba cuando lo intenté.
Kevin

GNU sed permite que una etiqueta sea justa :(más de un error tomado como característica), en cuyo caso tanto el ty b! los comandos saltan a la posición de la etiqueta. Además, un código sed debe funcionar para al menos una versión de sed, similar a otros lenguajes, por lo que no necesita crear código que funcione también para BSD.
seshoumara

2

PHP 7.1, 58 55 54 37 35 bytes

Nota: utiliza la codificación IBM-850

echo!!$argn[-1]^strspn($argn,~Ì)%2;

Corre así:

echo '!!!0!!!!' | php -nR 'echo!!$argn[-1]^strspn($argn,~Ì)%2;';echo
> 0

Explicación

echo
  strspn($a=$argv[1],~Ì) # Count the number of leading exclamation marks.
  % 2                    # Make 0 (even) or 1 (odd).
  ^ !!$a[-1];            # Negate with factorial part (truthy value of the 
                         # last char):
                         # - "0" is considered falsy.
                         # - "1" or "!" is considered truthy.

Ajustes

  • Guardado 3 bytes utilizando la codificación IBM-850
  • Guardado un byte cambiando ligeramente la expresión regular
  • Guardado 17 bytes, nueva versión sin nombres largos de función y retorno
  • Se guardaron 2 bytes mediante el uso -R(que está $argndisponible)

1

Fórmula IBM / Lotus Notes - 77 bytes

@Eval(@Left(a;@If(@Like(a;"%1%");"1";"0"))+@If(@Ends(a;"!");"1";@Right(a;1)))

No hay TIO para Notes Formula, por lo que a continuación se muestra una captura de pantalla de todos los casos de prueba:

Todos los casos de prueba

Cómo funciona

@Eval() evalúa una cadena como una expresión

Primero verificamos si la cadena de entrada en el campo (entrada) acontiene 1o 0y tomamos todos los caracteres a la izquierda de lo que sea, que será una cadena de !caracteres. No nos importa cuántos. @Eval()se encargará de eso.

Luego miramos para ver si hay un !al final de la cadena. Si existe, agregamos 1a la !cadena ( 0!y 1!ambos son 1, no importa cuántos !caracteres haya al final), de lo contrario, agregamos el último carácter sin cambios porque no es a !y podría ser a 1o a 0.

Ahora tenemos una cadena que contiene las inversiones iniciales más un número definido por si hay caracteres factoriales para poder alimentar esto @Eval()y obtener los resultados anteriores.


1

Bean , 24 bytes

Hexdump:

00000000 26 4a c1 53 a0 17 53 d0 80 a0 5d 20 80 0a a1 80  &JÁS .SÐ. ] ..¡.
00000010 81 00 25 3a ae a1 ab 24                          ..%:®¡«$
00000018

JavaScript equivalente:

+eval(a.replace(/.!+$/,1))

Perdón por pisar los pies, Arnauld .

Explicación:

Toma primera línea de entrada como una cadena sin formato en a, y sustituye cualquier dígito seguido por uno o más !con 1, por lo que el resto se puede eval'D mediante JavaScript.

Prueba la demo o el conjunto de pruebas

Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.