Combien de syllabes dans ce nombre?

15

Je serais ravi de prendre un certain nombre et de savoir combien de syllabes il y a, lorsqu'il est parlé en anglais.

Limitons cela à des entiers positifs inférieurs à mille.

Je suis britannique, nous allons donc suivre la colonne des centaines avec un «et» quand il y aura des chiffres non nuls après.

Le défi

  • Écrivez un code qui acceptera un entier positif inférieur à 1000 et affichera le nombre de syllabes dans les mots qui représentent ce nombre en anglais britannique.
  • Il N'A PAS besoin de générer les mots pour représenter les nombres, seulement le nombre de syllabes qu'ils contiennent.
  • C'est du golf de code, essayez d'y parvenir dans le moins d'octets.
  • Utilisez n'importe quelle langue que vous aimez.
  • Les failles standard sont interdites.

Cas de test

|  N  | In words                             | Syllables |
|   1 | one                                  |         1 |
|   2 | two                                  |         1 |
|   3 | three                                |         1 |
|   4 | four                                 |         1 |
|   5 | five                                 |         1 |
|   6 | six                                  |         1 |
|   7 | sev-en                               |         2 |
|   8 | eight                                |         1 |
|   9 | nine                                 |         1 |
|  10 | ten                                  |         1 |
|  11 | el-ev-en                             |         3 |
|  12 | twelve                               |         1 |
|  13 | thir-teen                            |         2 |
|  14 | four-teen                            |         2 |
|  17 | se-ven-teen                          |         3 |
|  20 | twen-ty                              |         2 |
|  21 | twen-ty one                          |         3 |
|  42 | four-ty two                          |         3 |
|  73 | sev-en-ty three                      |         4 |
|  77 | sev-en-ty sev-en                     |         5 |
| 100 | one hund-red                         |         3 |
| 110 | one hund-red and ten                 |         5 |
| 111 | one hund-red and el-ev-en            |         7 |
| 555 | five hund-red and fif-ty five        |         7 |
| 700 | sev-en hund-red                      |         4 |
| 770 | sev-en hund-red and sev-en-ty        |         8 |
| 777 | sev-en hund-red and sev-en-ty sev-en |        10 |
| 999 | nine hund-red and nine-ty nine       |         7 |
AJFaraday
la source
1
Pouvons-nous prendre l'entrée comme une chaîne ou un tableau de chiffres?
Dennis

Réponses:

11

Python 2 , 84 83 74 67 octets

lambda n:4*(n>99)+2-n%~9/9-0x55561aaaab/4**(n%100)%4+`n`.count('7')

Merci à @xnor d'avoir joué à 9 16 octets!

Essayez-le en ligne!


Python 2 , 79 octets

lambda n:4*(n>99)+([-1]+10*[1]+[3,1]+7*[2]+8*([2]+9*[3]))[n%100]+`n`.count('7')

Simple, mais plus long.

Essayez-le en ligne!

Dennis
la source
Pour votre solution de 83 octets, vous pouvez couper 3 octets en passant -10à ~9et en basculant autour du dernier bit en +(0<n%100!=12)-(n%100!=11), mais c'est toujours plus long que votre nouvelle solution.
xnor
@xnor C'est vraiment intelligent! min(n%100,13)%12/~9pourrait en fait aider avec une approche que j'essayais également pour ma réponse Jelly.
Dennis
En fait, simplement pousser les choses dans une constante codée en dur s'avère plus court.
xnor
@xnor Merci encore!
Dennis
8

Perl 5 -p , 53 octets

$_=4*/.../+2*/[^0].$/+!/0$/+y/7//-/1[^1]$/-/12$/-/00/

Essayez-le en ligne!

Comment

-p commandline flag reads input into $_

$_=4*/.../     # Hundreds place has minimum of 4 sylables (__ HUN-DRED AND),
               # match fails on number <100, and would add 0 here
  +2*/[^0].$/  # Tens place has two syllables if not 0 (__-TY or __TEEN),
               # match fails on numbers <10, and would add 0
  +!/0$/       # Ones place has one syllable if not 0 (__)
               # -- Now adjust for special cases --
  +y/7//       # add a syllable for every 7 present
  -/1[^1]$/    # remove a syllable for 10-19, except 11
  -/12$/       # remove another syllable for 12
  -/00/        # remove the syllable for AND if it's an even hundred

