String is Not Numeric - crystal-reports

Having an issue when attempting to run a Mod formula against a field. I keep receiving the error "String is Not Numeric" and so far I have not been able to get ToNumber to correctly format the field. The field is being generated by adding a static value and three fields that have been padded. Any help would be appreciated.
Combines fields and pads
StringVar strMICR;
StringVar strMICRLINE;
strMICRLINE := Chr(13) & "0603250694";
strMICRLINE := strMICRLINE & Right("000000" & Trim(Split({CUST.C_ID_ALPHA},"-")[1]),6);
strMICRLINE := strMICRLINE & Right("00000000" & ToText({STMT.STMT_NUMBER},0,""),8);
strMICRLINE := strMICRLINE & Right("0000000000" & Replace(ToText({#Total},2,""),".",""),10);
//Uncomment below to test Mod10 Check-digit
//strMICR := mod10("0603250694084469108961440000127874");
//IF NumericText (strMICRLINE)
//THEN ToNumber (strMICRLINE);
Mod10 (strMICRLINE);
MOD10 Function
Function (StringVar input_number)
input_number := replace(input_number, " ", "");
numbervar i := length(input_number);
numbervar sum_val := 0;
stringvar position := "odd";
do (
if position = "odd" then (
sum_val := sum_val + 3*tonumber(input_number[i]);
position := "even" )
else (
sum_val := sum_val + tonumber(input_number[i]);
position := "odd" )
;
i := i-1
) while i > 0;
numbervar remainder_val := Remainder(sum_val, 10);
numbervar check_digit := if remainder_val = 0 then 0 else (10-remainder_val) ;
input_number + ToText(check_digit, 0)

You're attempting to call toNumber() on a string that is not numeric and therefore can't be converted. You need to strip all non-numeric characters out of your string first.
//Formula sample to strip non-numeric characters
local stringvar input := "78906-adf0asdf-234";
local stringvar output;
local numbervar i;
for i:=1 to length(input) do
if numerictext(input[i]) then output:=output&input[i];
output
Then I would highly suggest you use the built in mod function instead of rolling your own.
toNumber({#NumericTextOnly}) mod 10

Related

Mod10 Formula in Crystal Reports

On another forum I found this formula and it seems to work except that I keep getting 2 different errors
First Error
I get "A string is required here" error. I'm getting the error on line 8 (counting blank lines) of the code where it says
replace({ACCOUNT_CARD_DATA.CARD_NUMBER}," ","")
Second Error
If I add totext and make it say
replace(totext({ACCOUNT_CARD_DATA.CARD_NUMBER})," ","")
it will save with no errors but when I try to put it in the report it gives me a "The string is non-numeric" error. When I click ok it shows me the error in the code is on line 18 (counting blank lines) where it says
v_calc := tonumber(v_temp) * 2
I feel like I'm in a loop that can't be resolved...what am I doing wrong?
Thank you!
Entire Code
whileprintingrecords;
stringvar v_cc := "";
stringvar v_temp := "";
numbervar v_calc := 0;
numbervar v_result := 0;
numbervar v_counter := 0;
v_cc := replace({ACCOUNT_CARD_DATA.CARD_NUMBER}," ",""); //THIS IS THE 1ST PLACE I'M GETTING THE ERROR
// Double every other digit starting with the last digit.
numbervar v_counter := len(v_cc);
while v_counter > 0
do
(v_temp := mid(v_cc,v_counter,1);
v_calc := tonumber(v_temp) * 2; //THIS IS THE 2ND PLACE I'M GETTING THE ERROR
if v_calc >= 10 then v_calc := tonumber(left(totext(v_calc,"#",0),1))+ tonumber(right(totext(v_calc,"#",0),1))
else
v_calc;
v_result := v_result + v_calc;
v_counter := v_counter - 2);
// Add in the non-doubled digits
v_counter := len(v_cc) - 1;
while v_counter > 0
do
(v_temp := mid(v_cc,v_counter,1);
v_calc := tonumber(v_temp);
if v_calc >= 10 then v_calc := tonumber(left(totext(v_calc,"#",0),1)) + tonumber(right(totext(v_calc,"#",0),1))
else
v_calc;
v_result := v_result + v_calc;
v_counter := v_counter - 2);
// Calculate check digit
v_cc + right(totext(v_result * 9,"#",0),1)

crystal reports switch statement not responding properly

Why is my code not properly reading a value in a Switch statement? Code below.
I've verified that it's properly iterating, one character at a time and that the numeric characters appear to match the conditionals. But every character is handled by the default, none by the conditional.
Local StringVar inString := "X12y1023" ;
Local StringVar outString;
Local NumberVar i :=1;
...
While i <= Length(inString)
Do (
Local StringVar inC := mid(inString, i, 1);
Local StringVar outC;
Switch(
inC = "1", outC := "!",
inC = "2", outC := "Z",
inC = "3", outC := "E",
...
inC = "0", outC := "O",
True, outC := inC
);
outString := outString + outC;
i := i+1;
);
outString;
To demonstrate that the number characters are not being read at any point above the default condition (and the length of each iteration is only one character), I modified True as follows:
True, outC := inC + "_" + Cstr(Length(inC)) + ", "
Output generates
X_1, 1_1, 2_1, y_1, 1_1, 0_1, 2_1, 3_1,
What am I missing?
Thanks
A switch statement is not really meant to be used the way you're trying to use it; It's meant for returning simple values and not for more complicated statements, like variable assignments. I'd guess that the behavior you're seeing is probably just a byproduct of the specific implementation of the function.
Instead, you can either use the case-statement or rearrange your switch so that it is only used to return simple values.
//Your code changed to use a case-statement
Local StringVar inString := "X12y1023" ;
Local StringVar outString;
Local NumberVar i :=1;
While i <= Length(inString)
Do (
Local StringVar inC := mid(inString, i, 1);
Local StringVar outC;
Select inC
Case "1" : outC:="!"
Case "2" : outC:="Z"
Case "3" : outC:="E"
Case "0" : outC:="O"
Default : outC:=inC;
outString := outString + outC;
i := i+1;
);
outString;
Or
//Your code rearranged to use switch as intended
Local StringVar inString := "X12y1023" ;
Local StringVar outString;
Local NumberVar i :=1;
While i <= Length(inString)
Do (
Local StringVar inC := mid(inString, i, 1);
outString := outString +
switch(
inC = "1", "!",
inC = "2", "Z",
inC = "3", "E",
inC = "0", "O",
True, inC);
i := i+1;
);
outString;

crystal report: print missing records

i want to print missing records in crystal report .
i am using below formula in the report and i have placed this formula in details b section.
details a has normal report fields.
formula:
local numbervar firstemp; // first Emp#
local numbervar nextemp; // next Emp#
local numbervar diff; // difference between firstemp and nextemp
local numbervar increase; // increment for missing Emp#'s
local numbervar result;
increase := 0;
firstemp := tonumber({getRptSalesSummery;1.Bill_Id});
nextemp := tonumber(next({getRptSalesSummery;1.Bill_Id}));
nextemp := nextemp -1;
diff := nextemp - firstemp;
if nextemp = firstemp
then ""
else (
while diff >= 1
do (
diff := diff - 1;
increase := increase + 1;
result := firstemp + increase;
exit while;
);
totext (result,"0000") & chr(13);
)
this formula is not giving me range.
for example if in report there is range of 1 to 10 and 6,7,8,9 is missing records, then if i check in the report its printing 1 to 5 and 6 as missing then directly 10, but its not giving me 7,8,9.
basically i required range of missing records

Display Serial Number as Roman letters in Crystal Reports

need to display serial no as roman letters(i,ii,iii,iv etc) in my crystal reports. I have the serial number captured as record number (1,2,3,4...).so what i have to do for it in crystal report.
Just use the Roman() function provided by Crystal Reports
I can't take much of the credit; I simply ported the code from this VB Helper article into Crystal, but it was a fun exercise:
NumberVar iCounter := 0;
Local StringVar ch := "";
Local NumberVar result := 0;
Local NumberVar new_value := 0;
Local NumberVar old_value := 0;
Local StringVar temp := "";
temp := UpperCase({?#Roman});
old_value = 1000;
For iCounter := 1 To Len(temp) do
(
// See what the next character is worth.
ch := Mid(temp, iCounter, 1);
if ch = "I" then new_value := 1
else if ch = "V" then new_value := 5
else if ch = "X" then new_value := 10
else if ch = "L" then new_value := 50
else if ch = "C" then new_value := 100
else if ch = "D" then new_value := 500
else if ch = "M" then new_value := 1000;
// See if this character is bigger
// than the previous one.
If new_value > old_value Then
// The new value > the previous one.
// Add this value to the result
// and subtract the previous one twice.
result := result + new_value - 2 * old_value
Else
// The new value <= the previous one.
// Add it to the result.
result := result + new_value;
old_value := new_value;
);
// Format the number without commas or decimals
ToText(result, 0, "");
Simply replace my {?#Roman} parameter placeholder with your variable, and you're all set.
I tried to fix it [enter image description here][1]
<https://www.tek-tips.com/viewthread.cfm?qid=887691>
or
<https://www.tek-tips.com/viewthread.cfm?qid=1613334>
and
<https://www.youtube.com/watch?v=X_UaulmICtM&list=TLPQMTUwMjIwMjMRAYZJzCsXDQ&index=6>
specifically: at crystal report
TH1: Fomula fields/new/"nameabc"/enter/"Roman(GroupNumber)"/ ctrl+S/and pull it out
TH2: Fomula fields/new/"nameabc"/enter/
select GroupNumber
case 1 : " I"
case 2 : " II"
case 3 : " III"
case 4 : " IV"
case 5 : " V"
case 6 : " VI"
case 7 : " VII"
case 8 : "VIII"
case 9 : " IX"
case 10 : " X"
case 11 : " XI"
case 12 : " XII"
case 13 : "XIII"
case 14 : " XIV"
case 15 : " XV"
case 16 : " XVI"
case 17 : "XVII"
default : ""
/ ctrl+S/and pull it out
But it really doesn't help t so there will be this 3 case (t improved from link 2-3) it can apply to the 3rd or even 10th group of headings
TH3: ex: (you want to create a text message for group 3)
Formula fields/new/"nameabc"/enter/
"
WHILEPRINTINGRECORDS;
GLOBAL NUMBERVAR INTSTTGRTEST;
INTSTTGRTEST :=0;
/ ctrl+S/ drag it out and put it in heading group 2 and hide it (= right click/format field/common/ check Suppress/ok) you can go to link 3 to see
Formula fields/new/"nameabcd"/enter/
"
WHILEPRINTINGRECORDS;
GLOBAL numbervar INTSTTGRTEST := INTSTTGRTEST + 1;
stringvar y;
STRINGVAR ARRAY X := ["A","B","C","D","E","F","G","H","I","J","K", "L","M","N","O","P","Q","R","S","T","U","V","W","X ","Y","Z"];
if INTSTTGRTEST <= 26 then (
redim preserve X[INTSTTGRTEST];
y := X[INTSTTGRTEST]
);
y;
/ ctrl+S/and pull it out and place it at group 3
and the alphabet can be whatever we want. ex:
X := ["I","II","III","IV","V","VI","VII","VIII","IX","X","XI" ,"XII","XIII","XIV","XV","XVI","XVII","XVIII","XIX","XX","XXI","XXII","XXIII"," XXIV","XXV","XXVI","XXVII","XXVIII","XXIX","XXX","XXXI","XXXII","XXXIII","XXXIV","XXXV","XXXVI" ,"XXXVII","XXXVIII","XXXIX","XL","XLI","XLII","XLIII","XLIV","XLV","XLVI","XLVII","XLVIII"," XLIX","L"];
or
X := ["a","b","c","d","e","f","g","h","i","j","k","l","m","n","o","p","q","r","s","t","u","v","w","x","y","z"];
hope it can help you
enter code here [1]: https://i.stack.imgur.com/OeBBQ.png

'The string is non-numeric' error in a crystal reports Formula

I have put a formula to display the value of a field after masking it in crystal reports. but it shows me an error 'The string is non-numeric' in cardno variable. Following is code of my formula:
StringVar cardno;
NumberVar current_len;
NumberVar card_len;
NumberVar start;
NumberVar last;
StringVar ca;
card_len := ToNumber (Mid ({#lens},1,2));
start := ToNumber (Mid ({#lens},3,2));
last := ToNumber (Mid ({#lens},5,2));
current_len := Length (Trim (ToText({CA.CA}, 0 ,'')));
ca := ReplicateString("0",card_len-current_len) + Totext({CA.CA},0,'');
If card_len > current_len Then
If start = 0 Then
If last <= 1 Then
cardno := Mid(ca, last, card_len)
Else
cardno := ReplicateString("X",last-start-1) + Mid(ca, last, card_len)
Else
cardno := Mid (ca,1,start) + ReplicateString("X",last-start-1) + Mid(ca, last, card_len);
Please provide a solution to avoid this error. Thanks in advance.
Why don't you do something like this:
Select Len({table.field})
//AmEx
Case 15: Picture({table.field}, "XXXX XXXXXX XXXXX")
//Visa
Case 16: Picture({table.field}, "XXXX XXXX XXXX XXXX")
Default: {table.field}
** edit **
Replace(Space(Len({table.field})-4), " ", "X") + Right({table.field},4)