Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations John Tel on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

Mod 11 Function results

Status
Not open for further replies.

pkw25

MIS
Mar 20, 2002
46
IE

Hello

I have a public function setup as a module which appends a modulus 11 checkdigit to a number. The thing is I'm getting different results when the input is a number from a query field and when the input is just a manually entered number

eg.


anpostocr([Bank_Branch_Code])

yields 000021008

where Bank_Branch_Code = 000021

and

anpostocr (000021)

yields 0000213

The latter is the correct result.

Any help would be much appreciated.

Paraic

 
What data type is Bank_Branch_Code? Can you post the code of the function? That would be very helpful. Terry L. Broadbent - DBA
Computing Links:
faq183-874 contains "Suggestions for Getting Quick and Appropriate Answers" to your questions.
 
I have looked at your code for the Mod11 function previously. It expects a string (although the arg list did not specifically require it). While this posting appears to be passing a string, I suspect that what is passed is actually a "formatted" numeric value.

[tab][tab][tab][tab][tab][tab]OOPS!!

With a MINOR revision of the 'simplified' code I posted earlier, You get the 'correct' results, however I cammot reproduce your weird results (with the simplified code)

The two mods tot he simplified code are:

Change the argument type from string to Variant

Delete / Comment out the If (ISNUMERIC()) block (three lines near the top.

NOTE: You MUST supply a STRING argument - at least for leading zeroes!!!


MichaelRed
m.red@att.net

There is never time to do it right but there is always time to do it over
 

Thanks for your replies

In answering Terry's Question I don't honestly know what data type it is. Access is picking it off an SQL Server DB. It was actually an unused field that we populated with a new Number for customer Invoicing.

I tried your revised code Michael with the mods and again it works for me only on manual input. bank_branch_code is yielding different results even from the original version.

basMod11chk([bank_branch_code])

Yields 000000037489

Note: I've added the leading zero's using a format function in the query.

The logic I draw from this is that if the a manual entry of a number produces the correct results what's read from bank_branch_code is something other than a number eg. a string. I see there is a function to convert a number to a string but not vice-versa.
Below is the current function code. I don't know if I made your mods correctly. I put Variant in different places which yielded thje same results.

Again Thanks for your time.

Paraic

Public Function basMod11Chk(ChkChr As Variant) As Variant

'Michael Red 3/21/2002 Adapted from Tek-Tips thread

Dim Idx As Integer
Dim ChkSum As Long
Dim ChkVal As Integer
Dim Wgt As Long
Dim MyStr As Variant
Dim MyChr As Variant

' If (Not IsNumeric(ChkChr)) Then
' Exit Function
' End If

For Idx = Len(ChkChr) To 1 Step -1 'One Char at a time - BACKWARDS
MyChr = Mid$(ChkChr, Idx, 1)
Wgt = Val(MyChr) * (Len(ChkChr) - Idx + 2)
ChkSum = ChkSum + Wgt
Next Idx

ChkVal = (11 - (ChkSum Mod 11))

If (ChkVal >= 10) Then
ChkVal = ChkVal - 10 '---for case of 10 or 11
End If

basMod11Chk = ChkChr & Trim(Str(ChkVal))

End Function





 
Hmmmmmmmmmmmmmmmm ... mmmmmmmmmmmmmmmm ... mmmmmmmmmmm

I am truly lost in the wilderness. I have NO clue as to what input returns the value 000000037489

From your original statement (the other thread), It appears that the anpostocr function expects a string, so numeric inputs will generally not return the correct response. Even the case of numerics with leading zeroes would generally return an "incorrect" response, as the process would "Truncate" the leading zeroes in the calling argument, so the value 000021 would return the string "213" (correct check digit, but incorrect as it "lost" the leading characters).

I have (again!) revised the code to accomodate either Numeric or Character input, by changing the conditional at the top of the program logic to simply provide the conversion from Numeric to (an internal) string which is operated on. This will permit the function to OPERATE with either input - but does not (cannot) correct for the leading zeroes. This limitation could be overcome if htere were 'limits' which apply to the bank code field (e.g. always a fixed length 'integer' type). But any limitations /validation rules of this nature are not stated, so it would be PURE speculation to impose any such 'rule' on the input arg (or the return).


Just to be sure of the process, I've re-posted the complete revised code below, along with a simple test routine to illustrate the return values for various (assumed) input arg values. In the test prog, I placed the return values in the asignment statements for the test values as comments. Hopefully, this will help - so you can at least see the results. Note that I did NOT get the same return value for the lase 'error' - at least not from what I assumed the input to be.


Code:
Public Function basMod11Chk(ChkChr As Variant) As String

    'Michael Red    3/21/2002   Adapted from Tek-Tips thread

    Dim Idx As Integer
    Dim ChkSum As Long
    Dim ChkVal As Integer
    Dim Wgt As Long
    Dim MyStr As String
    Dim MyChr As String
    Dim MyChkChr As String

    If (IsNumeric(ChkChr)) Then
        MyChkChr = CStr(ChkChr)
     Else
        MyChkChr = ChkChr
    End If

    For Idx = Len(MyChkChr) To 1 Step -1     'One Char at a time - BACKWARDS
        MyChr = Mid$(MyChkChr, Idx, 1)
        Wgt = Val(MyChr) * (Len(MyChkChr) - Idx + 2)
        ChkSum = ChkSum + Wgt
    Next Idx

    ChkVal = (11 - (ChkSum Mod 11))

    If (ChkVal >= 10) Then
        ChkVal = ChkVal - 10 '---for case of 10 or 11
    End If

    basMod11Chk = ChkChr & Trim(str(ChkVal))

End Function


Public Function basTstMod11()

    Dim MyTestVal(5) As Variant

    MyTestVal(0) = "000021"             '0000213
    MyTestVal(1) = 21                   '213
    MyTestVal(2) = 21#                  '213
    MyTestVal(3) = 21.0000000000001     '21.00000000000013
    MyTestVal(4) = 3748                 '37486
    MyTestVal(5) = "00000003748"        '000000037486

    For Idx = 0 To UBound(MyTestVal)
        If (MyTestVal(Isx) <> &quot;&quot;) Then
            Debug.Print MyTestVal(Idx), basMod11Chk(MyTestVal(Idx))
        End If
    Next Idx


End Function
MichaelRed
m.red@att.net

There is never time to do it right but there is always time to do it over
 

I've tried the your revised function but the result is still the same ie.
000000037489 for bank_branch_code = 000021
Your'e right in that the leading zero's are lost. I've used the format command to append them again plus additional one's that I require.
Below is the query field.

SerialCode: Format(basMod11Chk([bank_branch_code]),&quot;000000000000&quot;)

There's something else that we are not seeing here

Paraic
 
O.K., but I (obviously?) cannot see it from here. My sample tests DO NOT return the weirdness, so something is lost in the translation. As you can see from the 'test' program, the oprocedure is quitw capable of returning the 'correct' value when called with a parameter argument.


MichaelRed
m.red@att.net

There is never time to do it right but there is always time to do it over
 

I've finally got the right result. I went back to the original version and converted the input argument to a string for all cases - See below.
The manual entry of a number in brackets must be a string where I thought it was a number.
I could'nt your modified code to work buy then my coding skills are fairly Basic.

Anyway thanks for help, I've certainly learned something in the process.

Paraic.


Public Function anpostocr(Checkdigit)
'--checkdigit$ = Command$

Dim checkarray(40)
Dim weight(40)

CheckdigitST = Str(Checkdigit) '-- convert to string

lent = Len(CheckdigitST) '--get lenght of string

For I = 0 To (lent - 1) '--split up string digit by digit & put in array
checkarray(I + 2) = Val(Mid$(CheckdigitST, (lent - I), 1))
Next I

For I = 2 To lent + 1 '--calculate the weights for each digit
weight(I) = (checkarray(I) * I)
sum = sum + weight(I)
Next I
'--sum now holds value we need
Checkdigit = 11 - (sum Mod 11)
If Checkdigit >= 10 Then Checkdigit = Checkdigit - 10 '---for case of 10 or 11
checkarray(1) = Checkdigit '--add the checkdigit to the

'-- for debug only-- PRINT &quot; CheckDigit is > &quot;; checkdigit

For I = (lent + 1) To 1 Step -1 '--go through the array backwards & rebuild string with check digit attached
checkout$ = checkout$ + LTrim$(Str$(checkarray(I)))
Next I

Checkdigit = checkout$
anpostocr = checkout$

'--Print checkout$
End Function
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top