Détectez les plaques d'immatriculation presque parfaites

15

Remarque: Ceci est inspiré par cette question de @Willbeing où la tâche consistait à compter le nombre d'assiettes parfaites d'une certaine longueur, mais c'est légèrement différent.


Nous appelons une plaque d'immatriculation parfaite cette plaque dont le texte satisfait aux conditions suivantes:

  • Il se compose de caractères, qui peuvent être des lettres majuscules ( [A-Z]) ou des chiffres ( [0-9])
  • En additionnant les positions de ses lettres dans l'alphabet anglais, 1-indexé (ie:) A=1,B=2,...,Z=26donne un entier n
  • Obtenir chaque bloc de chiffres, les additionner puis multiplier tous les résultats donne le même résultat, n
  • n est un carré parfait (par exemple: 49 (7 2 ) , 16 (4 2 ) )

Une plaque d'immatriculation presque parfaite remplit les conditions d'une plaque d'immatriculation parfaite, sauf que n n'est pas un carré parfait.


Contribution

Une chaîne représentant le texte de la plaque d'immatriculation, prise en entrée sous n'importe quelle forme standard, à l'exception du codage en dur.

Production

Si la chaîne donnée représente une plaque d'immatriculation presque parfaite , retournez une valeur vraie (par exemple: True/ 1), sinon retournez une valeur fausse (par exemple: False/ 0). Toute forme standard de sortie est acceptée tout en prenant note que ces failles sont strictement interdites.


Exemples

licence plate -> output


A1B2C3 -> 1

A + B + C = 1 + 2 + 3 = 6
1 * 2 * 3 = 6 
6 is not a perfect square, 6 = 6 => nearly perfect plate

01G61 -> 1

(0 + 1) * (6 + 1) = 7
G = 7
7 is not a perfect square, 7 = 7 => nearly perfect plate

11BB2 -> 0

(1 + 1) * 2 = 4
B + B = 2 + 2 = 4
4 = 4, but 4 is the square of 2 => perfect license plate (not what we want)

67FF1 -> 0

(6 + 7) * 1 = 13
F + F = 6 + 6 = 12
12 != 13 => not perfect at all!

Notation

C'est le , donc la réponse la plus courte en octets l'emporte!

M. Xcoder
la source
Je pense que ce serait mieux comme code-golf .
Erik the Outgolfer le
Permettez-moi de m'assurer que je comprends cela. Nous ne produisons vrai que si la plaque d'immatriculation est parfaite et nn'est pas un carré parfait?
junkie en mathématiques du
@mathjunkie Oui. TL; DR: seulement si la licence est presque parfaite (PS désolé pour la réponse tardive)
M. Xcoder
1
Avant que quiconque ne s/licence/license/igle fasse , sachez que «licence» est l'orthographe correcte en anglais britannique (ainsi qu'en anglais dans d'autres parties du monde).
Mego

Réponses:

7

Gelée , 29 28 30 octets

1 octet pour corriger un bug repéré par ChristianSievers ( à tort traitant de sous - chaînes de zéros seulement) 1 octet pour corriger les faux positifs pour "0", "00"... trouvé au - dessus de fixation (0 est un carré parfait).

i@€ØAS;Ʋ$
e€ØAœpV€€LÐfS€P;0⁼Ç

Essayez-le en ligne! ou exécuter des tests

Comment?

i@€ØAS;Ʋ$ - Link 1: [letter-sum, letter-sum is perfect square?]: plate
i@€        - index of €ach char in plate [reversed @rguments] (1-based, 0 otherwise) in:
   ØA      -     uppercase alphabet
     S     - sum
         $ - last two links as a monad:
      ;    -     concatenate with:
       Ʋ  -         is square?

e€ØAœpV€€LÐfS€P;0⁼Ç - Main link: plate                        e.g. "11BB2"
    œp              - partition plate at truthy values of:
e€                  -     is in? for €ach char in plate:
  ØA                -         uppercase alphabet                   [['1','1'],[''],['2']]
      V€€           - evaluate for €ach for €ach                   [[1,1],[],[2]]
          Ðf        - filter keep:
         L          -     length                                   [[1,1],[2]]
            S€      - sum each                                     [2,2]
              P     - product                                      4
               ;0   - concatenate a zero                           [4,0]
                  Ç - last link (1) as a monad (taking plate)      [4,1]
                 ⁼  - equal? (non-vectorising)                     0
