3650 - Perechi3

De la Universitas MediaWiki

Enunţ

Se dă un șir de numere hexazecimale, adică numere în care cele 16 cifre sunt din mulțimea {0,1,2,3,4,5,6,7,8,9,A,B,C,D,E,F}. Spunem că două numere se potrivesc dacă nu au cifre hexazecimale comune și împreună conțin toate cifrele în baza 16, cel puțin o dată. De exemplu, 24FFA032 și EDCB1998765 sunt numere care se potrivesc.

Cerința

Să se determine numărul perechilor de numere hexazecimale care se potrivesc.

Date de intrare

Fișierul de intrare perechi.in conține pe mai multe linii șirul de numere hexazecimale, deci numerele sunt separate prin spații sau enter.

Date de ieșire

Fișierul de ieșire perechi.out va conține un singur număr natural reprezentând numărul perechilor de numere care se potrivesc.

Restricții și precizări

  • În șir sunt cel puțin două numere și cel mult 200.000 de numere
  • Numerele conțin cel puțin o cifră și cel mult 30 de cifre
  • Cifrele hexazecimale de la 10 la 15 se scriu cu ajutorul literelor mari A, B, C, D, E, F.

Exemplul 1

perechi.in
24FFA032 EDCB1998765
24FA03 24FFA032 0
123456789ABCDEF12
perechi.out
4

Explicație

Cele patru perechi sunt: (24FFA032, EDCB1998765), (EDCB1998765, 24FA03), (EDCB1998765, 24FFA032) și (0, 123456789ABCDEF12).

Exemplul 2

perechi.in
G123 24FFA032 EDCB1998765
perechi.out
Date de intrare invalide!

Rezolvare

#3650 perechi3
def citeste_numere_hexazecimale(fisier):
  numere = []
  for linie in fisier:
    numere.extend(linie.split())
  return numere

def se_potrivesc(numar1, numar2):
  cifre1 = set(numar1)
  cifre2 = set(numar2)
  if any(cifra in cifre2 for cifra in cifre1):
    return False
  cifre_unite = cifre1.union(cifre2)
  return len(cifre_unite) == 16

def numara_perechi_potrivite(numere):
  count = 0
  for i in range(len(numere)):
    for j in range(i + 1, len(numere)):
      if se_potrivesc(numere[i], numere[j]):
        count += 1
  return count

def verifica_date_intrare(numere):
  if len(numere) < 2 or len(numere) > 200000:
    return False
  for numar in numere:
    if not all(caracter.isdigit() or caracter.upper() in "ABCDEF" for caracter in numar):
      return False
  return True

def main():
  with open("perechi.in", "r") as fin:
    numere_hexazecimale = citeste_numere_hexazecimale(fin)

  if not verifica_date_intrare(numere_hexazecimale):
    with open("perechi.out", "w") as fout:
      fout.write("Date de intrare invalide!")
    return

  numar_perechi_potrivite = numara_perechi_potrivite(numere_hexazecimale)

  with open("perechi.out", "w") as fout:
    fout.write(str(numar_perechi_potrivite))

if __name__ == "__main__":
  main()