1 intro to programming & algorithm design input validation copyright 2003 by janson industries...
TRANSCRIPT
1
Intro to Programming & Algorithm Design
Input Validation
Copyright 2003 by Janson Industries
This presentation can be viewed on line in a file named: ch07.IntrotoProg.InputValidation.ppt
Assg
Copyright 2014 by Janson Industries2
Objectives▀ Explain
■ GIGO (garbage in garbage out)
■ Defensive programming
■ The input validation loop
■ Different types of validation♦ Data type♦ Range♦ Completeness
▀ Show how to code validation functions in Java
Copyright 2014 by Janson Industries3
GIGO▀ The program can be coded
correctly but if you put bad data in, you will get bad results
▀ This has been the demise a many a new application
■ All coding done and correct but the data conversion wasn't done properly
♦ I.e. the customer db data is incorrect so all the bills are sent to the wrong customers
Copyright 2014 by Janson Industries4
GIGO▀ Not just true of programs
■ What happens if you put diesel in your car engine?
♦ You had a perfectly good car but then ruined it with bad input
■ That’s why car manufacturers build the car so only the unleaded nozzle fits
♦ That's a form of input validation!
Copyright 2014 by Janson Industries5
Defensive Programming▀ Only provide valid values that the user
can select from
■ The ubiquitous state abbr list
■ Checkboxes/buttons indicating selected values
♦ I accept the license agreement
▀ Write code to detect all possible data errors and then either
■ Correct the error
■ Inform the user of the error and provide info to help them correct it
Copyright 2014 by Janson Industries6
Data Errors ▀ Wrong type of data
■ Numbers vs. text♦ For month: "November" vs. 11
■ Integers vs. decimal numbers♦ For month: is 11.53 a valid month
▀ Completeness/invalid size
■ Did the user enter no data or only part of the data
♦ 3224 for a zip code
■ Put in too much data♦ 322456245374835374 for a zip code
Copyright 2014 by Janson Industries7
Data Errors ▀ Data not within a valid range
■ Month should be between 1 and 12
■ Birthdates should not be over 120 yrs ago
▀ Data not from valid set of values
■ Gender can be "M" or "F"
▀ Data integrity
■ Zip code entered not valid for state abbr entered
■ Customer number entered not valid
Copyright 2014 by Janson Industries8
Data Validation Pre-test Loop▀ Standard way of making sure data
is valid
■ Prompt user for data
■ Read the data in
■ Have a loop that tests the data validity
■ If not valid♦ Fix data or display a useful message so
the user can fix the data♦ Read the data again
Copyright 2014 by Janson Industries9
Data Validation Pre-test LoopFunction String getMonth() Declare String month Declare Integer monthNumber // User prompt explains the valid values Display "Enter a month number between 1 and 12" Input month monthNumber = stringToInteger(month) While (monthNumber < 1 OR monthNumber > 12)
Display "Enter a month number. For example, 1 for Jan, 2 for Feb"
Input monthmonthNumber = stringToInteger(month)
End While Return monthEnd Function
Copyright 2014 by Janson Industries
monthNumber= stringToInteger(month)
Display “Enter a month number between 1 and 12”
Declare String month
Integer monthNumber
Data Validation Pre-test LoopgetMonth()
Input month
Copyright 2014 by Janson Industries11
Return month
Input month
While monthNumber<1 OR monthNumber >12
False
Display “Enter a month number. For example, 1 for Jan, 2 for Feb"
monthNumber= stringToInteger(month)
True
Copyright 2014 by Janson Industries12
Data Validation Loop▀ How could we have fixed the data
for the user?
■ Check to see if the three character abbr or full text for the month was entered
♦ If so, change to the correct number
■ Check to see if a space(s) was entered at the beginning or end of the text
♦ If so, trim the space(s) off
Copyright 2014 by Janson Industries13
Data Validation Post-test Loop▀ Start loop
■ Prompt the user for the data
■ Read the data in
▀ End of loop validity test, if not valid, go to the start of the loop
▀ A lot less code but only one prompt/msg to the user
■ No useful error msg with further info
Copyright 2014 by Janson Industries14
Data Validation Post-test Loop
Function String getMonth() Declare String month Declare Integer monthNumber Do // User prompt explains the valid values Display "Enter a month number between 1 and 12" Input month monthNumber = stringToInteger(month) While (monthNumber < 1 OR monthNumber > 12) Return monthEnd Function
Copyright 2014 by Janson Industries16
Validation Functions▀ For data that is commonly input, create validation
functions that many programs can use
■ Many programs may ask for the month
■ Have a common function to get data and do all the validation
■ Advantage: only written once♦ Less coding♦ If need to change, change in only one place
Copyright 2014 by Janson Industries18
MyUtils▀ Any program that requests a date can
now use the day and month functions
public class Test {
public static void main(String[] args) {String month = null, day = null;int monthNumber = 0;month = MyUtils.getMonth();monthNumber = Integer.valueOf(month);day = MyUtils.getDay(monthNumber);MyUtils.p("The date entered is " + month + "/" +
day); }}
Copyright 2014 by Janson Industries19
Validating Strings▀ Added problem of lower and upper case
▀ "yes", "YES", "Yes", "yEs" are all different values
▀ Easiest solution is to change input to either upper or lower case then test for the value
Copyright 2014 by Janson Industries20
Validating Strings▀ Restaurant is asking customer for items they want (pizza, soda, calzone, etc.) and sizes
▀ Need to validate both the item and size
▀ Since the sizes (small, medium, and large) are the same for all items will create a common getSize function
Copyright 2014 by Janson Industries21
Validating Strings▀ getSize will also check to see if the user enters "s", "m", or "l"
■ If so will convert to "small", "medium" or "large"
▀ In case of a typo ("meduim", "larj", "smal", etc.) will check the first letter
■ if "s", "m", or "l", will convert to "small", "medium" or "large"
Copyright 2014 by Janson Industries22
String Validationmain() Declare String item, size; Display "Enter the item you want to purchase: Pizza, Calzone or Soda" Input item item = toLower(item) While (item != "pizza" AND item != "calzone" AND item != "soda")
Display "Please enter Pizza, Calzone or Soda " Input item item = toLower(item) End While size = getSize(item) Display "You have ordered a ", size, " ", itemEnd
Copyright 2014 by Janson Industries23
String Validation
Function String getSize(String item)
Declare String size
// User prompt asks for size Display "Enter the size ", item, " you would like" Input size size = toLower(size)
While (size != "small" AND size != "medium" AND size != "large")
Copyright 2014 by Janson Industries
If (substr(size, 0 , 1) = "s" OR substr(size, 0, 1) = "m" OR substr(size, 0, 1) = "l" Then If substr(size, 0 , 1) = "s" Then
size = "small" Else If substr(size, 0 , 1) = "m" Then
size = "medium" Else
size = "large" End If
End IfElse Display "Enter small, medium, or large" Input size size = toLower(size)
End While Return sizeEnd Function 24
String Validation
Copyright 2014 by Janson Industries29
Flow Chart - Raptor▀ Raptor cannot convert strings to
upper or lower case
▀ However, we can write a function to do it
▀ All characters can be represented as numbers
▀ In ASCII, A-Z are 65-90 and a-z are 97-122
Copyright 2014 by Janson Industries31
Flow Chart - Raptor▀ Raptor can return the number
associated with a particular character or visa versa
■ charNum = to_ascii('A')♦ charNum will equal 65
■ char = to_character(97)♦ char will equal 'a'
▀ You can manipulate a character value as if it were a number■ Add 32 to get lower case character
Copyright 2014 by Janson Industries32
Flow Chart - Raptor▀ Raptor cannot perform a true
substring function
▀ Can identify a single character within a string by specifying the index of the character
▀ Assuming address = "1 Main St"■ address[3] is "M"■ address[7] is " "
Copyright 2014 by Janson Industries33
Flow Chart - Raptor▀ When an index is used, value
type is character NOT string■ Comparing two different value
types can't be done♦ 123 = "123" is invalid
■ Or in this case♦ address[3] = "M" is invalid♦ However, address[3] = 77 is valid
▀ Could also create a character variable with the value "M"■ charVar = to_character[77]
Copyright 2014 by Janson Industries34
toLowerCaseFunction String toLowerCase(String stringToChange)
Declare Integer ctr = 1
While ctr <= length(stringToChange)
If stringToChange[ctr] > 64 AND stringToChange[ctr] < 91 stringToChange[ctr] = stringToChange[ctr] + 32
End If
ctr = ctr + 1 End While
Return stringToChange
End Function
Copyright 2014 by Janson Industries
Start
ctr ← 1
ctr > length_of(stringToChange)
stringToChange[ctr] > 64 && stringToChange[ctr] < 91
stringToChange[ctr] ← stringToChange[ctr] + 32
NoYes
ctr ← ctr + 1
End
Yes
No
Loop
//Declare variablesInteger ctr
35
Raptor toLowerCase()
Notice how character value treated like a
number
Had to change loop condition because of
Raptor
Copyright 2014 by Janson Industries
Start
"Enter the item you want to purchase: Pizza, Calzone or Soda"GET stringToChange
toLowerCase
item ← stringToChange
item = "pizza" OR item = "calzone" OR item = "soda"
"Please enter Pizza, Calzone or Soda"GET stringToChange
toLowerCase
item ← stringToChange
getSize
PUT "You have ordered a " + size + " " + item¶
End
Yes
No
Loop
//Declare variablesString item, size, stringToChange
36
Raptor main()
Copyright 2014 by Janson Industries
Start
"Enter the item you want to purchase: Pizza, Calzone or Soda"GET stringToChange
toLowerCase
item ← stringToChange
item = "pizza" OR item = "calzone" OR item = "soda"
"Please enter Pizza, Calzone or Soda"GET stringToChange
toLowerCase
item ← stringToChange
getSize
PUT "You have ordered a " + size + " " + item¶
End
Yes
No
Loop
//Declare variablesString item, size, stringToChange
37
Copyright 2014 by Janson Industries38
Raptor getSize()
Start
"Enter the size " + item + " you would like"GET stringToChange
toLowerCase
size ← stringToChange
size = "small" OR size = "medium" OR size = "large"
size[1] = to_character(115) OR size[1] = to_character(109) OR size[1] = to_character(108)
size[1] = to_character(115)
size ← "small" size[1] = to_character(109)
size ← "medium" size ← "large"
NoYes
NoYes"Enter small, medium, or large"GET stringToChange
toLowerCase
size ← stringToChange
NoYes
End
Yes
No
Loop
Copyright 2014 by Janson Industries39
Raptor getSize()
Start
"Enter the size " + item + " you would like"GET stringToChange
toLowerCase
size ← stringToChange
size = "small" OR size = "medium" OR size = "large"
size[1] = 115 OR size[1] = 109 OR size[1] = 108
size[1] = 115
size ← "small" size[1] = 109
size ← "medium" size ← "large"
NoYes
NoYes"Enter small, medium, or large"GET stringToChange
toLowerCase
size ← stringToChange
NoYes
End
Yes
No
Loop
Again, notice how character value treated
like a number
Copyright 2014 by Janson Industries44
Java▀ Does have a toLowerCase
method■ So we don't have to mathematically
manipulate the ASCII integer values
▀ Also has an equalsIgnoreCase method■ String name = "MOE";■ name.equalsIgnoreCase("moe");
♦ Is true
Copyright 2014 by Janson Industries48
Reading Mixed Data Java lets you read individual
values not just the whole line next() gets all text on a line up to the
next space
nextInt() gets all text up to the next space and converts it to an integer
nextDouble() gets all text up to the next space and converts it to a double
None of these advance the cursor to the next line!
Copyright 2014 by Janson Industries49
Processing Data Not nitpicking! If entered the
following budget data
And you tried to process with these statements
Rent500Car280
item1 = keyboard.nextLine();item1Amount = keyboard.nextInt();item2 = keyboard.nextLine();item2Amount = keyboard.nextInt();
Copyright 2014 by Janson Industries50
Processing Data There would be an
InputMismatchException the second time nextInt executed
WHAAAAAAAT!! Must show where cursor is after
each statement executed to understand
First nextLine() reads "Rent" and places cursor at the beginning of the second line
Copyright 2014 by Janson Industries51
Processing Data When nextInt executed 500 read
and cursor placed at end after the second 0
When the second nextLine (3rd read) executed, it reads the rest of the second line A big fat null
Rent500Car280
Cursor after first read
Cursor after second
read
Copyright 2014 by Janson Industries52
Processing Data And cursor placed at
beginning of third line
Now when second nextInt executed InputMismatchException
Tries to convert "Car" into a int
Rent500Car280
Cursor after 3rd read
(2nd nextLine)
Copyright 2014 by Janson Industries53
Processing Data Solution:
Execute another nextLine after the nextInt
Forces the cursor to the line after the line with the int value
item1 = keyboard.nextLine();item1Amount = keyboard.nextInt();keyboard.nextLine();item2 = keyboard.nextLine();item2Amount = keyboard.nextInt();
Copyright 2014 by Janson Industries54
Points to Remember▀ Bad input will make an
application yield incorrect results
▀ Defensive programming consists of many techniques used to stop bad input
▀ All character data can be represented as an integer value