'Agregar' las letras en una palabra

17

Mi padre es un maestro retirado, y solía dar exámenes combinados de ortografía y matemáticas, donde el alumno deletreaba una palabra y luego 'puntuaba' la palabra sumando las letras, donde a = 1, b = 2, etc. (p. ej. cat = 3 + 1 + 20 = 24). Esto facilitó la calificación de los cuestionarios, ya que solo tendría que verificar las 'puntuaciones' incorrectas en lugar de las palabras mal escritas, y tuvo el beneficio adicional de probar 2 habilidades a la vez.

Contrató a un amigo mío para que escribiera un programa que calificara palabras para él, de modo que pudiera generar largas respuestas sin errores. Este problema está inspirado en ese programa.

Requisitos:

  1. Acepta cualquier palabra con letras mayúsculas y minúsculas
  2. Devuelve un error para cualquier carácter especial, es decir, espacios, guiones, @ ^% # etc.
  3. a = 1, b = 2, ... y A = 1, B = 2, ...
  4. Imprime el puntaje de la palabra
  5. (Opcional) verifique que la palabra esté en un diccionario después de la puntuación e imprima una advertencia si no lo está.
  6. No importa un diccionario externo de letras-> números. Debes generarlo tú mismo.

Cualquier idioma es aceptable. Esto es similar a la ' batalla raíz digital ', pero mucho más simple.

Zach
fuente
2
¿Se supone que esto es un código de golf?
Peter Taylor
2
@Zach Usando la code-golfetiqueta.
Lowjacker
2
¿Tu padre incluso se molestó en enseñar la regla "I antes de E excepto después de C"?
Nathan Merrill
2
Sí, solo revisando puntajes? Deletrearía gato como aaaaaaaaaaaaaaaaaaaaaaaa. Papá: ¿El puntaje es 24? ¡Así es!
ericw31415
3
@ ericw31415 Cada función de hashing tiene colisiones ;-). Hasta ahora ninguno de sus estudiantes ha intentado ese vector de ataque
Zach

Respuestas:

8

Golfscript - 23 caracteres