Jonathan Allan
la source
Wow, solution géniale de gelée!
M. Xcoder du
Et alors 11AA0?
Christian Sievers
@ChristianSievers, bonne prise. Correction d'un autre bug lié au genre et extension de la suite de tests.
Jonathan Allan
7

MATL, 36 34 33 35 octets

3Y432YXU"@V!Usvp]GlY2&msy=wtQ:qUm~v

Essayez-le sur MATL Online

Explication

        % Implicitly grab input as a string
3Y4     % Push the predefined literal '[A-Za-z]+' to the stack
32      % Push the literal 32 to the stack (ASCII for ' ')
YX      % Replace the matched regex with spaces (puts a space in place of all letters)
U       % Convert the string to a number. The spaces make it such that each group of
        % of consecutive digits is made into a number
"       % For each of these numbers
  @V!U  % Break it into digits
  s     % Sum the digits
  v     % Vertically concatenate the entire stack
  p     % Compute the product of this vector
]       % End of for loop
G       % Explicitly grab the input again
lY2     % Push the predefined literal 'ABCD....XYZ' to the stack
&m      % Check membership of each character in the input in this array and 
        % return an array that is 0 where it wasn't a letter and the index in 'ABC..XYZ'
        % when it was a letter
s       % Sum the resulting vector
y       % Duplicate the product of the sums of digits result
=       % Compare to the sum of letter indices result
w       % Flip the top two stack elements
Q       % Add one to this value (N)
t:      % Duplicate and compute the array [1...N]
q       % Subtract 1 from this array to yield [0...N-1]
U       % Square all elements to create all perfect squares between 1 and N^2
m~      % Check to ensure that N is not in the array of perfect squares
v       % Vertically concatenate the stack.
        % Implicitly display the truthy/falsey result
Suever
la source
Donne des faux positifs pour les plaques composées uniquement de zéros, par exemple '0'ou '00'(FWIW je viens de corriger cela dans mon code aussi).
Jonathan Allan
1
@JonathanAllan Mis à jour.
Suever
6

Python 2, 120 118 octets

s=t=p=0;r=1
for n in input():
 h=int(n,36)
 if h>9:s+=h-9;r*=t**p
 p=h<10;t=(t+h)*p
print(s==r*t**p)&(int(s**.5)**2<s)

Essayez-le en ligne!

