Rechercher si une liste est un triple ABC

16

Trois entiers positifs A, B, C sont triples ABC s'ils sont premiers, avec A <B et satisfaisant la relation: A + B = C

Exemples :

  • 1, 8, 9 est un ABC-triple car ils sont premiers, 1 <8 et 1 + 8 = 9
  • 6, 8, 14 n'est pas parce qu'ils ne sont pas coprime
  • 7, 5, 12 n'est pas parce que 7> 5

Vous pouvez voir cette présentation de Frits Beukers 2005 pour plus de détails sur les triplets ABC.

Entrée sortie

Trois entiers, décimaux écrits. Peut être des valeurs séparées ou une liste. La sortie devait être une valeur véridique / fausse, que les trois entiers soient un triple ABC.

Remarque: Il est important de respecter l'ordre des entiers dans la liste, par exemple: 1, 8, 9n'est pas considéré comme la même liste 9, 1, 8ou toute autre combinaison. Le premier est donc un triple ABC et le second ne l'est pas.

Ainsi, A est le premier élément de la liste, B le deuxième et C le troisième.

Cas de test

Chacune des listes suivantes doit produire une valeur véridique

[1, 8, 9]
[2, 3, 5]
[2, 6436341, 6436343]
[4, 121, 125]
[121, 48234375, 48234496]

Chacune des listes suivantes doit afficher une valeur de falsey

[1, 1, 2]
[1, 2, 5]
[1, 9, 8]
[4, 12872682, 12872686]
[6, 8, 14]
[7, 5, 12]
David
la source
La sortie doit-elle être uniquement l'une des deux valeurs, ou pouvons-nous produire différentes valeurs de vérité / fausse pour différentes entrées?
Luis Mendo
Je pense que cela devrait être cohérent: votre code doit produire un type de valeurs de vérité / fausse quelle que soit l'entrée. Mais le couple vérité / fausse peut être ce que vous voulez en ce qui concerne le travail: différencier les listes.
david
Si nous prenons l'entrée comme une liste de trois valeurs, l'entrée doit-elle être dans l'ordre [A,B,C], ou sommes-nous également autorisés à prendre l'entrée dans l'ordre [C,B,A]ou [C,A,B]?
Kevin Cruijssen
Il faut respecter l'ordre car A <B est un critère du challenge.
david
1
Je ne pense pas que le fait d'exiger un ordre de liste particulier soit compatible avec le fait de permettre la saisie de valeurs distinctes, car les valeurs distinctes sont intrinsèquement non ordonnées et peuvent être considérées comme une liste .
Dennis

Réponses:

8

Gelée , 10 9 octets

Ṫ=S×</=g/

Essayez-le en ligne!

Comment ça fonctionne

Ṫ=S×</=g/  Main link. Argument: [a, b, c] (positive integers)

Ṫ          Tail; pop and yield c.
  S        Take the sum of [a, b], yielding (a + b).
 =         Yield t := (c == a + b).
    </     Reduce by less than, yielding (a < b).
   ×       Multiply, yielding t(a < b).
       g/  Reduce by GCD, yielding gcd(a, b).
      =    Check if t(a < b) == gcd(a, b).
Dennis
la source
8

Haskell , 48 38 29 octets

-10 octets en raison de TFeld de » gcdtruc!

-7 octets grâce à HPWiz pour avoir amélioré le test de co-primalité et repéré un espace superflu!

-2 octets grâce à nimi avoir proposé un infix-opérateur!

(a!b)c=a<b&&a+b==c&&gcd a b<2

Essayez-le en ligne!

Explication

Les deux premières conditions a < bet a + b == csont assez évidentes, le troisième utilisations qui gcd(a,b)=gcd(a,c)=gcd(b,c) :

Écrire gcd(a,c)=Ua+Vc utilisant l'identité de Bézout et en substituant c=a+b donne:

Ua+V(a+b)=(U+V)a+Vb

Puisque le gcd est la solution positive minimale à cette identité, il s'ensuit que gcd(a,b)=gcd(a,c) . L'autre cas est symétrique.

ბიმო
la source
1
De plus, je crois que vous n'avez besoin que de cela gcd a b==1. Depuis gcd a bdivise a+b=c. soitgcd(gcd a b)c=gcd a b
H.PWiz
@HPWiz: Ah oui, bien sûr, merci!
Éditera
7

Perl 6 , 33 32 octets

-1 octet grâce à nwellnhof

{(.sum/.[2]/2*[<] $_)==[gcd] $_}

Essayez-le en ligne!

Bloc de code anonyme qui prend une liste de trois nombres et renvoie Vrai ou Faux.

Explication

{                              }  # Anonymous code block
                       [gcd] $_   # Is the gcd of all the numbers
 (                  )==           # Equal to
  .sum        # Whether the sum of numbes
      /       # Is equal to
       .[2]/2 # The last element doubled
             *[<] $_   # And elements are in ascending order