0\{.31&.(.26%=@64///+}/

Asegúrese de que no haya nuevas líneas finales en la entrada (por ejemplo, uso echo -n).

Nabb
fuente
¡Tenemos un nuevo ganador!
Zach
En general, se supone que el filtrado externo se incluye de alguna manera en el recuento de caracteres (Ctrl-f filtrado externo), aunque supongo que solo quedan 2 caracteres adicionales.
Jesse Millikan
2
@Jesse: echo -nrealmente no cuenta como filtrado externo; de hecho, la respuesta que vinculó lo sugiere como un formulario válido para la entrada.
Nabb
10

Brainf *** (100)

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

Sin embargo, debo admitir que esto no cumple con todos los requisitos. Primero, solo acepta letras mayúsculas, y la palabra debe terminar con una pestaña. Tiene un comportamiento indefinido para caracteres no válidos y no arroja un error. Muestra la suma de las letras como un carácter ASCII. Por ejemplo, si la palabra es "HOLA", (8 + 5 + 12 + 12 + 15 = 52) mostrará el carácter "4", que es el carácter ASCII para 52. Esto también significa que el programa se asusta cuando la suma es más de 255.

Pero aparte de eso , funciona bien. Dame un respiro, mi cerebro solo puede manejar pequeñas dosis de ... bueno, ya sabes.

Peter Olson
fuente
¿Por qué terminar la palabra con una pestaña en lugar de una nueva línea?
Lowjacker
@Lowjacker Porque asumí que TAB es más simple que preocuparse por \no \r\no \n\r. Y si usara nueva línea, no tendría un buen número redondo como 100 como el recuento de caracteres.
Peter Olson el
¿Qué pasaría si recibiera una dosis grande?
Mateen Ulhaq
8

Pitón ( 65 64)

print sum(['',ord(i)-64]['@'<i<'[']for i in raw_input().upper())

Esto genera un error si la palabra contiene caracteres que no son letras, pero no es útil o informativo. (Editar: punta del sombrero para evitar el truco de indexación).


fuente
1
print sum(['',ord(i)-64]['@'<i<'[']for i in raw_input().upper())afeitado un par de caracteres.
st0le
Solo un personaje en realidad. : - \
st0le
Guardar 4 caracteres mediante el uso input; obliga al usuario a poner comillas alrededor de las cadenas de entrada, pero "fácil de usar" y "no peligroso" no están en la especificación.
jscs
Bueno, ¡solo cámbialo a Python 3! raw_inputinput
Oleh Prypin
print sum([i,ord(i)-64]['@'<i<'[']for i in raw_input().upper()) otro byte afeitado
Alexander Nigl
8

Ruby, 43 caracteres

$_=gets.upcase;p~/[^A-Z]/?_: $_.sum-64*~/$/

Sin embargo, el mensaje de error que esto genera no es exactamente útil. Ambas soluciones publicadas aquí suponen que la entrada no tiene salto de línea final, así que para probarlas, use echo -n.

Ruby, 76 caracteres con verificación de diccionario

l=STDIN.gets;$_=l.upcase;p~/[^A-Z]/?_: $_.sum-64*~/$/;[*$<].index(l)||$><<?W

El mensaje de advertencia consta del carácter único "W". La ruta al diccionario se debe proporcionar a través de ARGV. Ejemplo de uso:

$ echo -n asd | ruby addletters.rb /usr/share/dict/words
24
W
$ echo -n cat | ruby addletters.rb /usr/share/dict/words
24
Ventero
fuente
2
Puede cortar 9 caracteres en la versión de verificación del diccionario haciendo que el mensaje de error sea un signo de exclamación.
Peter Olson el
Obtienes un premio de consolación por la entrada más corta con un cheque de diccionario. ¡Camino a seguir!
Zach
¿Por qué se propuso la verificación del diccionario si no le da ninguna ventaja real (por el contrario, solo hinchó el código)?
Método auxiliar
5

Python 2.6 (72 caracteres) Sin verificación de diccionario

print sum(map(" abcdefghijklmnopqrstuvwxyz".index, raw_input().lower()))

Python 2.6 (178 caracteres *) con verificación de diccionario

w=raw_input().lower()
print sum(map(" abcdefghijklmnopqrstuvwxyz".index, w))
if w not in open('/usr/share/dict/american-english').read().split():
 print('Word not in dictionary')

* Se puede bajar a 156 con un mensaje de error menos útil. :-)

Gracias a todos los comentaristas por ayudar a mejorar esto.

John
fuente
Es posible que desee considerar usar el sumbuiltin con una expresión generadora, en lugar de un forbucle. Le permitiría recortar algunos caracteres (~ 17).
@jloy: Gracias por señalarlo.
John
los paréntesis en la impresión se pueden eliminar
st0le
parece que estás usando asolo una vez, así que usa el literal en sí mismo ... "0abc....z".index(i)funcionará de manera equivalente.
st0le
La 0matriz de puntuación es inteligente, pero también significa que cat0se acepta sin error, lo cual no es correcto, creo. Lo cual es una lástima, ya que le permitiría pasar map(a.index,w)en su sumlugar (sustituyendo el literal por acomo sugiere st0le).
4

Perl (52) (48)

golf aún más gracias a Timwi

perl -lpe "($w=uc)=~/[^A-Z]/&&die;$w=~s/./$_-=64-ord$&/ge"

perl chino goth
fuente
Te estás perdiendo la -ebandera allí.
Lowjacker
1
Al menos debe incluir las banderas pe lintérprete en su recuento de caracteres. Ver esta discusión en meta.
Ventero el
syntax error at -e line 1, near "(=" Execution of -e aborted due to compilation errors.¿Qué estoy haciendo mal?
usuario desconocido el
si está ejecutando en Unix, cambie las comillas dobles a simples
chino perl goth
@Timwi: 'Aceptar cualquier palabra con mayúsculas y minúsculas' fue al hilo equivocado, lo siento. Lo eliminé ahora. @chinese: Sí, gracias, con comillas simples está bien. Mientras me limite a la entrada ascii. :)
usuario desconocido
4

