HUISWERKOPGAVE: ISBN-13 Controle

Deze opgave dient tevens als voorbeeldopgave voor het deeltentamen 2XP05.

PROBLEEM

Controleer de ISBN-13 codes in een opgegeven tekstbestand.

Elk (echt) boek heeft een International Standard Book Number (ISBN). Een (nieuw) ISBN bestaat tegenwoordig uit dertien 'cijfers'. In de praktijk worden de cijfers in groepjes verdeeld met een streepje ('-') of spatie ertussen. Zo staat achter op het leuke Sinterklaas kado

Michael Jackson.
Software Requirements & Specifications : a lexicon of practice, principles and prejudices.
Addison-Wesley, 1995.

het ISBN-13 (onder de barcode) 978-0-201-87712-0 en op het uiterst nuttige boek

Steven S. Skiena.
The Algorithm Design Manual (Second Edition).
Springer, 2008.

staat 978-1-84800-069-8. (In tegenstelling tot de oude ISBN-10, kan in de nieuwe ISBN-13 geen letter 'X' meer voorkomen.)

Niet iedere combinatie van cijfers die lijkt op een ISBN-13 is ook een geldige ISBN-13. Stel dat de cijfers van links naar rechts gegeven zijn door a1a2...a13. Zo'n rijtje van 13 cijfers is een geldig ISBN-13 dan en slechts dan als de gewogen cijfersom

(som k: 1 <= k <= 13: wk * ak )

een 10-voud is, waarbij de weegfactoren wk = 1 of = 3 zijn al naar gelang k oneven of even is.

EXTRA UITDAGING: Ga na welke verwisselingen van buurcijfers niet ontdekt worden met de ISBN-13 code, en leg uit waarom dat zo is.

INVOER

Op standaardinvoer wordt een naamprefix (string van letters en/of cijfers) aangeboden, zeg xyz.

In het tekstbestand met naam xyz.txt (d.w.z. de naamprefix met daar achter .txt) staat op elke regel een code bestaande uit 13 cijfers, d.w.z. karakters van '0' t/m '9'.

M.n. komen er geen streepjes en spaties in voor.

UITVOER

De uitvoer moet geschreven worden naar een nieuw aan te maken tekstbestand met naam xyz-checked.txt.

In het uitvoerbestand wordt voor iedere regel uit het invoerbestand een regel geschreven met daarop

  • de code uit de invoer (13 cijfers)
  • gevolgd door één spatie en, hetzij de tekst OK als de invoer een geldig ISBN-13 is, of anders de tekst FOUT

Tenslotte wordt na al deze regels nog een tweetal regels geschreven met daarop wat statistieken:

  • eerst het aantal geldige codes gevolgd door één spatie en de tekst OK,
  • dan het aantal ongeldige codes gevolgd door één spatie en de tekst FOUT.

Zie ook het voorbeeld.

N.B. Het maakt verder niet zo uit wat uw programma op standaarduitvoer schrijft. M.n. wordt een slotregel als 'Tik <return> ...' geaccepteerd.

RESTRICTIES

U kunt er op rekenen dat het volgende geldt (uw programma hoeft dit dus niet te controleren):

  • De opgegeven naamprefix is een geldig onderdeel van een bestandsnaam.
  • Het opgegeven invoerbestand bestaat.
  • Het opgegeven uitvoerbestand bestaat nog niet.
  • Elke regel in het invoerbestand bevat één code van precies 13 cijfers. Er komen geen andere tekens in voor.
  • Het invoerbestand bevat minder dan 1000 (duizend) regels.

VOORBEELD

Standaard invoer isbn.txt isbn-checked.txt
isbn
9780201877120
9781848000698
9781848000697
9781848000968
9780201877120 OK
9781848000698 OK
9781848000697 FOUT
9781848000968 FOUT
2 OK
2 FOUT

ANALYSE

Het programma kan het best opgebouwd worden uitgaande van de structuur van het invoerbestand.

Aangezien er geen speciale afsluitende regel wordt gebruikt, is het eerste patroon van het college niet van toepassing en dient Eof gebruikt te worden.

Aangezien de invoerregels kort zijn en een duidelijke structuur hebben, kunnen ze in hun geheel ingelezen en dan pas verwerkt worden, zoals in het tweede patroon het geval is. (Maar met het derde patroon kan het natuurlijk ook.)

Aangezien het controleren van een code met zich mee brengt dat de gewogen som over al de cijfers bepaald wordt, zal een geneste repetitie nodig zijn (we gebruiken nog steeds geen zelf-gedefinieerde routines).

M.b.v. de standaadfunctie ord kan een teken (van een string ingelezen uit het het invoerbestand) omgezet worden in een volgnummer. Door het verschil te nemen met ord('0') krijg je de waarde van het betreffende teken. Zie ook de slides van het college.

De standaardfunctie odd(n) kan gebruikt worden om te bepalen of een geheel getal n oneven is. Dit kan uiteraard ook met de formule n mod 2 = 1.

ONTWERP

Inventariseer welke stappen te onderscheiden zijn, welke variabelen daarvoor nodig zijn en wat hun rol is.

Bij de analyse hebben we al gezien dat er een geneste repetitie aan te pas komt. De "binnenste" repetitie heeft een duidelijke eigen taak: de gewogen som bepalen van de ingelezen regel. Daarbij spelen een beperkt stel variabelen een rol.

CODEREN

Het is verstandig niet het hele programma in één keer in te tikken en dan pas te controleren. Bouw het op in wat kleinere stappen.

  1. Maak bijvoorbeeld eerst een programma dat de naam inleest, het invoerbestand opent en het uitvoerbestand creëert, de invoer regel voor regel doorleest en een kopie ervan in het uitvoerbestand schrijft. Controleer of dat goed werkt. Zorg meteen voor een nette opmaak en geschikt commentaar.
  2. Voeg vervolgens het stukje programma toe dat de gewogen som uitrekent en achter de code in het uitvoerbestand schrijft. Controleer ook dit.
  3. Neem daarna het stukje programma op dat aan de hand van de gewogen som bepaalt of de code al dan niet geldig is en schrijf de overkomstige uitvoer naar het bestand.
  4. Tenslotte kunnen variabelen en tellingen toegevoegd worden om de statistieken te bepalen en naar het uitvoerbestand te schrijven.

Denk ook aan de introductie van geschikte constanten.