Www.drfrostmaths.com



A Crash Course in ProgrammingNote: The particular programming language I use here (as concrete examples of theory) is in Java, but much of the syntax (i.e. the way the code is written) is very similar, and often identical, to how it can be expressed in other languages such as C++, C#, etc.Contents TOC \o "1-3" \h \z \u Getting Started PAGEREF _Toc338515525 \h 3Software you will probably find very helpful PAGEREF _Toc338515526 \h 3A ‘Hello World’ Program PAGEREF _Toc338515527 \h 6Running your Program PAGEREF _Toc338515528 \h 9Part A - Primitive Types and Statements PAGEREF _Toc338515529 \h 10Statements PAGEREF _Toc338515530 \h 10Primitive Types revisited PAGEREF _Toc338515531 \h 11Operations on primitive types PAGEREF _Toc338515532 \h 12More statements PAGEREF _Toc338515533 \h 13If Statements PAGEREF _Toc338515534 \h 13While loops PAGEREF _Toc338515535 \h 14Turning this into a runnable program. PAGEREF _Toc338515536 \h 15Rewriting the program using a ‘for’ loop PAGEREF _Toc338515537 \h 15One Final Note: The ‘Scope’ of Variables PAGEREF _Toc338515538 \h 16Section Review PAGEREF _Toc338515539 \h 17Check your knowledge PAGEREF _Toc338515540 \h 18Part B - Methods PAGEREF _Toc338515541 \h 19Some basic pre-written methods you should know about PAGEREF _Toc338515542 \h 20String PAGEREF _Toc338515543 \h 20Math PAGEREF _Toc338515544 \h 21How to find out the methods a class has in Eclipse PAGEREF _Toc338515545 \h 21Part C – Converting between types PAGEREF _Toc338515546 \h 23Casting PAGEREF _Toc338515547 \h 23Part D – Arrays PAGEREF _Toc338515548 \h 24Some Quick Basics PAGEREF _Toc338515549 \h 24Cycling through an array’s values using a ‘for loop’ PAGEREF _Toc338515550 \h 25Example program: Finding the factors of a number PAGEREF _Toc338515551 \h 25Test Your Knowledge PAGEREF _Toc338515552 \h 27Answers PAGEREF _Toc338515553 \h 28Another Example: Roman Numerals PAGEREF _Toc338515554 \h 28Object Orientation PAGEREF _Toc338515555 \h 32Fraction Example PAGEREF _Toc338515556 \h 32toString methods PAGEREF _Toc338515557 \h 34Getting StartedWe’re going to start from absolute scratch! We’ll be introducing the basic concepts involved in creating a basic program before working up to gradually complex stuff, as well as describing how we can use some of the tools to write, test and ‘debug’ our programs. My philosophy to learning programming is to learn by example, but that some basic ‘scaffolding’, i.e. programming theory, is essential also to becoming an effective coder. Without the latter, there is a danger to ‘hack stuff together’ in an undisciplined way.Coding is a mixture of problem solving, engineering, creativity and scientific rigour. It involves approaching some potentially high-level problem, perhaps found in maths or science (such as generating a driving route based on a road map), and engineering a solution that translates that problem to a workable program.Software you will probably find very helpfulWe recommend a program called Eclipse to write your programs. You can find it at . There’s lots of versions, but the one we’ll be using her is “Eclipse IDE for Java Developers” (there’s a similar one called “...for Java EE Developers” – you probably don’t need this one for the moment). There’s versions for Windows, Mac and Linux based operating systems.Eclipse is known as an IDE or Integrated Development Environment. This helps you in a number of ways when coding:For many languages, such as Java, it’ll let you know about incorrectly written code immediately. While most ‘bugs’ in your code (i.e. unexpected behaviour) it won’t be able to detect, it will underline code that has been written correctly according to the Java language, just as a word processor might underline incorrectly spelled words.It’ll ‘compile’ and run your code at the click of a button. Compiling is the process of taking your code and converting it into a more basic form that the computer can directly read and run.It’ll make managing your code much easier, if for example if you want to rename variables, move code about and other changes.You can of course write your code in a basic text editor (e.g. Notepad!), and it’s useful knowing how to compile and run code yourself without the assistance of an IDE. But if you insist on using a basic text editor (which I did myself for many years before seeing the light!) you’ll miss all the advantages that IDEs bring, and waste much more time on the less important parts of coding.When you’ve downloaded Eclipse, double click on the icon of the main Eclipse program (probably named eclipse.exe). You’ll be asked to select a workspace:Your workspace is where you can create your various coding projects. Just name it anything you like, put it somewhere on your hard drive you can easily find, then click OK.This will take you to the main welcome screen, which will look different depending on what version you downloaded. Click the arrow icon labelled ‘Workbench’ (pictured here on the top-right). This will bring up the workbench that you’ll be working from. It may seem somewhat intimating at first, but getting a basic program going is not too difficult.From the File menu, select ‘New Project’, then ‘Java Project’ (since we’ll be coding in Java). If for some reason Java Project doesn’t appear in the list, select ‘Project’, and then choose ‘Java Project’ from the list provided there. You should see a dialog something like this:Enter an appropriate project name (e.g. “TestProject”), and then click Finish. Now, your should have a new empty project to start coding in!Hover your mouse over the tab named ‘Package Explorer’, i.e. where the ‘TestProject’ item is. You’ll see a small arrow appear next to the label. Click it to expand the contents of the project, and you should see something like this:There’s two things here. The src folder is where all your ‘source code’ is going to go. Source code is code that you write, whereas binaries are compiled code that the computer runs. The latter goes in a directory called ‘bin’ which is hidden from view. Don’t worry about the ‘JRE System Library’ for now. This contains various ‘libraries’ (i.e. prewritten code that you can refer to from your own) that you might use.A ‘Hello World’ ProgramMany people who start learning a programming language start with a ‘Hello World’ program. This is the simplest program you can imagine: just printing out the words “Hello World!” and then ending. It’s obviously not a particularly useful program, but it’s quite useful to get over the initial program of writing some code in the new unfamiliar language, and getting used to the start-to-finish process of compiling and running the code.Right click the src folder in TestProject, and select ‘New -> Class’ (see screenshot below).We’ll be looking at ‘classes’ later, but for now, think of it as a place where we can store items and behaviour associated with one thing in particular (e.g. computing a route on a map, or dealing with a transaction from a customer). You’ll get this dialog:There’s lots of options here, most of which won’t make sense yet. But there’s information you’ll have to fill out to create the class.In Name, put the name of your class. For the moment, put ‘MyTestProgram’.Click the checkbox that says “public static void main” under ‘create method stubs’.Definition: A ‘main method’ is where the computer looks for code when you ‘point’ it at a particular class. So if you ran MyTestClass, the program would start at the main method, and run whatever code is inside it.Click ‘Finish’ and abracadabra! You’ll now have a workspace that looks something like this:What have we got here? Towards the middle of the workspace we have a tab where we can modify the code for our class. On the left in the Package Explorer, we can see our class listed under ‘default package’. We won’t see ‘packages’ till later, but they allow us to group classes with similar behaviour together. Since we didn’t specify a package name, it doesn’t have an assigned package, so appears as ‘default package’.Let’s just concentrate on the code in our class now. We can see the ‘main method’ inside the class. Most of the line starting “public static void” won’t make much sense at the moment. But the overall effect of this line is to say we have some ‘method’ called ‘main’. Our code goes between the curly braces, i.e. { }.Starting a line using “//” indicates that the line of code is a comment. Comments allow us to explain what our code is doing, and these lines will be ignored when the program is compiled/run. Comments can span multiple lines, using “/* Your comment here */”. Here, the IDE has put a comment starting ‘TODO’. This comment is just to say that the method has been automatically generated, and we need to insert our code there, because it currently doesn’t do anything.Remove the comment, and type the following into the code area:And that’s all folks! We now have a fully-functioning program that we can immediately run.Running your ProgramWe want to compile and run your program. Towards the top of the workspace, you’ll see an icon like this: . Click on it, and voila, the IDE will do the work for you. Towards the bottom of the workspace, you’ll see the following very exciting message:If you see this, it means you program has run successfully. So what is the ‘console’? It’s more or less somewhere where you print text to. You may have heard of the ‘command line’ (known in Windows as the ‘command prompt’), where you can type commands and navigate your file and directories for example. If you were to run your program from the command line rather than in the IDE, you’d see your ‘Hello world!’ message printed there. For the moment, think of it as somewhere were you can show text you want to display. Otherwise, you might display your text in more advanced ways, such as on a user interface, or transmitting it across a network to a display device somewhere else.At this point, giving our salutary success in greeting the world, we’re going to give the practical side of things a bit of a breather and get some basic programming theory that underpins many programming languages (not just Java!). Once that’s done, we’ll be able to write some actual useful programs!Part A - Primitive Types and StatementsIn computer programs, we can store values in placeholders, called ‘variables’, in exactly the same way as we use variables in mathematics. In maths, these values can usually just be numerical figures. In programming however, we have a number of different types. We say a variable has a particular type, to mean that it holds particular types of values.Here are the main ‘primitive types’:NameExplanationExampleLengthintAn integer, i.e. holds a round number.-34 bytescharA single ‘character’, i.e. symbol.‘e’, ‘!’ (notice the single quotes)4 bytesboolA ‘boolean’, which is a truth value.true, false (and nothing else)4 bytesfloatAny decimal number (i.e. not necessarily whole)1.42f, -6.0f (the ‘f’ at the end is to distinguish it from a double type below)4 bytesdoubleAgain, any decimal number, but we can store double as many digits.5.3, 7.48 byteslongNot used as often, but allows us to store very large integer numbers.132458l (notice the ‘l’ at the end, to distinguish it from an integer)8 bytesWe’ll see some examples of how we can use these in a short while, as well as what we mean by the ‘length’ column in the table.StatementsA statement in programming simply represents some kind of ‘action’. Such actions might be prompting some procedure to launch a missile, or much simpler things like assigning a value to a variable. You may also have heard of ‘if’, ‘for’ and ‘while’ statements which we’ll get onto later, along with all the other possible actions we might have.The simplest action is an assignment. This is the process of assigning a variable a value. The ‘syntax’ is this:type variableName = value;Let’s dissect this.The type is whatever type we want the variable to be. e.g int, bool.The variable name can be anything. Convention however (at least for the moment) is that the variable name starts with a lower case letter. A popular convention for naming variables is camel case. This involves capitalising all but the first word in the name. e.g. “stockPriceValue”. Make sure your variable name is descriptive of the value being stored in it, so people reading you code know what it represents. Avoid using numbers, symbols, and you’re not allowed a space.The = in this case does not mean equality. It means whatever is on the right of the equals is assigned to the variable on the left. We’ll see later how we can express equality in the mathematical sense. In many programming languages, assignment is instead written as “:=”, with a colon, so we might have “x:= 2”.Finally we have the value we want to assign to the variable.In many languages (including Java), we need to put a “;” at the end of the statement to say we’ve finished the particular statement. In other languages (such as Python), the program reading your code can work it out without the semicolon. Some examples:int x = 4;bool isPresent = true;float stockValue = 4756.35f;Primitive Types revisitedWhen you assign a variable, the computer needs somewhere to store the value. We’ll see later that there’s different types of places the computer might store the value.All variables are assigned either 4 bytes or 8 bytes. 1 byte = 32 bits, where a bit is a 0 or 1 (these are known as binary values). Therefore integers and floats for example are stored using 32 bits. A ‘double’ and ‘long’ variable however is stored using 64 bits, allowing us to store twice as much information. You may wish to read up on what a ‘binary representation’ is to understand this more.Definition: PRIMITIVE TYPEA primitive type is one where the value is directly stored in the space assigned for it. This means for example that an int, say 432, can be converted to binary (i.e. 0s and 1s), and this value is put in the 4 byte slot allocated to it.A ‘String’ is a type that is not primitive. A ‘string’ is simply a sequence of characters, e.g. “hello Bob” to represent some textual value. Just like other variables, we assign 4 bytes to hold the value. However, the string might be very long (e.g. an essay!), so it wouldn’t be possible to store it with just 32 bits. Instead therefore, we store a numerical address (which can think of for example as a house number), which ‘points’ to where the value of the string is actually stored. This therefore is why a String is not a primitive type, because we don’t actually store the value itself in the slot in memory allotted to it.You might at this point be thinking “Why do we restrict the value of the slots to 4 or 8 bytes? Why not make the slots bit enough to hold the value depending on how long it is? We’ll see the reason when we come on to arrays.So where are these ‘slots’ to hold values? These are stored on the stack.x (int): 44 bytes = 32 bitsb (bool)= falsestr (String) = 253 “hello”253253 is the ‘address’ for some location in another part of the memory.STACKWhile this stuff might seem like very technical detail, there are reasons why it will be important later, when for example we consider equality of non-primitive types.Operations on primitive typesWe can use a number of different ‘operators’ on primitive values. An ‘operator’ is just a symbol used to represent function which takes two arguments. For example, + is obviously an operator which takes two arguments and adds the values together. + is an infix operator because the operator appears between the two arguments (i.e. 3 + 2, not + 3 2).Some examples:2 + 3: just addition on integers. Obviously also works on floats and doubles.2 * 3 and 8 / 4: Multiplication and division. Important note: If you use / on integers, the result is actually the whole number of times the divisor goes into the dividend. e.g. 7 / 3 will give you 2. 7 % 3: The ‘modulus’ operator, which finds the remainder after the divison. In this case, the result will be 1.true && false: The && operator means ‘and’, and is usually applied to Boolean values. The result is true if both the first and second argument is true, and false otherwise. We’ll see how this can be used later.true || false: As above, but represents ‘or’. Gives true if either the first or the second value are true.== This is equality! It takes the two arguments, and give the Boolean ‘true’ if they’re equal, and false otherwise. So 3==4 evaluates (i.e. simplifies) to ‘false’. We’ll revisit equality later.You might wonder if we can mix operands (i.e. the arguments of the operator) of different types. What do you think happens if we evaluate this:char myValue = ‘c’ + 2;The answer, curiously, is that myValue now holds the value ‘e’. This is because primitive types are ultimately just stored as a ‘number’ (represented in binary). ‘c’ happens to have the numerical value 99 (you will find the corresponding numbers for characters by looking up an ASCII table). 99 + 2 = 101. And since myValue has the specified type ‘char’, it will be interpreted as a character. Conveniently, the numbers representing each of the letters of the alphabet are in order, so 101 gives us ‘e’. So we can perform arithmetic using characters as well as numbers! We’ll see an example program later where we want to print to the screen all the 26 letters of the alphabet using a loop and character arithmetic.There are some type combos that we are not allowed to combine. For example true + 5 is both meaningless and will give us a code error. 2 * 4.03 though (where we’ve combined an integer and a double) is meaningful, and gives us back 8.06 (a double).More statementsWe’ve previously only seen ‘assignment’ as a type of statement. What value does y store at the end of this program?int x = 3;x = x + 1;int y = x * 2;The answer is 8. On the second line, the assignment first evaluates x+1 using the existing value of x, then updates the value of x with the result of that expression. In this case, we’ve reassigned the value of x. Notice we didn’t have to specify the type of x again on the second line, because we’ve already declared it on the first. Technically speaking, the first line is a declaration (with assignment) where we’re announcing the creation of x, whereas the second line is an assignment.What other kinds of statements can we have then?If StatementsLet’s see a few concrete examples first to see what ‘if’ means.int x = 4;if(x>2) {x*=2;x+=3;}We could describe in words the program as follows: “We first assign x the value 4. If this is greater than 2 (which it is), we multiply x by 2, then add 3 to it”.The *= and += are new types of statements we haven’t encountered yet. x*=2 is a quick way of the assignment x = x*2. Similarly x+=3 means x = x+3.Why the curly braces { }? This allows us to group these two statements involving reassigning x together. You may have deduced the if statement consists of some condition (in normal brackets), which we determine if it’s true, followed by a statement that we carry out if it is indeed true. The curly braces allows us to say we do both x*=2 and x+=3 if we find that x>2 is true. If we have just one statement, we don’t need to use curly braces:if(x>2)x+=1;The type of the condition should be bool, since it represents a ‘truth’ value. We could technically write if(1), but it’s not very meaningful. There are cases however in some languages where it may be useful to do something like this. In web-based languages such as Javascript or PHP, where the variable ‘str’ holds some string value, if(str) asks whether the length of str is more than 0 characters (i.e. is not the empty string). So it’s possible to have a non-boolean type for a condition, but let’s not worry about this for the moment.We can also specify some statements to run if the condition is false. For example:if(x>=2)x = y;else x = z;Presuming that x, y and z already exist, this sets x to the value y if the existing value of x is greater or equal than 2 (notice that we use >= rather than >), and set x to z otherwise.While loopsIt’s possible to keep repeating a statement (or statements) until some condition is met. We can actually start to build something resembling a useful program now! For example, let’s say we wanted to sum all integers from 1 to n.int n = 20;int total = 0;int i = 1;while(i<=n) {total+= i;i+=1;}Let’s try and dissect this, as it’s slightly more complicated! We have three variales. n in this case represents the number we’re summing up to (i.e. 1 + 2 + … + (n-1) + n). ‘total’ represents our running total, i.e. what we’ve counted so far. ‘i’ represents the current number we’re adding. So it’s starts with 1 (since it’s the first number we’re adding to our running total), and has the value ‘n’ by the time we’ve repeated the statements in the ‘while loop’ for the last time.Let’s consider it step by step:To start, n=20, total = 0, i = 1;It is true that i<=n (since 1<=20), so we perform the statements inside the curly braces.total+=i is the same as total = total + i. So the new value of total is 1, representing the fact we’ve started by putting 1 in our running total.We increment i by 1, so say that we now want to add 2 to our running total.Since we’ve finished this two statements, we consider the condition of the while loop again. Does i<=n? Yes, because 2<=20 evaluates to true.Now, total = total + i gives total = 1 + 2. So the new running total is 3. Again, we increment i on the next line, so i is now 3.…When i is finally 20, we find our condition 20<=20 still just about holds true. On the first line of the while body (the ‘body’ refers to the statements we execute for an if/while/for statement), we add 20 to the running total. i is incremented again, so is now 21.We again evaluate the condition. Is i<=n. Now it’s false! 21<=20 is not true, and so the ‘while loop’ finally terminates. The program would now proceed to whatever comes after the while statement if there was anything following it.In general, the principle to coding is:Thinking of some algorithm (perhaps in words, or thinking about it conceptually) that achieves what we want. In this case, we’ve thought of a method on paper we can add the numbers 1 to n (i.e. by adding 1, then 2, then 3, and keeping a running total).We then translate this method/conceptualise to code.Sometimes step 1 is the tricky part and step 2 is easy. And sometimes it’s the other way around!Those with some mathematical knowledge will know that we could have found the sum of 1 to n much easier using a summation formula. Our code could have been condensed to a simple:int total = 0.5 * n * (n+1);This illustrates nicely that there’s often multiple solutions to a given problem, and some solutions are much more elegant, and require much less code, than others.Turning this into a runnable program.Let’s actually run this code!public class MyTestClass {public static void main(String[] args) {int n = 20;int total = 0;int i = 1;while(i<=n) {total+= i;i+=1;}System.out.println(total);}}Press the ‘Run’ button again at the top of your workspace to run the code. Hopefully, you’ll see the correct result of 1 + 2 + …. + 20.Rewriting the program using a ‘for’ loopThere’s actually one more kind of construction besides ‘if’ and ‘while’ statements. These are known as ‘for loops’. For loops basically allow you to vary some variable between some range. For example, it might be useful to do something with all the numbers between 10 and 100. We’ll see particularly when we come to arrays that for statements can be very useful! Here’s a simple example:for(int i=100; i<200; i++) {System.out.println(i);}What do you think it does? Here’s what’s going on:We’re creating some temporary variable, in this case ‘i’, which holds the value we’re varying. We give it some initial value – this is the number at the start of the range (in this case 100).The expression after the first semi-colon is some condition involving our variable that needs to hold true for the code between the { … } to be executed. In this case, we’re saying that our value of I must be less than 200.The statement after the second semi-colon says what we do with our value of I each time. We previously saw that i+=1 increases the value of a variable by 1. i++ is an alternative way of writing this.The result of the program therefore is to print out ‘i’ while I varies between 100 and 199. We don’t see the 200 because the inequality is strict.You may be thinking that when adding the numbers from 1 to n, the for loop might be useful because we do indeed ‘do something’ with the numbers in a particular range. We rewrite our program more simply like this:int currentTotal = 0;for(int i=1; i<=n; i++)currentTotal+= i;Here we’re using the for loop to let ‘i’ vary between 1 and n, and add each of these numbers to our running total. Notice that just like the while loop and if constructions, we don’t need the curly braces if we only have one action to do (although the program would still run if we put them there).One Final Note: The ‘Scope’ of VariablesI’ve said that in a ‘for’ loop, the variable ‘i’ we’ve declared is only temporary. What exactly do I mean by this?It means that ‘i’ can only be used inside the body of the for statement. For example, this would give an error:for(int i=0; i<10; i++) {System.out.println(“Hello! “+i);}int b = i + 1;The first 3 lines of code are fine, and in line 2 we’d print out “Hello 0”, then “Hello 1” and so on. This works because ‘I’ is said to be scoped to the ‘for’ statement. That is, it ‘exists’ while we’re in the body of the for statement (in this case, between the curly braces). However, the last line of code uses ‘i’ outside of this scope, so will raise a compiler error.A variable can only be declared once in the same scope. So this case for example is invalid:int i = 3;for(int i=0; i<10; i++) { … }This is because the ‘i’ has already been declared on line 1, and we can ‘reassign’ to it after, rather than create it again. However, interestingly, this is OK:for(int i=0; i<10; i++) { … }int i = 3;This is because the scope of the first ‘i’ is only the ‘for loop’. It is discarded after, so we recreate/redeclare it once more.We’ll see in the next section when we look at methods/functions how variables might be scoped in different contexts.Section ReviewHere’s a summary of what we’ve learnt so far:Our program consists of a list of ‘statements’. There’s a number of statements we explored:We can declare/create a new variable using “type variableName = initialValue”, e.g. “int x = 2” creates a variable, of type ‘integer’, that initially holds the value 2.We can reassign the value of a variable. E.g. “x = 3” updates the value of x to 3. Obviously, a variable must already have been created if we want to modify its value.x+=2 is a shorthand for x = x+2, i.e. updating the value of x by increasing its value by 2. We can similarly do x-=2 or x*=2 or x/=2.x++ is a shorthand for x+=1.“If” constructions allow us to run some statements based on some condition holding. E.g. if(x==2){ System.out.println(“It is 2!”); } else { System.out.println(“It isn’t 2”) }“While” constructions allow us to run some statements ‘while’ the given condition holds.“For” constructions allow us to execute some statements based on some temporary variable varying between a range of values.There are different ‘primitive types’ which store simple kinds of values, such as integers (int), real numbers (float or double), Booleans (bool) and a single character (char). “String” is not a primitive type (hence why the type name is not all lowercase letters).We can combine values using various arithmetic operations. We could use “int x = y + z” for example. “==” is used for equality, and the result of type bool. So “2==4” yields “false”, as does “2>4” or “2>=4”. “true && false” (i.e. logical ‘and’) would give “false”, whereas “false || true” (i.e. logical ‘and’) would give “true”. “7%2” gives us the integer 1, because it’s the remainder when we divide 7 by 2. Beware: 7/2 gives us 3 not 3.5. This is because an integer divided by an integer gives an integer (where anything after the decimal point is discarded). If we did 7 / 2.0, then the compiler sees the first number as a integer and the second as a ‘double’, so the result is a double, i.e. the correct result of 3.5.Check your knowledgeWhat do the following programs print out? (without running the code) Answers below!123int x = 0;while(x<100)x++;System.out.println(x);int x = 3;if(x>3)x*= 2;else x*=3;System.out.println(x);int y = 1;for(int x=0; x<100; x++){ if(x%2==1)y*= x;}System.out.println(y);Program 1 gives you 100! Each time the while loop runs its statement, we add 1 to x. When x=99, the condition 99<100 still holds, so x gets incremented to 100. But then it’s not the case that 100<100, so the while loop terminates.Program 2 gives you 9. In the ‘if’ statement, it’s not the case that 3>3 (because the inequality if strict, so we run the ‘else’ statement rather than the ‘then’ statement. x*=3 updates the value of x by multiplying by 3, so we get 9.Program 3 is a bit harder. We have a ‘for construction’ where the value of x ranges between 0 and 99. For each of these numbers, we’re seeing if x%2==1. What does this mean? It says that if we divide by 2, is the remainder 1? That’s equivalent to asking if x is odd! So for each odd value between 0 and 99, we’re updating y so that we multiply by each of these values. Thus y ends up being 1 x 3 x 5 x … x 99.Part B - MethodsWith our ‘add all the numbers up to n’ program, we had to specifically set the value of n. You might think it useful however to be able to reuse this method for different values of n. In maths, this concept is known as a function. Here’s an example function:2xxtwiceor f(x) = 2x. You may also sometimes see the domain and the range of the function specified. For example f:R -> R indicates that the input of our ‘twice’ function can be any ‘real’ number, and the output is similarly any ‘real’ number.With methods/functions in programming, we similarly have to specify our inputs, what type they are, and what the type of the output is. This is how we’d code our ‘twice’ function:double twice(double x) { return x*2;}Let’s dissect this. The first line specifies the various properties about the method. The first ‘double’ tells us the return type, i.e. the type of what the method returns (in this case some real number). Next is the method name. In the brackets, we specify the arguments of the function, where each one we specify the type. So in this case, we have one input x, which is also a real number.If we want multiple arguments for the function, we can comma separate them:double add(double num1, double num2) {return num1 + num2;}Create a new class for these new methods within Eclipse. Unlike before, don’t tick the ‘main method’ checkbox. Name it “MathsUtils”.public class MathsUtils {public static double add(double num1, double num2) {Return num1 + num2;}public static int addToN(int n) {int runningTotal = 0;for(int i=1; i<=n; i++)runningTotal+= i;return runningTotal;}}Hmm, we seem to have used a few extra keywords here:The public keyword means we can use the method in other classes. If it was private, we could only use it in other methods in the same class. This is known as an access modifier. It basically stops us making methods that we want only to be used within the class (e.g. to calculate intermediate results) used elsewhere.The static keyword is a bit more complicated. We’ll see in later sections the distinction between a class and an object. But for the moment, consider it as allowing you to refer to your method elsewhere as YourClass.myMethod(arguments).Let’s use this elsewhere. In some other class that DOES have a main method:public class TestClass {public static void main(String[] args) {System.out.println(MathsUtils.addToN(100));}}Now run this code and voila, you should get the correct result printed to the console. Now that we have moved our ‘addToN’ method to another class, we can keep reusing it for different values of n.Before we move on, let’s look at the type signature of the ‘main method’:It’s static. So when the program runs, it in essence calls TestClass.main(...).The return type is void. This is a special type which just means “our method doesn’t return anything”. Unlike mathematical functions, methods in programming need not actually give you back a result. We might have a method “activeEjectorSeat” in a fighter plane – but we might not be interested in the result this gives once the method has run!It’s input is of type String[]. We’ll see in the very section that this is an ‘array of Strings’. If we were running our program from the command line, we can actually pass information to the program, which will be stored in args which we can use within the main method if we wish (we haven’t so far). It’s possible to set these arguments in Eclipse too, but let’s not worry about this for the moment.Some basic pre-written methods you should know aboutMost programming languages have large swathes of pre-written code for you to use. These are known as libraries. Java has libraries for all sorts of things, whether it be accessing a database, doing mathematical calculations, manipulating Strings, drawing stuff and even connecting with a digital piano! (perhaps my favourite ever program I’ve written is to get the screen to flash up with “MERRY CHRISTMAS!” if I played Jingle Bells on my piano – I probably had too much free time).But here’s some initial libraries you should definitely know about.StringI’ve mentioned before that a ‘string’ is not a primitive type. And that’s handy, because the String class has all sorts of useful methods:char charAt(int i): This gets the character at the ith position of a string. For example, the code:String str = “Hello”;System.out.println(str.charAt(1));Will print out: ‘e’. Notice firstly that this didn’t give us ‘H’, which is the 1st letter. This is because in programming, we tend to start counting from 0. Thus the argument of 1 actually gives us the 2nd letter. Get used to this fact!Notice also that we applied the method directly to the variable ‘str’, rather than say write “String.charAt(...)” like we did in the previous section. This is because the charAt method is not static, and thus it applies to a specific variable and its value. We’ll cement this later.int length(): This gives us the length of a string, i.e. how many characters it has. So “Hello”.length() will give us 5.MathThis class contains a huge number of methods to do all sorts of mathematical calculations. Here’s just a few:static int round(double num): This rounds a number to the nearest integer. For example Math.round(4.32) gives us 4.static double sin(double angle): Unsurprisingly, this gives us the ‘sin’ function. But beware, this takes the angle in radians, not in degrees. Older students will know that 180 degrees is the same as pi radians. We could therefore find the sin of an angle in degrees as follows:double angle = 45; // in degreesSystem.out.println(Math.sin(angle * Math.PI / 180));Here we’ve used the constant Math.PI. We can see the Math class doesn’t just have methods we can use, but constants as well!static double pow(double a, double b): This gives us ab. So Math.pow(2,3) gives us 8. Obviously quite handy!How to find out the methods a class has in EclipseYou never actually have to ‘memorise’ the methods a class has. You tend to ‘discover’ them. Eclipse has some nice tools to help you see the methods available in a class.Just type in Math. Into Eclipse. As soon as you type the dot, you’ll get a popup showing you all the possible methods and constants you can use. You can either double click on an option to then fill in the code, or use the up and down arrays and press return to select. Here, we can see that Math contains a lot of methods, as well as the constants PI and of course, E.If this pop up doesn’t show up for any reason, put the text cursor after the dot, then press “Ctrl + Space”. In general “Ctrl + Space” is a way of ‘auto-completing’ code. There’s all sorts of tricks you can use to speed up coding. For example, just type “sysout” on a line, followed by “Ctrl + Space”. Eclipse will expand this for you to System.out.println(...). Similarly, create a new class with nothing inside it, and click within the curly braces. Type “main” there and press “Ctrl + Space”. This will expand into a main method! Quite handy huh?Part C – Converting between typesIt’s often quite useful to convert between different types. For example, suppose someone typed in a number into your program which you wish to do some calculations with. When they initially type it in, it’s just text – i.e. it’s of type String. But we want it to be type int, or double/float, since we can’t do mathematical operations on a String. This summary table indicates how we convert between different types:TOintcharfloatStringFROMint(int) 'c'(presuming you want to character corresponding to an ASCII number)No conversion necessaryString.valueOf(63)charCharacter.digit('6', 10)(the 10 just means the number is base 10)String.valueOf('c')float(int) 6.37f(this ‘truncates’ the decimal, i.e. discards everything after the decimal point – it does not round)Don’t do it!String.valueOf(4.32f)StringInteger.parseInt(“693”)"Hello".charAt(3)(gets the 4th character)Float.parseFloat("3.23")So for example, if we wanted to convert from an int to a String, then using the table, we’d do:int exampleNumber = 24;String numberAsAString = String.valueOf(exampleNumber);We now have a new variable numberAsString which holds our number, except the type of it is now String. We’ll see in a later program involving Roman Numerals why this might be helpful.This example gets the 3rd digit (as an integer) of a number that was in String form:String numAsStr = "59403";char c = numAsStr.charAt(2);int digitThird = Character.digit(c, 10);This involves two conversion processes – firstly getting a char from within a String, and then converting that char into an int. You’ll get used to these over time.You might want to practice these conversions by starting with an int, converting to a char, then to an String, and then back to an int again. Try writing this in one line of code.CastingYou might wonder looking at this table why we have a primitive type in brackets when converting from an int to a char or a float to an int. This is known as casting, and basically means we attempting to directly change the type. So for int n = (int) 8.03, we’re taking the value 8.03 which is of type double, changing the type to int using (int), and now we’re allowed to assign this resulting value to a variable n which says the value must be of type int. When we convert to an int, we have to discard any data after the decimal point. Why can’t we do a similar cast to and from String then? We can’t cast between primitive types and non-primitive types. String is a class, not a primitive type.Part D – ArraysYou might wonder how we might store a ‘collection’ of things in a single variable. One way to do this is using arrays. An array contains a number of ‘slots’ in which we can put information. Arrays are useful because it’s not always practical (or even possible) to have a separate variable for each bit of information in a collection. Imagine for example we wanted to get all the words in a sentence, and store each one separately. If we were to have a separate variable for each word, then (a) we would have to have a huge number of variables for a long sentence and (b) if the sentence was the change in length, we’d need a different number of variables. An array would solve this particular problem. Some Quick BasicsDeclaring: To declare/create an array (just as we would create a variable of a primitive type), use something this:int[] nums = new int[4];In this case, we’ve created an array of integers, and allocated 4 slots. The syntax might seem a little unusual at first, and we haven’t yet covered what the ‘new’ keyword means (we’ll encounter it later, but we basically use it when we creating something that is not a primitive value). Currently these slots don’t have anything in them. But we can assign a value to a particular slot:nums[2] = 3;This is what our array would look like after:3 0 1 2 3Indexing: Remember that in computing, we start counting from 0. So the slot with index 2 is actually the third slot. We can also access the value of an array. This is known as indexing the array: nums[2] = nums[2] + 1;As you can see, the ‘index’ goes in square brackets, both when assigning to a lost and retrieving the value in the slot.Initialising/assigning: If we know in advance what values we’re going to put in the array, we can combine the process of declaring the array variable and assigning it some values:String[] colours = new String[]{ “green”, “blue”, “orange” }Notice in this case we didn’t have to put the size of the array between the second square brackets. This is because the compiler can work out the size from the number of items you’ve put in the curly braces.Getting the length: We can get the length of an array using myArray.length. So colours.length would give us 3. Note that this includes empty slots! So nums.length would give us 4, even though we’ve only put one item in it.Cycling through an array’s values using a ‘for loop’Perhaps the most common way of using a for loop is to go through the values of an array and do something with each one. Recall that for loops are used when want to repeat some action using some number in some range. We do have a range: the slot numbers in an array (of length n) go from 0 to n-1 (not including n, because we have 0 to n-1, not 1 to n, as we start slot numbers from 0). Here’s a few examples:String[] colours = new String[]{ “green”, “blue”, “orange” }for(int i=0; i<colours.length; i++) {System.out.println(“Colour: “+colours[i]);}This for loop does it statement for ‘i’ in the range 0 to colours.length-1 (because we used < not <=). We then used this variable to index colours and print out the value.Here’s another nice example of printing out the words in a sentence and its length:String sentence = “This is a cool sentence.”;String[] words = sentence.split(“ “);For(int i=0; i<words.length; i++) {System.out.println(“Word: “+words[i]);}System.out.println(“Length of sentence: “+words.length);Here we’ve used a method of the String class we haven’t seen yet – split. This takes one argument, the ‘delimiter’, or a string we use to split up a larger string. In this case, we’re saying to split the sentence up by “ “, i.e. by spaces. The output is an array of Strings which contains the sentence split up into words.Warning: You might think we can print out the contents of an array with System.out.println(myArray). Try it: you’ll see it gives you something fairly nonsensical. You have to cycle through it values and print them one by one.Example program: Finding the factors of a numberWe’re going to create a method that finds all the factors of a number, and puts them in an array. Add this method to your MathsUtils class:public static int[] findFactors(int n) {// …}How might we find the factors of the number n? Well, we could try candidate factors from 1 up to half of n (there can’t be any factors above half its value, except for itself). And to tell a number is a factor, we have to see if there’s a remainder of 0 when we divide n by the candidate factor.We’ll create an array ‘factors’ which holds these factors we’ve found. One problem however (and why for this particular program I wouldn’t usually use an array) is that we don’t know in advance how many factors we’ll find so we don’t know how big to make the array so have exactly the right number of slots. Our strategy here therefore is to have a temporary array which will have definitely have enough slots to put our factors in (although with some slots likely to be empty), and then clean up at the end by returning an array of the right size and with no empty space.Let’s get started!public static int[] findFactors(int n) {int[] factors = new int[n];int c = 0;for(int i=2; i<=n/2; i++) {if(n%i==0) {factors[c] = i;c+=1;}}return factors;} Here’s what’s going on:On the first line of the method, we’re creating our array. We’ve got n slots, because that’s definitely going to be enough for all our factors.We’ve created a variable c. The point of this is to act as a counter for how many factors we’ve found so far. This is so we know the correct slot number to put a factor into the factors array once we’ve found a new one.Our for loop goes from 2 to half of n. You might wonder what happens if n is an odd number. Recall that an integer divided by an integer gives us a integer, discarding any decimals. So if n is 15, we’d look for factors up to 7. That seems fine. And even if n/2 gave us a decimal number (e.g. a double), then it wouldn’t be a problem because if n=7, we’d execute the body of the for loop with i=3 (since it satisfies the for loop’s range condition of 3<=3.5), and once we do i++, I will be 4, and 4<=3.5 is not true, so the for body wouldn’t run again.Inside the for loop (i.e. in the body), we’re checking whether our candidate factor i is indeed a factor. We’re once again using the % operator to find the remainder.If it is a factor, we add it to our factors array in the correct slot. c effectively points at the correct slot number to put our factor in. Since we’ve added a factor to our array, we now need to move c along to the next slot number for when we find the next factor.We’re returning factors at the end. But we have a lot of empty slots, which is not somewhat messy (because if another method using findFactors tries to get the length of the array so for example we can look through the factors we’ve got with a for loop, the .length value is going to be the size including empty slots, not the number of factors there actually are).There’s two ways we can fix this last problem.Method 1: We could create a second array which has the correct number of slots, say factorsNew, and copy the factors from the factors array to factorsNew. Recall that c is a counter which counted the number of factors we’ve found. We can now use that to know the size of the array we need.int factorsNew = new int[c];for(int i=0; i<c; i++)factorsNew[i] = factors[i];return factorsNew;n = 20 (and c ends up being 4 after finding the factors)We’ve used a for loop here to copy each element of factors into factorsNew. Here’s a diagram which might help visualise what we’re doing here:int[] factors2451024510int[] factorsNew Method 2: If there’s a common operation you want to do, there’s almost certainly a utility method for it! Googling “Java array copy” brought up a utility class System.arraycopy. Here’s how we’d use it:int factorsNew[] = new int[c];System.arraycopy(factors, 0, factorsNew, 0, c);return factorsNew;The arguments are as follows:The first is the array we’re copying from (factors).The second is the index of the source array which we start copying from (i.e. slot 0).The third is the destination array, where we’re copying to (factorsNew).The fourth is the index of the destination array we start copying to (again slot 0, so we copy to the start of the array).The fifth is the number of items we’re copying over. We’re copying c items in this case, because we found c factors.In general, you never need to explicitly remember these library functions because they’re so easy to look up. But some are so common, that it’s worthwhile to remember how to use them to save you time in future.The System class has a number of useful methods. We’ve already seen println, and now we’ve seen arraycopy. Remember, in Eclipse you can find out what methods are available by typing System. , and hopefully you’ll get a popup listing the various methods.Test Your KnowledgeWrite programs using arrays to do the following:Generate an array with the numbers 1 to 100 in them (and then print out the items of the array).Generate an array of the first 100 square numbers. Then subsequently update the array so each value is doubled.Slightly more difficult: Generate an array with the letters of the alphabet (without explicitly writing out all the letters). Hint – you character arithmetic.AnswersProgram 1: (note that our for loop varies i from 0 to 99, so we have to add one to get the numbers 1 to 100)int[] nums = new int[100];for(int i=0; i<100; i++)nums[i] = i+1;for(int i=0; i<100; i++)System.out.println(nums[i]);Program 2:int[] squares = new int[100];for(int i=0; i<100; i++)squares[i] = Math.pow(i+1, 2);for(int i=0; i<100; i++)squares[i] = squares[i]*2;Program 3:char[] alphabet = new char[26];for(int i=0; i<26; i++)alphabet[i] = ‘a’ + i;Another Example: Roman NumeralsYou’ve been asked to write a program that converts the current year (or any number) into roman numerals. Roman numerals have symbols for units, tens and hundreds. So for example, to get the roman numeral representation of 654, we get the representation of 600 (“DC”), the representation of 50 (“L”) and the representation of 4 (“IV”) and just stick them together giving “DCLIV”.Create a new class called “RomanFun” and copy this code. We’ll then dissect it to find out what’s going on:import java.io.BufferedReader;import java.io.IOException;import java.io.InputStreamReader;public class RomanFun {public static String convert(int n) {String[] units = new String[] { "", "I", "II", "III", "IV", "V", "VI","VII", "VIII", "IX" };String[] tens = new String[] { "", "X", "XX", "XXX", "XL", "L", "LX","LXX", "LXXX", "XC" };String[] hundreds = new String[] { "", "C", "CC", "CCC", "CD", "D","DC", "DCC", "DCCC", "CM" };String nAsStr = String.valueOf(n);int u = Character.digit(nAsStr.charAt(nAsStr.length() - 1), 10);int t = Character.digit(nAsStr.charAt(nAsStr.length() - 2), 10);int h = Character.digit(nAsStr.charAt(nAsStr.length() - 3), 10);return hundreds[h] + tens[t] + units[u];}public static void main(String[] args) {BufferedReader br = new BufferedReader(new InputStreamReader(System.in));while (true) {try {System.out.print("> ");String input = br.readLine();System.out.println(RomanFun.convert(Integer.parseInt(input)));} catch (IOException e) {e.printStackTrace();}}}}Here’s an explanation of the convert method:As we’ve done before, we’ve created a (static) method that does the conversion process, then written a separate main method so we can test it out. Remember that by putting the code to convert a number to roman numerals in a separate method, it makes it easier to execute the code multiple times for different numbers as inputs, and makes it easier to reuse elsewhere.The method signature tells us we’re taking an integer as the input (as a variable n), and returning a String at the end which is the roman numeral representation.In a String array, we’ve put the various roman numeral representations of each number for units, tens and hundreds. Notice that the roman numeral for 4, i.e. “IV”, is in ‘slot 4’ of the array (remembering slot 0 is the first slot because we count from 0). That means if we were to use units[4], we would get the roman numeral for 4. So we just need to establish the ‘units’ digit of the input, say u, and then use units[u] to find the digit as a roman numeral.The first element of each array is the empty string because 0 has representation in roman numerals. If we had the number 103 for example, we’d have CIII, without using any letters for the number of 10s.If say our input is n=541, and we’ve found some way (which we’ve yet to discuss) of getting the hundreds digit h=5, the tens digit t=4 and the units digit u=1, then hundreds[h] + tens[t] + units[u] will give us the final result we want. Here, the + operator is being used on strings, so it has the effect of joining the strings together.So the remaining question is how we find h, t and u? One way is to convert the number to a String, so 541 becomes “541”. If we do, we can use the String class’ .charAt method to get each of the characters that make up the string, and thus each digit.We can use String.valueOf(n) to convert our integer n to a String. We’ve assigned this to a variable nAsStr.We can get the length of the String (and thus the number of digits in the numbers) by using nAsStr.length(). For our 541 example, this will obviously be 3.The units digit appears at the end of the number. What index is this at? Remember that .charAt(0) will get the first digit of the String, .charAt(1) the second, and so on. Because we start counting from 0, we actually want the character at position in the String nAsStr.length()-1. So we can get the character (of type char) of the last digit using nAsStr.charAt(nAsStr.length()-1). This gives us ‘1’.But we want this character as an integer. We can use the method Character.digit to do this. Its first argument is the character we want to convert. The second argument is the ‘base’. Use 10, because the English number system (or more historically accurate, the Hindu number system!) is base 10.Similarly, we can get the tens and hundreds digit by looking at the second from last and third from last digit respectively.That’s the convert method sorted. The main method in the code shows how we can actually take input from the console! Previously, our programs have printed out to the console using System.out (appearing at the bottom of the screen if using Eclipse). But we can use System.in to actually type into the console as well and use the input.Let’s break it down line by line:BufferedReader br = new BufferedReader(new InputStreamReader(System.in));Don’t worry about the exact syntax yet, since we haven’t really discussed the creation of objects. But in our variable br, we’re essentially getting a connection to the console so we can read from it one line at a time.while (true) {A while loop that takes ‘true’ as its condition will loop forever, because the condition of the while loop always holds (because it is literally ‘true’!). This is good, because it means our ‘Roman Numeral Service’ will always ask for more numbers to convert without stopping.try {Later on we’ll be covering ‘exceptions’. But for now this is all you need to know: Some methods of classes require has to have some backup behaviour if something goes wrong. Suppose for example there was a method to read from a file. What if the file didn’t exist? Or what if for some other reason we couldn’t read from it? We need to be able to have a contingency strategy in such cases. The basic syntax of this is: try { ..Do some code which might go wrong.. } catch(..potential problem..) { ..Backup strategy.. }System.out.print("> ");The prints out a “>” symbol onto the console. Notice that this method is print not println. The difference is that in the former, what is printed doesn’t get a line to itself. Anything printed after (or anything we type into the console) will come after it on the same line, rather than the next.String input = br.readLine();We’re using the readLine() method of the class BufferedReader (because the variable br we created is of type BufferedReader). This will wait until we’ve typed something into the console and pressed return (because we earlier told the BufferedReader to ‘listen’ to System.in), and then return a String. We’ve put the output of the method into a variable input.System.out.println(RomanFun.convert(Integer.parseInt(input)));This does multiple things in one go. Firstly, the number we typed into the console is currently in String form. We need to convert it to an integer, because the RomanFun.convert method expects an integer as its input. Integer.parseInt converts from a String to an integer. Roman.convert then uses this integer and gives back a String containing the Roman numeral form. Then finally, System.out.println prints it out to the console.} catch (IOException e) {This line says we want to deal with any problems that arose in the block of code following ‘try’. In this particular case, the .readLine method could of had a problem in terms of reading from the source (e.g. for some reason, we couldn’t get what was typed into the console). ‘IO’ here stands for ‘Input Output’. So this line code says we’re dealing with any problems to do with input/output.e.printStackTrace();This is our ‘backup strategy’. Here we’re just printing out the details of the error that occurred (when it does occur). The variable ‘e’ represents the error that occurred. And it has a method called printStackTrace() which prints details of the error. Don’t worry about this now, we’ll be covering it later.Things you might want to try to extend this program: Why not try and extend the code above to deal with thousands in roman numerals? The roman numerals for 1000, 2000 and 3000 are M, MM and MMM respectively.The maximum number you can hand in Roman Numerals is 3999. Make sure your program returns something sensible (e.g. the string “INVALID”) if the number inputted to your convert method is outside this range.Your program will currently give an error message if you try to enter a two digit number, because when trying to get the hundreds digit using .charAt, you’ll find that nAsStr.length()-3 will give you a negative number (and you can’t get the -1th character of a String!). Make use of ‘if’ statements to make sure you handle different length numbers.Object OrientationThere’s been a few instances in our programs where we’ve used the ‘new’ keyword when assigning a value to a variable. We did this for example when creating an array, and some of the example programs, we saw something like:BufferedReader br = new BufferedReader(new InputStreamReader(System.in));This was different to when we say assigned ‘primitive’ values to a variable, e.g:int x = 3;The ‘new’ keyword is creating a new ‘object’ for us. But let’s take a step back first and consider what an ‘object’ is. With primitive types, we saw that we can only hold a simple value, like an integer or character. But there’s certain things that we might like to use or assign to a variable that aren’t quite as simple. Take a fraction for example. We might want to assign the fractions ? and ? to variables x and y, and then say manipulate them to find x + y to yield a new fraction. Primitive types won’t let us do that (unless we convert the fractions into decimal form). A fraction is an example of an ‘object’ – it has multiple constituent values, i.e. the numerator and denominator, and behaviour associated with it, such as multiplying the fraction by a constant or another fraction, or adding/subtracting another fraction it.An object therefore can have two things:Associated properties. We could call this the ‘state’ of the object, to mean the data currently associated with it. We’ll see this term being used particularly often.Associated behaviour.Let’s roll right into a concrete example, sticking with our fraction theme.Fraction ExampleCreate a new class ‘Fraction’, and then copy this code. I’ll then explain it bit by bit:public class Fraction {int numerator;int denominator;public Fraction(int n, int d) {numerator = n;denominator = d;}public Fraction add(Fraction other) {int numeratorNew = numerator*other.denominator + denominator*other.numerator;int denominatorNew = denominator*other.denominator;return new Fraction(numeratorNew, denominatorNew);}public Fraction multiply(int k) {return new Fraction(numerator*k, denominator);}public Fraction multiply(Fraction other) {return new Fraction(numerator*other.numerator, denominator*other.denominator);}public static void main(String[] args) {// Let's test our class out!Fraction half = new Fraction(1, 2);Fraction quarter = new Fraction(1, 4);Fraction result = half.add(quarter);System.out.println("1/2 + 1/4 = "+result.numerator+"/"+result.denominator);}}Run it, and you should see on the console: “1/2 + 1/4 = 6/8”. Now let’s work out what’s going on:int numerator;int denominator;Previously, when we’ve declared new variables, they’ve always been inside the body of a method. These were known as ‘local variables’, because they only existed while running the code inside our method (see the subsection on ‘Scoping’ for a reminder). When the variables are inside the class, but not in any method, they’re known as attributes. This is data associated with a particular fraction, in this case, the numerator and denominator. When we create a new fraction, we expect these attributes to hold these values.Class vs object: Before I go any further, let’s establish the difference between a class and an object. The code you see above is a class. It represents some specification about what a fraction is and how it behaves. But it doesn’t actually represent a specific fraction. When we create a specific ‘Fraction’ using the Fraction class by supplying a numerator and denominator, then we have an object. Our class therefore embodies the concept of a generic ‘fraction’, whereas an object is a specific fraction like ? or ?. We say that ? is an instance of the Fraction class, and you will sometimes see the term instantiation to mean we’ve taken a class a created a concrete object from it.public Fraction(int n, int d) {numerator = n;denominator = d;}Constructors are methods which allow an object to be created. We want to be able to create the fraction ? for example by using:Fraction half = new Fraction(1,2);A constructor is just like any method we’ve seen before, except for the method name is the name of the class (Fraction), and it has no return type. It takes arguments just like a normal method, and this is the data concerning the fraction we need to build it, in this case the numerator and denominator.Good so far, but what’s happening inside this method?Recall from before that parameters of a method only exist while the method is running, before they’re destroyed. So the variables n and d won’t last for very long. We need to be able to preserve this data inside the object. The solution is to set our attributes to these values. That way, we’ve passed on the data we’ve passed into the constructor to the storage location of the object.public Fraction add(Fraction other) {int numeratorNew = numerator*other.denominator + denominator*other.numerator;int denominatorNew = denominator*other.denominator;return new Fraction(numeratorNew, denominatorNew);}We can also define behaviour associated with the fraction. We’ve seen previously that objects can have associated methods. So for example, we could do:String x = “Hello”;char c = x.charAt(1);Similarly, if we have a fraction which we’ve stored in the variable half, and want to add a fraction stored in a variable quarter, we might want to do half.add(quarter), which we might expect to return a new fraction with these fractions added together.Our ‘add’ method in the code presented takes the other fraction passed in as an argument (the variable other), and then combines. When we do numerator*other.denominator for example, we’re using a combination of the state of the current fraction with the state of the ‘other’ fraction. When the method runs, it’s in the context of the object we’re applying the method to. So for half.add(quarter), the attribute numerator (and any other attributes) holds the value associated with the half fraction, because the method is being applied to this object.Similarly, when we run x.charAt(1)in the example above, the charAt method (however it is implemented) has access to the attributes of the String value that the variable x holds, presumably being able to access its individual characters and give back the right one according to the number we passed in as the argument of the method.public Fraction multiply(int k) {return new Fraction(numerator*k, denominator);}Now we’re defining another method, which allows us to take the fraction we’re applying the method to, multiply it by a number, and then return a suitable new fraction.public Fraction multiply(Fraction other) {return new Fraction(numerator*other.numerator, denominator*other.denominator);}Wait, we already have a multiply method don’t we? Java (along with most other Object-Oriented languages) allow us to have multiple different methods with the same name, provided that the argument types are different. This is known as overloading the method. By having two different multiply methods, we allow a fraction to be multiplied by either a constant or another fraction.public static void main(String[] args) {// Let's test our class out!Fraction half = new Fraction(1, 2);Fraction quarter = new Fraction(1, 4);Fraction result = half.add(quarter);System.out.println("1/2 + 1/4 = "+result.numerator+"/"+result.denominator);}Our main method, as ever, allows us to test out our code (and could have been put elsewhere outside of the Fraction class – we’ve just left it in there for convenience). Because we defined a constructor of the Fraction class, we can create concrete instantiations of our class representing actual fractions. We’re creating new fractions here and putting the values in the variables half and quarter. We’re then adding these two fractions to get a new fraction result.We’re then printing out the fraction to the console by accessing its attributes.toString methodsYou might be wondering what would happen if we tried to print out the fraction directly:System.out.println(result);The answer is this:Fraction@119298dWhat on Earth? The problem is, we haven’t told our program how to put our Fraction in a suitable String form. Therefore, its just gone with its default behaviour of printing the class name of the object and a fairly unhelpful number indicating its identity. But we can add a new method to our Fraction class so that our program knows what to do:public String toString() {return numerator+"/"+denominator;}The toString method takes no arguments and needs to return a String. Its role is to take the state of our object, and convert it into a suitable string format so it can say be printed to the console. We usually expect it to use the attributes of the class, because the attributes represent the state of the object, and we want to express the state of the object when we put it in string form. If you replace your main method with this, you’ll then get the same output as in the older version of the program:public static void main(String[] args) {// Let's test our class out!Fraction half = new Fraction(1, 2);Fraction quarter = new Fraction(1, 4);Fraction result = half.add(quarter);System.out.println(half+" + "+quarter+" = "+result);}Run it, and hey presto! Recall that when we use the + operator and one of the arguments to the left or right is a String, then all the arguments get converted to Strings so that + can append them together into one String. When Java does so, it looks at the type of your class (in this case Fraction), and then uses your toString method if you supplied one. ................
................

In order to avoid copyright disputes, this page is only a partial summary.

Google Online Preview   Download