Pitón (80)

w=raw_input().lower()
s=0
for l in w:s+=range(97,123).index(ord(l))+1
print s

Python v2 (65 pero char `será aceptado)

print sum(map(range(96,123).index,map(ord,raw_input().lower())))

v3 (60 caracteres, @ serán aceptados pero no contados, gracias jloy)

print sum(map(range(64,91).index,map(ord,input().upper())))
Uno de uno
fuente
SUGERENCIA: HAY UNA FORMA DE ELIMINAR UN CARÁCULO MÁS DE SUS SOLUCIONES. :)
2
@jloy Qué 'sugerencia' útil. ;)
Mateen Ulhaq
4

Scala: 59 caracteres, 7 de ellos carga útil, sin dict:

(0/:"Payload".map(c=>if(c.isLetter)(c-'A')%32 else-999))(_+_)
67

No hay diccionario hasta ahora. Resultado negativo significa: ¡Negativo!

(0/:"Pay!wall?".map(c=>if(c.isLetter)(c-'A')%32 else-999))(_+_)   
-1915

Maneja el Umlaute alemán con gracia, por cierto:

(0/:"Müllrößchen".map(c=>if(c.isLetter)(c-'A')%32 else-999))(_+_)
155
usuario desconocido
fuente
Wow, menos caracteres que la versión de Perl (y aún más legible).
Método auxiliar
Probé SHiNKiROU y la solución de chinesis-Perl, pero no funcionaron para mí. Los guardé como alpha.ply los comencé perl alpha.pl. ¿Solo manejan Ascii? Bueno, en Perl es una bestia tan vieja ... :)
usuario desconocido
Perl y Unicode es un gran desastre. Probablemente tengas que ejecutarlos como perl -M5.010 alpha.plo algo así.
Peter Taylor
Escuché que necesito comillas simples en lugar de comillas dobles en Linux, y esto funcionó, gracias.
usuario desconocido
4

Bibliotecas Java + Google Guava, 347 caracteres, con verificación de diccionario

Versión de 1 cadena larga ilegible :-)

import java.io.*;import com.google.common.base.*;import com.google.common.io.*;class C{public static void main(String[]a)throws Exception{int s=0;for(int c:a[0].toUpperCase().toCharArray()){assert(c>64&&c<91);s+=c-64;}String d=Files.toString(new File(a[1]),Charsets.UTF_8);if(StringUtils.containsIgnoreCase(d,a[0]))System.out.println("w");System.out.println(s);}}

Versión legible para humanos (tipo de :-))

import java.io.*;

import com.google.common.base.*;
import com.google.common.io.*;

class C {
    public static void main(String[] a) throws Exception {
        int s=0;

        for(int c : a[0].toUpperCase().toCharArray()) {
            System.out.println(c);
            assert(c > 64 && c < 91);
            s += c - 64;
        }

        String d = Files.toString(new File(a[1]), Charsets.UTF_8);

        if (d.contains(a[0])) System.out.println("w");

        System.out.println(s);
    }
}

La ruta del diccionario ahora se pasa a través de a[1], para que las aserciones funcionen, debe usar la -eabandera (+3 caracteres más). En cuanto al diccionario, /usr/share/dict/wordsse ha utilizado el dict (debería estar disponible en la mayoría de los sistemas * nix).

Método de ayuda
fuente
Hasta ahora eres el único con un chequeo de diccionario, entonces +1
Zach
¿una línea? esto no es particularmente legible de esta manera, aunque supongo que ahorra caracteres
Nate Koppenhaver
Agregaré una solución más legible (y también una más corta usando Google Guava para reducir el código repetitivo).
Método auxiliar
¿Solo permite ascii, pero usa Charset.UTF-8?
usuario desconocido
1
Porque el String UTF-8es más corto que los otros conjuntos de caracteres :-).
Método auxiliar
4

Python 3, 95 caracteres con diccionario

d=input().lower()
print(d in open("d").read()and sum(['',ord(c)-96]['`'<c<'{']for c in d)or'f')

El diccionario tiene que estar en un archivo llamado d.

Python 3, 61 sin diccionario, pero idea robada

print(sum(['',ord(c)-96]['`'<c<'{']for c in input().lower()))
cemper93
fuente
3

Perl (71)

($a)=lc<>;$a=~/[^a-z]/i&&die;$x+=ord$_ for split//,$a;die$x-96*length$a;
Ming-Tang
fuente
3

VB.NET, 84 82 73 71

Console.Write(Console.ReadLine.Sum(Function(c)Asc(Char.ToUpper(c))-64))


Editar: Con validación es:

Dim r=Console.ReadLine
Console.Write(If(r.All(AddressOf Char.IsLetter),r.Sum(Function(c)Asc(Char.ToUpper(c))-64),"Invalid input."))

129 caracteres. En ese caso:

C #, 118

var r=Console.ReadLine();Console.Write(r.All(char.IsLetter)?r.Sum(c=>char.ToUpper(c)-64).ToString():"Invalid input.");
Ry-
fuente
1
Esto no valida la entrada.
Lowjacker
¡Uy! Espera un segundo ...
Ry-
3
Creo que deberías proporcionar programas completos. Su solución C # no se compila; debe colocarlo en un método Main dentro de una declaración de clase y contar todos los caracteres.
Timwi
1
No, porque ese código no hace nada, y no es justo perjudicar a los usuarios de lenguajes orientados a objetos. Esto es válido C # / VB.NET de todos modos.
Ry-
3

Mejorando ligeramente la respuesta de John: Python (90)

s=0
for i in raw_input().lower():
 s+=("abcdefghijklmnopqrstuvwxyz".index(i)+1)
print(s)
Zach
fuente
2
añadiendo el carbón maniquí en el comienzo cadena es menor ... paréntesis se puede quitar
st0le
3

Erlang, 104

a()->
a(string:to_lower(io:get_line([])),0).
a([_|[]],S)->
S;
a([C|R],S) when C<${, C>=$`->
a(R,S+C-$`).
xymostech
fuente
3

Golfscript - 39 caracteres

n%~{.96>{96}{64}if-..26>\0<|{0/}*}%{+}*

El error que arroja no es exactamente el mejor, pero bueno, aborta la ejecución.

Juan
fuente
No sé nada sobre golfscript, ¡así que voy a asumir que cumple con los requisitos y declararle ganador!
Zach
¡Vaya, has sido vencido! ¿Supongo que 2 días no son suficientes para esperar una pregunta de código de golf?
Zach
3

PYTHON 62 68 * Personajes

print sum(map(chr,range(65,91)).index(c)+1 for c in input().upper())

Requiere que el usuario ingrese cadenas usando comillas, y no es seguro ( inputejecuta el código), pero, como dije en un comentario en otra publicación, "no es fácil de usar" y "no es un riesgo de seguridad" no está en la especificación.


* Me olvidé print, maldita sea.

jscs
fuente
La respuesta de jloy es aún más corta, en realidad, debido a la diferencia input/ raw_input.
jscs
2

Ruby 1.9, 69

w=gets.chop.upcase
w[/[^A-Z]/]&&fail
p w.bytes.inject(0){|s,b|s+b-64}
Lowjacker
fuente
Solo maneja caracteres ascii. ¿Pensé que Ruby es de nuestro siglo? :)
usuario desconocido
@user unknown: la especificación no dice que tenga que hacerlo. Hacerlo sería bastante complicado ...
Lowjacker
2

GolfScript, 50 (53)

Da un error en los caracteres incorrectos, pero no uno muy bueno (50 caracteres):

);[{""123,97>+91,65>+?}/].-1?0<{{26%1+}%{+}*}{@}if