Jo King
la source
2
32 octets
nwellnhof
5

Excel, 33 octets

=AND(A1+B1=C1,GCD(A1:C1)=1,A1<B1)
Wernisch
la source
4

bash, 61 octets

factor $@|grep -vzP '( .+\b).*\n.*\1\b'&&(($1<$2&&$1+$2==$3))

Essayez-le en ligne!

Entrée comme arguments de ligne de commande, sortie dans le code de sortie (produit également une sortie sur stdout comme effet secondaire, mais cela peut être ignoré).

The second part (starting from &&(() is pretty standard, but the interesting bit is the coprime test:

factor $@      # produces output of the form "6: 2 3\n8: 2 2 2\n14: 2 7\n"
|grep -        # regex search on the result
v              # invert the match (return truthy for strings that don't match)
z              # zero-terminated, allowing us to match newlines
P              # perl (extended) regex
'( .+\b)'      # match one or more full factors
'.*\n.*'       # and somewhere on the next line...
'\1\b'         # find the same full factors
Doorknob
la source
last && can be changed to & because of precedence
Nahuel Fouilleul
4

Java 10, 65 64 bytes

(a,b,c)->{var r=a<b&a+b==c;for(;b>0;a=b,b=c)c=a%b;return r&a<2;}

-1 byte thank to @Shaggy.

Try it online.

Explanation:

(a,b,c)->{        // Method with three integer parameters and boolean return-type
  var r=          //  Result-boolean, starting at:
        a<b       //   Check if `a` is smaller than `b`
        &a+b==c;  //   And if `a+b` is equal to `c`
  for(;b>0        //  Then loop as long as `b` is not 0 yet
      ;           //    After every iteration:
       a=b,       //     Set `a` to the current `b`
       b=c)       //     And set `b` to the temp value `c`
    c=a%b;        //   Set the temp value `c` to `a` modulo-`b`
                  //   (we no longer need `c` at this point)
  return r        //  Return if the boolean-result is true
         &a<2;}   //  And `a` is now smaller than 2
Kevin Cruijssen
la source
a==1 -> a<2 to save a byte.
Shaggy
@Shaggy Thanks!
Kevin Cruijssen
4

05AB1E, 12 11 10 bytes

Saved 1 byte thanks to Kevin Cruijssen

ÂÆ_*`\‹*¿Θ

Try it online! or as a Test Suite

Explanation

ÂÆ           # reduce a reversed copy of the input by subtraction
  _          # logically negate
   *         # multiply with input
    `        # push the values of the resulting list separately to stack
     \       # remove the top (last) value
      ‹      # is a < b ?
       *     # multiply by the input list
        ¿    # calculate the gcd of the result
         Θ   # is it true ?
Emigna
la source
Oops.. deleted my comment.. >.> So again: you can save a byte by using multiples instead of swaps with product: RÆ_*`\‹*¿Θ Test Suite.
Kevin Cruijssen
@KevinCruijssen: Thanks! Yeah, usually when you have that many swaps, you're doing something wrong :P
Emigna
3

Python 2, 69 67 63 62 55 bytes

lambda a,b,c:(c-b==a<b)/gcd(a,b)
from fractions import*

Try it online!


Python 3, 58 51 bytes

lambda a,b,c:(c-b==a<b)==gcd(a,b)
from math import*

Try it online!


-7 bytes, thanks to H.PWiz

TFeld
la source
is the gcd in gcd trick valid? What if a is not coprime with c?
Jo King
2
@jo-king If p divides a and c, it should divide c-a so b.
david
2
@JoKing: It is in this case, but not in general (you can prove it via Bezout's identity).
ბიმო
You can take it one step further and use gcd(a,b), since gcd(a,b) divides a+b
H.PWiz
@H.PWiz Thanks :)
TFeld
3

Japt, 16 14 13 11 bytes

<V¥yU «NÔr-

Try it

                :Implicit input of integers U=A, V=B & W=C
<V              :Is U less than V?
  ¥             :Test that for equality with
   yU           :The GCD of V & U
      «         :Logical AND with the negation of
       N        :The array of inputs
        Ô       :Reversed
         r-     :Reduced by subtraction
Shaggy
la source
Here is another 11 byte solution, though on closer inspection it isn't much different from yours in its actual logic.
Kamil Drakari
@KamilDrakari, had a variation on that at one stage, too. It could be 10 bytes if variables were auto-inserted when > follows ©.
Shaggy
3

JavaScript (ES6),  54 43 42  40 bytes

Thanks to @Shaggy for pointing out that we don't need to compute gcd(a,c). Saved 11 bytes by rewriting the code accordingly.

Takes input as 3 separate integers. Returns true for an ABC-triple, or either 0 or false otherwise.

f=(a,b,c)=>c&&a/b|a+b-c?0:b?f(b,a%b):a<2

Try it online!

Arnauld
la source
1
I don't think you need to test gcd(c,a).
Shaggy
@Shaggy Thanks! I've rewritten the code entirely.
Arnauld
3

Wolfram Language 24 30 28 26 bytes

With 2 bytes shaved by Doorknob. A further 2 bytes shaved off by @jaeyong sung

#<#2&&GCD@##==1&&#+#2==#3&
DavidC
la source
I think you should also be able to use CoprimeQ@## to save 2 bytes.
Doorknob
@Doorknob, If the first and second numbers are coprime, are they necessarily coprime with their sum?
DavidC
They are, but the original definition actually states that A, B, and C should be coprime. Most answers check only A and B just because it's usually shorter.
Doorknob
I think GCD@##==1 would save 2 bytes
jaeyong sung
2

C# (Visual C# Interactive Compiler), 90 bytes

n=>new int[(int)1e8].Where((_,b)=>n[0]%++b<1&n[1]%b<1).Count()<2&n[0]+n[1]==n[2]&n[0]<n[1]

Runs for numbers up to 1e8, takes about 35 seconds on my machine. Instead of calculating the gcd like others, the function just instantiate a huge array and filter the indexes that aren't divisors of a or b, and check how many elements are left. Next it check if element one plus element two equals element three. Lastly, it checks if the first element is less than the second.

Try it online!

Embodiment of Ignorance
la source
2

ECMAScript Regex, 34 bytes

Input is in unary, in the domain ^x*,x*,x*$ (repeated xs delimited by ,).

^(?!(xx+)\1*,\1+,)(x*)(,\2x+)\3\2$

Try it online! (.NET regex engine)
Try it online! (SpiderMonkey regex engine)

# see /codegolf/178303/find-if-a-list-is-an-abc-triple
^
(?!                # Verify that A and B are coprime. We don't need to include C in the
                   # test, because the requirement that A+B=C implies that A,B,C are
                   # mutually comprime if and only if A and B are coprime.
    (xx+)\1*,\1+,  # If this matches, A and B have a common factor \1 and aren't coprime.
)
(x*)(,\2x+)\3\2$   # Verify that A<B and A+B=C. The first comma is captured in \3 and
                   # reused to match the second comma, saving one byte.

The question does say "Three integers, decimal written", so this might not qualify (as it takes input in unary), but it makes for such an elegant pure regex that I hope it will at least be appreciated.

However, note that if the phrasing is to be literally interpreted, lambda and function submissions that take integer arguments are to be disqualified too, as to strictly adhere to the question's specification they would need to take the input in the form of a string.

Deadcode
la source
1

C# (.NET Core), 68 bytes

Without Linq.

(a,b,c)=>{var t=a<b&a+b==c;while(b>0){c=b;b=a%b;a=c;}return t&a<2;};

Try it online!

Destroigo
la source
1

Clean, 43 bytes

import StdEnv
$a b c=a<b&&a+b==c&&gcd a b<2

Try it online!

Similar to basically everything else because the direct test is the same.

Οurous
la source
1

Befunge-98 (FBBI), 83 bytes

&:&:03p&:04pw>03g04g\:v_1w03g04g+w1.@
00:    [email protected][^j7      _^;>0.@;j7;>0.@;:%g00\p

Try it online!

The input which is a triple of integers [A,B,C] is feeded into Befunge as space-separated integers C B A.

Wisław
la source
1

Mathematica 35 bytes

CoprimeQ @@ # && #[[1]] + #[[2]] == #[[3]] & 

if order is important:

CoprimeQ @@ # && Sort[#]==# && #[[1]] + #[[2]] == #[[3]] & 

or...

And[CoprimeQ @@ #, Sort@# == #, #[[1]] + #[[2]] == #[[3]]] &
David G. Stork
la source
1

Retina 0.8.2, 42 41 bytes

\d+
$*
A`^(11+)\1*,\1+,
^(1+)(,1+\1)\2\1$

Try it online! Link includes test cases. Edit: Saved 1 byte thanks to @Deadcode. Explanation:

\d+
$*

Convert to unary.

A`^(11+)\1*,\1+,

Check that A and B have no common factor.

^(1+)(,1+\1)\2\1$

Check that A < B and A + B = C.

Neil
la source
1
There appears to be a bug in your program. [121, 48234375, 48234496] is returning false.
Deadcode
1
@Deadcode Fixed, thanks for letting me know.
Neil
As with my regex, you can drop 1 byte by changing ^(1+),(1+\1),\1\2$ to ^(1+)(,1+\1)\2\1$.
Deadcode
1
@Deadcode Thanks! It's a shame that my use of Retina's A operation doesn't actually save me any bytes.
Neil
1
@Deadcode I'm using Retina's behaviour of turning the last regex into a positive assertion (actually a (count of) match stage) so moving the antigrep would cost me 5 bytes.
Neil