-p commandline flag outputs contents of $_
Xcali
la source
7

JavaScript (ES6), 89 octets

n=>(s='01111112111312222322',n>99&&+s[n/100|0]+3-!(n%=100))+~~(s[n]||+s[n/10|0]-~s[n%10])

Essayez-le en ligne!

Arnauld
la source
7

Python 2 , 112 108 octets

f=lambda n:n>99and f(n/100)+3+f(n%100)-(n%100<1)or n>19and f(n/10)-~f(n%10)or int("01111112111312222322"[n])

Essayez-le en ligne!

-4 octets, merci à Shaggy

TFeld
la source
2
De plus, votre [2]*7partie échouera 17, car cela devrait être 3 au lieu de 2 ( sev-en-teen).
Kevin Cruijssen
2
-4 octets , y compris un correctif pour 17.
Shaggy
@Shaggy Thanks :)
TFeld
@KevinCruijssen Fixé maintenant (grâce à Shaggy)
TFeld
6

Langue Wolfram 101 115 octets

s=StringSplit;Length[Join@@(WordData[#,"Hyphenation"]&/@Join@@s/@
s[IntegerName@#,"-"])]+Boole[#>100&&#~Mod~100!=0]&

Explication

(remplacement StringSplitde s)

Length[Join@@(WordData[#,"Hyphenation"]&/@Join@@
StringSplit/@ StringSplit[IntegerName@#,"-"])]+Boole[#>100&&#~Mod~100!=0]&

IntegerNamerend le nombre en anglais américain (c'est-à-dire sans "et" inclus dans les nombres supérieurs à 100) 777-> "seven hundred seventy-seven.

StringSplit[IntegerName@#,"-"] supprime tous les tirets du rendu.

StringSplit/@ divise le rendu en mots.

Join@@ laisse une simple liste de mots, sans liste intégrée (dans le cas où un trait d'union est apparu).

WordData[#,"Hyphenation"] décompose un seul mot en ses syllabes.

Join@@ laisse une simple liste de syllabes dans tous les mots.

Length compte les syllabes

+Boole[#>100&&#~Mod~100!=0]ajoute 1au nombre de syllabes pour les nombres supérieurs à 100 (en raison des «et» supplémentaires utilisés dans le rendu anglais britannique), à ​​l'exclusion des multiples entiers de 100.

DavidC
la source
6

Java 11, 105 102 octets

n->(""+"".repeat(8)).charAt(n%100)+(n+"").split("7",9).length-(n>99?2:6)

Contient des charges de caractères non imprimables.

-3 octets merci @ OlivierGrégoire .

Essayez-le en ligne.

Explication:


n->               // Method with integer as both parameter and return-type
  (""
                  //  Push string with ASCII-value digits 46666666666867777777
 +"".repeat(8))
                  //  Appended with 8 times a string with ASCII-value digits 7888888888
   .charAt(n%100) //  Take the (input modulo-100)'th character of this string (as integer)
  +(n+"").split("7",9).length
                  //  Count the amount of 7s in the input + 1
  -(n>99?         //  And if the input is larger than 99:
     2            //   Subtract 2 (-1 for the 7s+1 count; -5 to map the ASCII-digits to:
                  //               4 → -1; 6 → 1; 7 → 2; 8 → 3;
                  //               and +4 for the inputs above 99)
    :             //  Else:
     6)           //   Subtract 6 (-1 for the 7s+1 count and -5 to map the ASCII-digits to:
                  //               4 → -1; 6 → 1; 7 → 2; 8 → 3)
Kevin Cruijssen
la source
1
102 octets en passant .split("7",-1)à .split("7",9)et -6+(n>99?4:0)à -(n>99?2:6).
Olivier Grégoire
1
@ OlivierGrégoire Merci. Complètement raté -(n>99?2:6), mais c'est tellement évident maintenant que vous l'avez souligné. Et -1à 9cause de la taille d'entrée limitée à laquelle je n'aurais pas pensé, alors merci!
Kevin Cruijssen
5

05AB1E , 34 31 octets

т%U7¢I€Ā`Iт@3*X_(X20@X12Q(X11QO

Essayez-le en ligne ou vérifiez tous [1,999]les cas de test .

Explication:

Avec tous les contrôles mentionnés, il en résultera 1 pour truey et 0 pour falsey.

т%         # Take modulo-100 of the (implicit) input
           #  i.e. 710 → 10
  U        # Pop and store it in variable `X`
7¢         # Count the amount of 7s in the (implicit) input
           #  i.e. 710 → 1
I€Ā        # Trutify each digit in the input (0 if 0; 1 otherwise)
   `       # And push all of the mapped values to the stack
           #  i.e. 710 → [1,1,0]
Iт@        # Check if the input is larger than or equal to 100
           #  i.e. 710 → 1 (truthy)
   3*      # Multiply that result by 3 (for 'hund-red and')
           #  i.e. 1 → 3
X_         # Check if variable `X` is 0
           #  i.e. 10 → 0 (falsey)
  (        # And negate that (to remove 'and' when #00)
           #  i.e. 0 → 0
X20@       # Check if variable `X` is larger than or equal to 20 (for '-ty')
           #  i.e. 10 → 0 (falsey)
X12Q       # Check if variable `X` is exactly 12
           #  i.e. 10 → 0 (falsey)
    (      # And negate that (to remove 'teen')
           #  i.e. 0 → 0
X11Q       # Check if variable `X` is exactly 11 (for 'el-ev-en' minus 'one one')
           #  i.e. 10 → 0 (falsey)
O          # Sum everything on the stack (and output implicitly)
           #  i.e. [1,1,1,0,3,0,0,0,0] → 6
Kevin Cruijssen
la source
Cela échoue au cas de test 700. 'Seven Hundred' a 4 syllabes, cela renvoie 5.
AJFaraday
@AJFaraday devrait être corrigé maintenant. Accidentellement eu I(entrée) au lieu de X(entrée mod 100) lors de la vérification si elle est supérieure à 20 pour le +1 de ty.
Kevin Cruijssen
Je suis vraiment désolé, il renvoie 0 pour 'cent'
AJFaraday
@AJFaraday Fixed again .. >(vérifier si l'entrée est supérieure à 100) a été remplacé par @(vérifier si l'entrée est supérieure ou égale à 100). Peut-être que j'aurais dû vérifier moi-même plus de cas de test avant de poster .. Désolé à ce sujet ..
Kevin Cruijssen
4
Au fait, aimer le chapeau haut de forme sur un cube rubix!
AJFaraday
5

Fusain , 39 31 octets

I⁻⁺↨E謬Iι²№θ7I§⁺”)∨∧⌈a¡↶”×0⁸⁰N

Essayez-le en ligne! Le lien est vers la version détaillée du code. Explication:

I⁻⁺

Calculez les ajustements du nombre de syllabes et sortez le résultat sous forme de chaîne.

↨E謬Iι²

Commencez par changer chaque chiffre non nul en 1 puis décodez-le en base 2. Cela donne la bonne réponse pour la plupart des entrées.

№θ7

Ajoutez 1 pour chacun 7.

I§⁺”)∨∧⌈a¡↶”×0⁸⁰N

Prenez la chaîne littérale 10000000001021111111et ajoutez 80 zéros, puis indexez cycliquement par l'entrée et soustrayez ce chiffre.

Neil
la source
4

Gelée , 28 25 23 octets

9ḊŻ;2+⁵Żċ%ȷ2$ạDṠḄƊ+Dċ7Ɗ

Essayez-le en ligne!

Comment ça fonctionne

9ḊŻ;2+⁵Żċ%ȷ2$ạDṠḄƊ+Dċ7Ɗ  Main link. Argument: n (integer in [1, ..., 999])

9                        Set the return value to 9.
 Ḋ                       Dequeue; yield [2, 3, 4, 5, 6, 7, 8, 9].
  Ż                      Zero; yield [0, 2, 3, 4, 5, 6, 7, 8, 9].
   ;2                    Concat 2, yield [0, 2, 3, 4, 5, 6, 7, 8, 9, 2].
     +⁵                  Add 10; yield [10, 12, 13, 14, 15, 16, 17, 18, 19, 12].
       Ż                 Zero; yield [0, 10, 12, 13, 14, 15, 16, 17, 18, 19, 12].
         %ȷ2$            Yield n % 1e2.
        ċ                Count the occurrences of the modulus in the array.
                 Ɗ       Combine the three links to the left into a monadic chain.
              D            Decimal; convert n to its array of digits in base 10.
               Ṡ             Take the sign of each decimal digit (0 or 1).
                Ḅ            Convert the array of signs from base 2 to integer.
             ạ           Compute the abs. difference of the results to both sides.
                      Ɗ  Combine the three links to the left into a monadic chain.
                   D       Decimal; convert n to its array of digits in base 10.
                    ċ7     Count the number of 7's.
Dennis
la source
3

PHP , 190 158 145 141 137 octets

<?for($j=$p=0;$p<strlen($i=$argv[1]);)$j+=str_split($i)[$p++]>0;echo$j+substr_count($i,7)+3*($i>99)-!($i%=100)+($i>19)-($i==12)+($i==11);

Essayez-le en ligne!

Un portage de la solution de Kevin Cruijssen (malheureusement il n'a pas la même brièveté en PHP :))

- 32 45 merci à Shaggy!

-3 merci à Kevin Crujissen!

NK1406
la source
Tant d'économies à réaliser ici! En voici quelques-unes très rapides
Shaggy
1
145 octets . Vous pouvez enregistrer quelques octets supplémentaires à l'aide de balises courtes, mais je ne me souviens pas comment les utiliser sur TIO. (Remarque: je suis sur mon téléphone, je n'ai donc pas testé toutes les entrées.)
Shaggy
1
@Shaggy 2 octets supplémentaires peuvent être modifiés lors de l'utilisation de >99et à la >19place de >=100et >=20.
Kevin Cruijssen
1
@KevinCruijssen en fait qui économise 3 octets car il passe de 100 à 99 :)
NK1406
J'ai également réussi à enregistrer un autre octet en plaçant la variable au début de l'écho.
NK1406
2

05AB1E , 24 octets

Réponse de gelée du port de Dennis

8L>Ć¾šT+¾šsт%¢sSĀJCαs7¢+

Essayez-le en ligne! ou comme suite de tests

Explication

8L>                       # push range [2 ... 9]
   Ć                      # enclose, append head
    ¾š                    # prepend 0
      T+                  # add 10 to each
        ¾š                # prepend 0
          sт%¢            # count occurrences of input % 100 in this list
              sS          # push input split into a list of digits
                Ā         # truthify, check each if greater than 0
                 JC       # convert from base-2 to base-10
                   α      # absolute difference
                    s7¢+  # add the amount of 7's in the input
Emigna
la source
1

05AB1E , 26 octets

€ĀJCI7¢•Ž¢Γ}Þ±6u•¾80׫Iè(O

Réponse de Port of @Neil Charcoal , alors assurez-vous de lui aussi voter positivement si vous aimez cette réponse!

Essayez-le en ligne ou vérifiez tous les cas de test .

Un entier compressé •Ž¢Γ}Þ±6u•peut également être •8JA•b2TÌǝpour le même nombre d'octets.

Explication:

€Ā                   # Trutify every digit in the (implicit) input
                     # (0 remains 0; everything else becomes 1)
  J                  # Join it together to a single string
   C                 # Convert from binary to integer
I7¢                  # Count the amount of 7s in the input
•Ž¢Γ}Þ±6u           # Push compressed integer 10000000001021111111
          ¾80׫      # Append 80 "0"s
               Iè    # Index the integer (with automatic wraparound) into it
                 (   # Negate the result
O                    # Sum all values on the stack (and output implicitly)

Voir cette réponse 05AB1E de mes (section Comment compresser les grands entiers? ) Pour comprendre pourquoi •Ž¢Γ}Þ±6u•est 10000000001021111111.

Kevin Cruijssen
la source