Da "E" en caso de error (53 caracteres):

);[{""123,97>+91,65>+?}/].-1?0<{{26%1+}%{+}*}{;"E"}if

El fragmento generador de alfabeto 123,97>+es robado de Ventero.

Jesse Millikan
fuente
2

J (55)

+/64-~-&32`]@.(<&97)`_:@.(<&65)`_:@.(>&122)"0,I.a.&e."0

Esto satisface todas las condiciones excepto la del diccionario. Como condición de error, devuelve "infinito" (el símbolo de subrayado en J) para palabras que contienen cualquier cosa menos letras.

Gregory Higley
fuente
2

Haskell (127)

(genera un error en caracteres extraños)
(también: el espacio entre toUpper.y \xes necesario, de lo contrario lo analiza como (toUpper) .\ (x))

import Char
main=getLine>>=putStrLn.show.sum.(map$(-65+).ord.toUpper. \x->if x`elem`['A'..'Z']++['a'..'z']then x else error"")

Haskell (70)

(no genera un error, pero es un 45% más corto)

import Char
main=getLine>>=putStrLn.show.sum.(map$(-65+).ord.toUpper)
marinus
fuente
2

C ++ ( 111 107)

void main(){int a=0;s8*b=new s8[99];for(cin>>b;*b;)if(isalpha(*b))a+=tolower(*b++)-96;else return;cout<<a;}

La "configuración" / etc:

#include <iostream>
#include <cstdio>
#include <cctype>

#ifdef _MSC_VER
    typedef __int8 s8;
#else
    typedef signed char s8;
#endif

Comportamiento "indefinido" (es más 'mala práctica' que 'indefinido', pero bueno):

  • void main() Eso lo dice todo.
  • Estoy usando newsin delete.
Mateen Ulhaq
fuente
1

JavaScript 1.8, 80 caracteres

Sorprendentemente legible!

alert(Array.reduce(prompt().toLowerCase(),function(a,b)a+b.charCodeAt(0)-96,0))
Casey Chu
fuente
Para su uso en Chrome tuve que convertirlo en un poco de: alert(prompt().toLowerCase().split("").reduce(function(a,b){return a+b.charCodeAt(0)-96},0)). Todavía me gustan las soluciones de JavaScript :)
pimvdb
¿No devuelve un error cuando haces un carácter no válido?
ericw31415
1

APL (34)

+/{⍵∊⍳26:⍵}¨{64-⍨A-32×96<A←⎕UCS⍵}⍞

Da la puntuación o un VALUE ERRORsi hay caracteres no alfabéticos en la entrada.

Explicación:

  • : lee una línea de entrada
  • {... }: función aplicada a cada carácter de entrada
  • A←⎕UCS⍵: almacena el valor ASCII del carácter actual en A
  • A-32×96<A: hace que el carácter sea mayúscula: de Ase resta 32 si 96<A(entonces, si es mayúscula), de lo contrario 0
  • 64-⍨: resta 64 de esto, dando A = 1, B = 2 ...
  • ¨: aplica esta función a cada personaje:
  • ⍵∊⍳26: si el personaje tiene entre 1 y 26 ...
  • :⍵: luego devuelve ⍵ (y dado que no hay otra cláusula, habrá un VALUE ERRORsi no está entre 1 y 26)
  • +/: suma todos los valores juntos (y este valor se genera automáticamente porque es el resultado final).
marinus
fuente
1

JavaScript, 60 bytes

s=>[...s.toUpperCase()].reduce((a,b)=>a+b.charCodeAt()-64,0)

Si el programa debe devolver un error en entradas no válidas, entonces 80 bytes:

s=>/[^a-z]/i.test(s)?_:[...s.toUpperCase()].reduce((a,b)=>a+b.charCodeAt()-64,0)

Si una entrada no es válida, la consola dirá que _no está definida (no debe haber una variable definida llamada _).

ericw31415
fuente
1

Pitón 3, 58 55

print(sum(ord(x)%32for x in input()if x.isalpha()or z))

sin diccionario o idea robada pero todavía error inútil;)

thx @ Eᴀsᴛᴇʀʟʏ

Prueba aquí .

Alexander Nigl
fuente
Creo que puede guardar un byte cambiando a python 2 y haciendo print<SPACE>sum(ord(......., eliminando los 2 paréntesis alrededor de la expresión.
Rɪᴋᴇʀ
@ EᴀsᴛᴇʀʟʏIʀᴋ eso es correcto, pero la entrada debe estar entre paréntesis y no quiero promover python 2;)
Alexander Nigl
¡PYTHON 2 ES VIDA! y también, ¿no creo que eso requiera que la entrada esté entre paréntesis?
Rɪᴋᴇʀ
@ EᴀsᴛᴇʀʟʏIʀᴋ sry quise decir citado. input()en python3 está raw_input()en python2
Alexander Nigl
Oh, lo olvidé. Hm.
Rɪᴋᴇʀ
1

C, 98 bytes

 int a(char *s){int b=0;while(*s){if(!isalpha(*s))throw 1;b+=(toupper(*(s++))-64);}printf("%d",b);}
Adam Spindler
fuente
1

F # (sin validación) 79 57 caracteres

let a w=w|>Seq.fold(fun a b->a+(int b)-65)0|>printfn"%i"
Smetad Anarkist
fuente
1

C # con validación: 108 caracteres (con 12 para mensaje de error):

var s=Console.ReadLine();Console.Write(s.All(Char.IsLetter)?s.Sum(x=>x&'_'-'@').ToString():"Invalid input");

C # sin validación: 60 53 caracteres:

Console.Write(Console.ReadLine().Sum(x=>x&'_'-'@'));
driis
fuente
1
En el segundo sin validación, puede reducir los caracteres aún más eliminando la declaración de variable s y utilizando Console.ReadLine () en línea.
hermiod
1

Perl (42 31)

perl -F -pale '$c+=ord(uc$_)-64for@F;$_=$c'

Espero contar F, p, a y l como 1 carácter fue correcto.

memowe
fuente
1

JavaScript, 68 bytes

Esto casi seguro se puede jugar más al golf

w=>[...w.toLowerCase()].map(v=>v.charCodeAt()-96).reduce((a,b)=>a+b)

Con comprobación de diccionario (Node.js y descendientes de Unix únicamente) 195 bytes

Usos /usr/share/dict/words, y definitivamente se puede acortar (ver el mensaje de advertencia)

w=>(require("fs").readFile("/usr/share/dict/words",(e,t)=>!(t+"").split`
`.includes(w=w.toLowerCase())&&console.warn(w+" not found in dict")),[...w].map(v=>v.charCodeAt()-96).reduce((a,b)=>a+b))
AlcaldeMonty
fuente
Para un mensaje de error, lo hace console.error(), no console.warn().
ericw31415
Pero el desafío decía advertir (5. (Opcional) verifique que la palabra esté en un diccionario después de anotar, e imprima una advertencia si no es así.) No significa ser pedante, pero el desafío especificó una advertencia
MayorMonty
@SpeedyNinja Creo que todavía cuenta, ese no es realmente el punto del desafío ...
Rɪᴋᴇʀ
@ EᴀsᴛᴇʀʟʏIʀᴋ es 1 carácter más corto;)
MayorMonty
@SpeedyNinja Tienes razón, leí mal.
ericw31415