Review
Let's review our material from last week with a quick warmup!
Write a script that starts off with some string variable named stringy that can be any string (except the empty string), and alerts stringy with the last character
turned into an exclamation mark (!). Hint: you might need to use a string's length, concatenation (+), and substr(begin, numChars) property and methods.
Prompt
We've already looked at alert as a means of outputting text to our users, but what about getting input from them?
That's where the prompt command comes in:
The prompt command operates in the browser, creating a pop-up with text (typically a question or indication for what the user should type) and an input box, in which the user may provide information.
The syntax for prompt is as follows:
let name = prompt("What is your name?"),
ssn = prompt("Enter your social security number into this legit site."),
etc = prompt("Please enter your home address and a list of your phobias.");
In the above example, we see that we can store the results of each our prompts to the user in a variable for later use!
Try entering the above into a console!
Note: when a user clicks the "cancel" option to remove a prompt pop-up, for example in let x = prompt("question here");, x will attain the value
null.
Warning: the prompt command, when used to collect a lot of data from users, can quickly annoy them -- those pop-ups don't go away until you've either entered
something or hit cancel! Later, we'll investigate better ways of getting input from the user.
Here's something you might have already considered based on our discussion of the typeof operator.
What is the type of data collected using prompt? Let's find out!
Design a script that simply prompts a user for some input, and then alerts the typeof their entry. Experiment with numerical and textual input.
What are the "peculiar" findings from your script above?
The type of the user-collected data is always string, even when we enter numbers!
Let's see how to deal with this...
Type Conversions
As we saw in the last section, we need a means of converting between types!
Sometimes, we want to use numerical data, and other times we want to use text data; we need tools to convert between them.
The toString method, when called on a numerical variable or parenthesized numerical expression, will return the string representation of it.
The parseInt(str) function, when called on a string, will return the number it represents with any decimal points cut off.
The parseFloat(str) function, when called on a string, will return the number it represents with any decimal points left in-tact.
WARNING: Note that toString() can only be called on a numerical variable (not a numerical literal like the number 5), and that parseInt and parseFloat accept the string they're converting within their parens.
Try these out!
let num5 = 5,
str5 = "5.5";
console.log(num5.toString());
console.log(num5 + num5);
console.log(num5.toString() + num5.toString());
console.log(parseInt(str5));
console.log(parseFloat(str5));
Why do you think toString can only be used on numerical variables / parenthesized expressions rather than numerical literals like: 5.toString()?
Because the period following a number is usually the decimal point, and our interpreter gets confused!
Write a script that prompts the user for two numbers and alerts true if the second one is a factor of the first. For example, if a user enters "6" and then "3" we'll print out true, since 3 is a factor of 6. Ignore the possibility of being fed bad input (like text).
Formatting Output
Suppose I'm making an application to calculate the tip on a user-entered dollar amount.
It would look very unprofessional to output something like "$15.333333" when we always format dolar amounts with 2 decimal places representing cents, like: "$15.33".
To help us with this formatting goal, we have an important tool:
The toFixed(decimalPoints) method converts a number into a string in which exactly decimalPoints number of decimal places are preserved in
the string representation.
Try this out too!
let lotsODecimals = 10.123456789; alert(lotsODecimals.toFixed(0)); alert(lotsODecimals.toFixed(2)); alert(lotsODecimals.toFixed(10));
Style Tips
Note: we'll only go over this section in class if there's time -- otherwise, you must read it yourself and make sure you're aware of its content!
Recall that having good coding style is very important, and the earlier you learn it, the sooner you can avoid mistakes that might otherwise cost you an interview or job!
What does it mean to have good programming style?
You can express your code, its purpose, and how it accomplishes its task in a parsimonious, structured, and well-documented fashion.
Why is it important to have good programming style?
There are many reasons, but two of the most important: (1) Others who look at your code can easily pick it up (important for legacy support / team or enterprise programming) and (2) you can structure your thoughts more elegantly, leading to cleaner, more robust, and less buggy functionality.
There are many stylistic conventions that we'll talk about throughout the course, but here are a couple to mention at the start:
Name variables clearly, giving an indication of their purpose.
Good Style |
Bad Style |
|---|---|
let base = 3,
height = 4,
hypotenuse = Math.sqrt(base * base + height * height);
|
let x = 3,
y = 4,
z = Math.sqrt(x * x + y * y);
|
Indent using space characters only (no tabs) and do so consistently. For example, when you leave a space between the assignment operator (=) and the variable, do so on the right side as well, and everywhere else you define a variable.
Good Style |
Bad Style |
|---|---|
let base = 3,
height = 4,
hypotenuse = Math.sqrt(base * base + height * height);
|
let base= 3,
height = 4,
hypotenuse=Math.sqrt(base* base +height * height);
|
Comments are documentation that you can add to your source code that is completely ignored by the interpreter, but can serve to instruct inspectors of your code on what it does, or how it does it.
A single-line comment has the following syntax, where everything to the right of the // reserved sequence is completely ignored.
// Here is a useful comment! Everything here is ignored by your code.
A multi-line comment has the following syntax, where everything between the /* and */ reserved sequences is completely ignored.
/* * Here's a comment on this line! * ...and this line too! * Notice how I start each line with an asterisk (*)? * That's totally optional, but looks nice and is common practice */
Comments should be used to explain any non-obvious or sufficiently complex functionality in your code, and should not be used when the meaning can be gleaned from your code's syntax alone.
Good Style |
Bad Style |
|---|---|
let weight = 180,
factor = 1/6,
// Converted weight represents weight on
// different planets
convertedWeight = weight * factor;
|
// Begin by declaring variables
let weight = 180, // Here is your current weight
factor = 1/6, // This is the conversion factor
// used to compute your new weight
// Converted weight represents weight on
// different planets
// e.g., factor = 1/6 represents your weight on the moon
convertedWeight = weight * factor;
|
You should know the following shortcut operators that can simplify your code:
The increment operator (++) / decrement operator (--) increases a variable by 1 (increment) or decrements it by 1 (decrement)
So instead of saying let x = 5; x = x + 1; I could instead say: let x = 5; x++;
That's not the best example, but we'll see instances later when it's more cleanly to use increment.
The add-and-assign (+=), subtract-and-assign (-=), multiply-and-assign (*=), divide-and-assign (/=) operators perform the given mathematical operation on the current value of the variable, and then save the result into the variable again.
Good Style |
Bad Style |
|---|---|
let health = 100; // Oh no! You got hit! health -= 10; // health is now 90 |
let health = 100; // Oh no! You got hit! health = health - 10; // health is now 90 |
There will be many other stylistic tips throughout the course -- make sure you pay attention to them, style counts on assignments (and life, of course)!
Testing Tips
Note: we'll only go over this section in class if there's time -- otherwise, you must read it yourself and make sure you're aware of its content!
"Beware of bugs in the above code; I have only proved it correct, not tried it." - Donald Knuth
Testing your code is an important part of the programming process!
It is incredibly easy for even seasoned programmers to overlook some cases in which their code does not operate as intended. As such, it is important to test your code!
Since we haven't covered much just yet, let's talk about a simple, guiding principle that you can use to test your code.
The zero-one-infinity principle gives a guideline for testing code, saying that you should try inputs that are empty, a single item, and then two or more items to verify that it is working properly.
Let's re-examine our eXtreme function from last week and apply the zero-one-infinity principle, just for review that was:
Write a script that has a variable called "toExclaim" that, by assumption, contains a string. You have another variable called exclaimPoint that is some integer between 0 and the toExclaim.length. Your task: alert toExclaim with the character at the given exclaimPoint index replaced by "!".
let toExcite = "excite",
excitePoint = 2;
alert(toExcite.substr(0, excitePoint) + "!" + toExcite.substr(excitePoint + 1));
To verify that our code is working, we should test it with a variety of inputs.
// Some good tests for toExcite: toExcite = "a"; // one letter toExcite = "ab"; // two... toExcite = "abc"; // three... etc. // Some good tests for excitePoint excitePoint = 0; // zero... excitePoint = 1; // one... excitePoint = 2; // infinity! (kinda)
Above, toExcite = "a"; is our "zero" test (assuming it can't be empty for the function), but we should be certain to test the emptry string whenever it is a legal input.
In general, we should test as thoroughly as possible.
A bug can, at least, annoy a user, and at worst, erroneously start a thermonuclear war.
Later, we'll examine more sophisticated testing techniques that don't take as much fiddling from you as the programmer, and are more structured than the above... for now, a hands-on approach to debugging is just fine!