An implementation of the modulo 97 algorithm for calculating checksum avoiding use of large integers and allow operation in unsigned integers (< 2^31). Properties of congruence relations, more specifically this, give the correctnes of algorithm.
The project started to become acquainted with Span<T> to reduce costly string manipulations when calculating the checksum. Along the way I realized that it's possible without any allocations, so the use of ReadOnlySpan<char> in this case could just as well be replaced with char[]. The iterator IbanDigitizer could then strip the ref keyword which would allow to implement IReadOnlyCollection<int> and make for an even neater API.
Lets take iban number for a Croatian bank and disect the steps.
-
Move last four to the end
CR23015108410023612345 -> 015108410023612345CR23 -
Replace characters with digits
015108410023612345CR23 -> 015108410023612345122723 -
Start iteration over nine digit numbers
N = 0151084410, d = N % 97 = 78N = _78_0260123, d = N % 97 = 77N = _77_451227, d = N % 97 = 25N = _25_23, d = N % 97 = 1
-
If
d == 1then valid; otherwise invalid.
The implemention make us of a specialized "iterator" that perform step 1 and 2 without any allocations.