Skip to main content
A check digit is an extra digit calculated from the rest of a number. Recalculate it, and if your answer doesn’t match the digit that’s there, the number was misread or mistyped. It tells you a number is damaged. It can’t tell you what the right number was, and it can’t tell you the number belongs to the product in front of you.

Decode one

Scan or paste a barcode and see every part of it.

Make one

Generate a valid barcode from fields.

Which method applies

2D barcodes go further than a check digit. Their error correction can rebuild data from a damaged symbol, not just detect the damage.

GS1 mod-10

Every GS1 number uses this method: GTINs of any length, and the SSCC on a pallet label.
  1. Leave the check digit aside. Starting from the digit next to it and working left, multiply the digits alternately by 3 and 1.
  2. Add up the results.
  3. Subtract the total from the next multiple of 10. The difference is the check digit (0 if the total is already a multiple of 10).
Working from the right is what makes one method fit every length. For a 13-digit number, the leftmost digit ends up multiplied by 1. For 12 or 8 digits, it’s multiplied by 3. EAN-13, 9521234567899: UPC-A, 061414100007: EAN-8, 95212340: ITF-14, 19521234567896: Adding zeros to the front of a number never changes its check digit, because the zeros add nothing to the total. That’s why a UPC-A keeps its check digit when it’s padded to 13 or 14 digits.

What it catches

Mod-10 catches every case of one wrong digit. It catches most cases of two neighboring digits swapped, but not when the two digits differ by 5: swapping a 1 and a 6, or a 2 and a 7, gives the same check digit.

Mod-11 for ISBN-10 and ISSN

Mod-11 uses a different weight for every position, counting down to 2.
  1. Multiply each digit by its weight. For an ISBN-10 the nine digits take weights 10 down to 2. For an ISSN the seven digits take weights 8 down to 2.
  2. Add up the results.
  3. Divide the total by 11 and take the remainder.
  4. Subtract the remainder from 11. That’s the check digit. If the answer is 10, write X. If it’s 11, write 0.
ISBN-10, 0-306-40615-2: The total is 130. Dividing by 11 leaves a remainder of 9, and 11 − 9 = 2. ISSN, 1234-5679: The total is 112. Dividing by 11 leaves a remainder of 2, and 11 − 2 = 9. Mod-11 is stronger than mod-10: it catches every single wrong digit and every swap of two neighboring digits. The price is the eleventh possible answer, which is why these numbers can end in X. Neither check digit appears in the barcode. A 13-digit ISBN and an ISSN barcode both end in a GS1 mod-10 check digit instead.

Code 128 mod-103

Every Code 128 barcode ends with a check character. It’s part of the symbol, not the data: scanners verify it and then discard it, so you never see it and never need to calculate it to read a barcode. You do need it to draw one. Each character has a value from 0 to 102. In code set B, which covers upper- and lowercase text, a character’s value is its ASCII code minus 32.
  1. Start with the value of the start character: 104 for code set B.
  2. Multiply each data character’s value by its position, counting from 1.
  3. Add everything up, divide by 103, and take the remainder. That’s the value of the check character.
For ZipZap: The total is 1585. Dividing by 103 leaves a remainder of 40, which in code set B is the character H. GS1-128 uses the same check character. The GTINs and SSCCs inside it also carry their own GS1 mod-10 check digits, so that data is checked twice.

Code 39 mod-43

Code 39 doesn’t require a check character, and most Code 39 barcodes don’t have one. Where it’s used, it’s the last character of the data, and it’s printed and sent like any other. Each of the 43 characters has a value: 0 to 9 are 0 to 9, A to Z are 10 to 35, then - . space $ / + % are 36 to 42.
  1. Add up the values of the characters.
  2. Divide by 43 and take the remainder. The character with that value is the check character.
For ZIPZAP: The total is 148. Dividing by 43 leaves a remainder of 19, which is the character J. With its check character the data is ZIPZAPJ. Nothing in the barcode says whether the last character is a check. Scanners have to be told, and so does your app: if you don’t know a label uses mod-43, J just looks like part of the data.

Validating in your app

A scanner has already verified the check digit of a UPC or EAN by the time your app sees the value. Checking it yourself matters for numbers that didn’t come from that kind of read:
  • numbers typed by hand
  • GTINs carried inside another barcode type, such as a QR code
  • scans from barcode types with an optional check, such as Code 39
ZipZapKit does this with one modifier. See Validation.