Interprète chaque caractère comme un nombre en base-36 ( h). Convertit en décimal et ajoute à la somme if h>9(ce qui signifie qu'il s'agit d'une lettre), sinon ajoute à une variable qui est multipliée pour former le produit en cours d'exécution plus tard.

accro aux mathématiques
la source
4

Perl 5 , 80 octets

79 octets de code + -pindicateur.

$.*=eval s/./+$&/gr for/\d+/g;$t-=64-ord for/\pl/g;$_=$.==$t&&($.**.5|0)**2!=$.

Essayez-le en ligne!

$.*=eval s/./+$&/gr for/\d+/g;multiplie les sommes de chiffres consécutifs. (J'utilise $.parce que sa valeur initiale est 1, ce qui signifie que c'est l'élément neutre pour la multiplication). Plus précisément, pour chaque bloc de chiffres ( for/\d+/g), s/./+$&/grplace un +avant chaque chiffre, puis la chaîne est evaluée et multipliée par le produit actuel.
Deuxièmement, les $t-=64-ord for/\pl/g;sommes dans $tchaque lettre ( for/\pl/g). ( ordretourne le code ascii de la lettre, et le 64-..fait entre 1 et 26.
Enfin, $.==$tvérifie que les deux valeurs sont les mêmes, et ($.**.5|0)**2!=$.que ce n'est pas un carré parfait.

Dada
la source
4

Python 2, 267 207 octets

60 octets enregistrés grâce aux ovs

import re
def g(l):a=reduce(lambda a,b:a*b,[sum(map(int,list(i)))for i in re.sub(r'\D',' ',l).split()],1);return a==sum(sum(k)for k in[[ord(i)-64for i in x]for x in re.sub(r'\d',' ',l).split()])and a**.5%1>0

Fonction avec usage: print(g('A1B2C3'))

Essayez-le en ligne!

M. Xcoder
la source
4

Python 3 , 163 156 155 155 164 161 octets

from math import*
m=1;s=t=p=0
for x in input():
 try:t+=int(x);p=1
 except:m*=[1,t][p];p=t=0;s+=ord(x.upper())-64
if p:m*=t
print(m==s and sqrt(m)!=int(sqrt(m)))

Essayez-le en ligne!

  • économisé 7 octets grâce à Jonathan et Shooqie
  • 1 octet enregistré: également résolu le problème des faux positifs. Merci à Jonathan de l' avoir signalé!
  • ajout de 11 octets: l'édition précédente était incorrecte (la multiplication de la somme des chiffres se faisait dans une boucle indésirable)
officialaimm
la source
1
from math import*est plus court
shooqie
1
Vous n'avez pas besoin a, utilisez simplement for x in input():. Vous pouvez avoir des faux positifs pour les plaques se terminant par une chaîne de zéros (par exemple 11AA00), car la finale m*=tn'est pas exécutée.
Jonathan Allan
1
Apparemment, mon code montre un faux positif pour n'importe quelle chaîne contenant des zéros isolés (3A0B est également montré vrai) ... Merci d'avoir souligné cela @JonathanAllan. Je vais essayer de le réparer.
officialaimm
Vérifiez la version la plus récente ... J'ai ajouté une nouvelle variable indicateur 'p' pour décider de multiplier ou non la somme des chiffres.
officialaimm
3

Rétine, 143 octets

Renvoie 1 pour vrai, 0 pour faux

[1-9]
$ *
10 | 01
1
S_` (\ D)
O`
{`1 (? = 1 * \ n (1+))
1 $
) 2 = `1 + \ n

[JS]
1 $ +
[TZ]
2 $ +
T`0L`ddd
1> `\ d + \ n?
$ *
^ ((? (1) ((? (2) \ 2 (11) | 111)) | 1)) * \ n

^ (1 *) \ n \ 1 $

Essayez-le en ligne!

Explication:

[1-9]
$ *
10 | 01
1

Tout d'abord, nous remplaçons tous les chiffres non nuls par leur représentation unaire. Nous supprimons tous les zéros avec un chiffre adjacent afin qu'ils n'affectent pas nos opérations unaires

S_` (\ D)

Fractionnez la chaîne résultante sur les lettres, en prenant soin d'exclure les lignes vides (c'est un problème lorsque deux lettres sont consécutives AA).

O`
{`1 (? = 1 * \ n (1+))
1 $
) 2 = `1 + \ n

Triez la chaîne lexicographiquement. Effectuez ensuite plusieurs fois les opérations suivantes:

1) Remplacez chacun 1par le nombre de 1s sur la ligne suivante (cela imite la multiplication)

2) Retirez la deuxième ligne de 1s

[JS]
1 $ +
[TZ]
2 $ +
T`0L`ddd

Remplacer les lettres J-Savec 1J, 1Ketc. et remplacer les lettres T-Zavec 2T, 2Uetc. Ensuite, remplacer chacun des groupes A-I, J-Set T-Zavec 1-9. Il nous restera la valeur numérique de chaque lettre (par exemple 13pour M).

1> `\ d + \ n?
$ *

Convertissez chaque ligne sauf la première en unaire (la première ligne est déjà en unaire). Concatène ces lignes. Il nous reste maintenant une chaîne du formulaire <product of digits>\n<sum of letters>.

^ ((? (1) ((? (2) \ 2 (11) | 111)) | 1)) * \ n

Remplacez un nombre carré par la chaîne vide. Celui-ci utilise la méthode "arbre de différence" .

^ (1 *) \ n \ 1 $

Retourne 1si les deux cordes de chaque côté du \nmatch. Sinon, revenez 0.

accro aux mathématiques
la source
Les faux positifs pour 11AA0, 0AA11etc.
Allan Jonathan
@JonathanAllan Merci! Cela m'a coûté 11 octets à réparer
junkie mathématique