Java Programming Handbook
Tags: beginners, java, learn, handbook
Published: 2021-03-14 17:26:03

This post is part of the Object Oriented Programming Notes series I'm still writing. It's intended to be a quick handbook for people who need or want a language overview and see how to write some code.

There is a running example at the end of the post.

If you need a full amazing Java tutorial/course/guide, please visit this page I found while I was studying about access modifiers:


[http://tutorials.jenkov.com/java/index.html](http://tutorials.jenkov.com/java/index.html) 🚀


You won't find how to install anything or how to setup you development environment here by the moment,  but you can test code using [replit.com](replit.com) to start coding Java online ;)


## ☕ Java Overview

In this section you will find some information about the Java language. But if you want a deeper understanding, please read the **_Thinking in Java_** book by **Bruce Eckel** if you already know some programming basics.

### 📓 What is Java?

Java is a **_Programming Language_** designed to allow programming under the **_Object Orientation Paradigm_**. 

Like any other language, it **offers a set of special words and some rules** to form logic sentences that others can understand. The main goal of the _Programming Language_ is **to allow you to write sentences the  computer can understand in order to perform actions**.


You can write a group of instructions to create processes, then create a group of processes to create programs, and then create a group of programs to create a system.

There are some words for a specific usage. These words are known as **_reserved words_**. Also, there are two main set of rules: the **_syntax_** and the **_semantics_**. The syntax defines how to write sentences in the right way, and the semantics defines the structure of the code in the right way so the computer can understand your instructions.

### 🤖 Strongly typed language

Java is a strongly typed language. This means that Java needs you to define the type of every data you declare.

Because the way a computer works is by **reading data from memory** (from Hard Disk or RAM) to use it in processes running in the **CPU**, we need to separate a place in the memory for every variable and temporary data to ensure our program works fine.

**Every data type has a size** in bits (physical slots in memory).  So, when we declare the data type of a variable, for example, we are telling the computer to **ensure the right space** to store our data in memory to avoid errors like insufficient memory space.

There is a set of **data types**: numbers, strings of characters (text), single characters, booleans (true or false), objects (data structures), etc.

You can read more about strong and weak typed languages [here](https://medium.com/android-news/magic-lies-here-statically-typed-vs-dynamically-typed-languages-d151c7f95e2b#:~:text=Strongly%20typed%20languages,typed%2C%20and%20so%20is%20Java.).

### 🔮 The magic

One more thing. The computer just understands binary instructions (0 and 1, the **_machine language_**). This is called **_low level_** language. Low is near to the machine language, and hight is near to human language.

**Java is a _hight level_ language**, so we need to translate our hight level instructions to low level instructions. Fortunately, there's a program that do the dirty job. 

This program is called **_"compiler"_**. It **translates a hight level language to  low level language**. 

There exists another programs called  **_"transpilers"_** which translates a language to other language in the same level.

However, in this case **we need a "compiler"** to **compile** (translate to low level) our **Java code** to machine language.

The compilers and the transpilers have internal mechanisms which allows to **check** if the code **syntax** is ok and it respects the **semantic rules**. So, the compiler won't leave to compile or run code with syntax and semantic errors. But remember, you can write code with logic errors with well written instructions.


# 👩‍💻 Writing Code

In this section you will find a reference about the basics to write Java code. Feel free to re-visit it when you need to.

### Comments

Comments are a way to **write things in the code that will be ignored** by the computer. Comments don't have any functionality.

It's recommended to **write comments** to explain something about the code **if necessary**. Usually, we use comments to _"document"_ the code, to help other programmers to quickly understand a process, or to explain certain specific concepts that are not common.

When you are learning is ok to write many comments to add notes, but when you are working on a more serious project you should **avoid to abuse of this resource**. To avoid unnecessary comments try to write the code as simple and understandable as possible. If you want to know more, google about clean code and good practices.

```java
/**
 * ✅ This is a multiline comment
 * so you can write a very long comment.
 * This format is used to document your code.
 */

/* ✅
This is a valid  multiline
comment
*/

/* ✅ as well as this one*/

// ✅ This is an inline comment. You can't use multiline
because this line won't be interpreted as a comment ❌
```

### Semi-colon and Curly braces
This is the semicolon symbol `;`, and these are the curly braces `{}`.

**Semicolons** are used to **specify the end of an instruction**,  and **curly braces** are used to **specify an scope**.

#### Semicolon usage examples: 
```java
// ✅ method execution ends until the semi-colon appears
sendAnEmail("hey@well.com");

// ✅ declaration ends until the semi-colon appears
String thisWillStoreMyDogName = "Pulgas";

/**
 * ❌ In this line I forget to write a semicolon after "Florencio"
 * so the Java compiler will understand that these two lines are the same
 * instruction, so the instruction:
 *  
 * String myFishName = "Florencio"String myDogAge = 4;
 *
 * doesn't make sense to the compiler and will be marked
 * as an error
 */
String myFishName = "Florencio"
String myDogAge = 4;

public String sendAnEmail(String email) {
  // ✅ return statement ends until semi-colon appears
  return "Message sent to: " + email;
}

public String sendAnSMS(String phone) {
  // ❌ Java will read the sentence as:
  // return "Message sent to: " + phone }
  // so it doesn't make sense to the compiler
  // if a curly brace } appears at the end of a return
  // statement. So don't forget the semicolons never!
  return "Message sent to: " + phone
}

```

**Curly-braces** also wrap your pieces of code to allow to reuse your logic and to create named processes called **methods**. You will use `{}` to write the definition of your classes and methods inside, and for some statements like loops and comparisons.

**The `{}` defines a scope**, so you can access to anything that is **inside** the `{}`, but if there is something out, you won't be able to access to it.

#### Curly braces usage examples:
```java
public class Cellphone { // your class scope starts here

  // ✅ These variable will be available for all the methods 
  // inside the class curly braces {}
  public String myCatName = "Bigotes";


  public String getCatName() { // method scope starts here
    // ✅ You can access to the variable at class level from the 
    // method using the special word `this` only if the
    // method is under the class scope defined by the class 
    // curly braces
    return this.myCatName;
  } //  method scope ends here


  public String getDogName() { // method scope starts here
    // ✅ You can access to the variables inside the {} of the method
    String myDogName = "Pulgas";
    return myDogName;
  } // method scope ends here


  public String getMyDogName() { // method scope starts here
    // ❌ This method will cause an error because it doesn't know 
    // about the variables of other methods that are out of
    // its scope
    return myDocName;
  } // method scope ends here


} // class scope ends here
``` 


### Types

Java is a **strongly typed language**. We need to specify data types to tell Java what kind of values we are working with. Thanks to this, the values are more predictable and it's possible to ensure the memory space to store our data.

**Analogy**: If I tell you that the variable `x` stores a number, and the variable `y` stores another number, when we sum `x + y` we  can infer that the result will be a number. But if you don't know what kind of data the variable `y` stores, you won't be able to know if it's even possible to sum it with `x`. The Java compiler has the same problem, so it needs our help to specify the data type of the variables.

I'll copy and paste some examples from `w3schools.com`, but you should read more about [here](https://www.w3schools.com/java/java_data_types.asp).

```java
int myNum = 5;             // Integer (whole number)
float myFloatNum = 5.99f;  // Floating point number
char myLetter = 'A';       // Character
boolean myBool = true;     // Boolean
String myText = "A text";  // String
```

### Access modifiers

Remember that Java is an **Object Oriented Programming Language**. One of the main concepts of the OOP is **encapsulation**. The access modifiers are a Java feature that allows us to encapsulate objects  behaviors (methods) and data (variables).

Very basically, the **access modifiers are key words that specify the visibility** (exposition or availability are good terms too) of variables and methods.

**Note**: the variables and methods of a class are know as members of a class.

- `public`: Makes members available outside the class. Can be inherited to  the sub-classes  (inheritance is another key concept of OOP) and outside the package.
- `private`: Makes members available only inside the class. The members cannot be inherited to the "subclasses", and are not available from outside the package.
- `protected`: Makes members available only inside the package of the class, and for subclasses even if the subclass is outside the package.
- `default`: Makes the class members accessible at package level only. Subclasses can inherit protected members only if it's inside the package. 

```java
public class MyPublicClass {
  // This variable is accesible inside the class  only.
  private myDogName = "Pulgas";

  // This method is accesible from the outside of the class and package
  public void getFirstLetterOfMyDogName() {
    String letter = this.myDogName.substring(string.length() - 1);
    return formatText(letter);
  }

  /**
   * This method is for internal usage in the class only.
   * We don't want others to know what we are doing here.
   */
  private String formatText(String text) {
    return "Your dog's name first letter is: " + text.toUpperCase();
  }

  /**
   * This method is accessible at package level
   * or available to sub-classes
   */
  protected void sayHello() {
    System.out.println("No, I will say goodbye!");
  }

  /**
   * This method has a default access modifier, so
   * it will be available at package level only,
   * and for subclasses inside the package.
   */
  void sayHello() {
    System.out.println("Goodbye!");
  }
}
```
Let's see what happens when we try to access to the class variables and methods:
```java
// First of all, lets create an object based on the MyPublicClass
MyPublicClass objectInstance = new MyPublicClass();

// ✅ Now that the object exists, lets execute this public method
objectInstance.getFirstLetterOfMyDogName();
// It works fine because the method is public, so we can access from the outside

// ❌ But this method execution is not possible because the method
// is privated and it's not available for external usage
objectInstance.formatText();

// ❌ Trying to access to a private class variable isn't possible either
objectInstance.myDogName;
```

I found [this great page](http://tutorials.jenkov.com/java/access-modifiers.html). You can check it out for a deeper explanation.

### Variables

Variables allow you to store data temporary in the computer memory. They are very useful to make operations. You can set them values over and over again.

Creating a variable is known as **variable declaration**.

You can declare variables inside a **_"class"_** or inside a **_"method"_**. When the method is finished or the class instance is collected by the **_Java Garbage Collector_** (a Java mechanism to remove useless stuff from the memory) the variable will be removed from memory and you won't be able to use it anymore. 

This is **the way to declare a variable**:
`[type] [variableName] = [value];`

Variables declared at **Class level** must have an access modifie):
`[visibility] [type] [variableName] = [value];`

The variable names must be in *camelCase* which is a style by **_convention_** (a convention is a style everybody follow).

```java
// ✅ Declare a variable without an initial value.
// You can't use it until you set it a value
int age;

// ✅ You can declare many variables in a single line
// if all them are of the same type
String address, email, website;

// ✅ You can set a value to the variable in this way
age = 25; // the "=" is called assignation operator

// ✅ Declare a variable with an initial value
String name = "unknown user";

// ✅ You can set a new value later
name = "Sara";

// You must set compatible types
// ✅ This is valid
boolean isAnAdult = true;

// ❌ But this is not valid because "nop" is a String
// and isAnAdult was declared as a boolean type variable
isAnAdult = "nop";

// ✅ Class level variables are declared in this way
public String myName = "Unknown";
private String myDog = "Pulgas";
protected String myCat = "Bigotes";
```

### Methods

A method is a **code structure that allows you to wrap some instructions as a single process** you can execute whenever
you want and all the times you want. Methods will perform your awesome instructions when you execute them. Until that, they will be sleeping (inactive).

**This is the way to execute a method:**  `doSomething();` . As you can see, you only have to write the method name followed by two parenthesis `()`.

A method is a bit more complex than a variable because it can do more: **it performs the instructions you write inside it**.

A method **can receive** many **values** (or no one), **and return values** (or nothing).

This is the way to **send values** to the method: 
`doSomething("with this text");`

This is the way to **receive values** from a method:
`String receivedValue = giveMeAValue();`

The values that the method can receive are called **"parameters"**   or **"arguments"** (params and args in short). You **must specify the type of each arg**. Also, you **must specify the type of the value you will return** (use void if you won't return anything).

You can execute a method from inside another method, so you are able to have multiple simple methods to do an specific task and combine them to create a more complex process.

This is the structure to declare a method:
```
[access modifier] [return value type] [methodName]([args]) {
  ...method definition
}
```

Let's see some examples:

```java
public void doNothing() {
 // ✅ nothing will happens when you execute this method
}

// ✅ This method don't return anything so we declare it as void
// Also, this method doesn't receive any arg, so we keep the () empty
public void saySomethingNice() {
 // your instructions go here..
 System.out.println("Hi there! You are a nice person!");
}

/**
 * ✅ This method will return a text with the planet name
 * so we specify String as the return type.
 * Also, this method doesn't receive any arg, so we keep the () empty
 */
public String giveMeThePlanetName() {
  return "Earth";
}

/**
 * ❌ This method will throw an error because the method
 * return type is specified as void, so the Java compiler
 * won't allow to return anything, but you are trying to
 * return something
 */
public void giveMeTheCountryName() {
  return "I don't know";
}

/**
 * ✅ This method will return a number with the result of a sum
 * so we specify int as the return type.
 * Also, this method receives two args, both int numbers
 */
public int sumTwoNumbers(int numberA, int numberB) {
  int result = numberA + numberB;
  return result;
}

/**
 * ❌ This method will throw an error because the method
 * return type is specified as int, so the Java compiler
 * expects a compatible return value, but you are not returning anything
 */
public int giveMeThisPostYear() {

}

/**
 * ✅ You can combine methods
 */
public void sum1and3() {
  const myResult = sumTwoNumbers(1, 2);
   // System.out.println method writes a text in the console
   // you can see a running example in the Classes section
   System.out.println("This is the result: " + myResult);
}

```

### The if - else Conditional Statements

These **utilities** are very useful to validate data and to define processes that have different behavior depending on a condition. E. g. if you are building a login to allow and block access to the platform, you will need to validate if the user and password are correct. If yes, allow to access. If not, deny the access.

```java
// ✅ This is the common way to use the if-else statements
if (true) {
  // the condition was fullfilled
} else {
  // the condition specified in the if was not fullfilled
}

// ❌ You can't use only the else statement alone because it depends on the if statement defined rules
else {
  
}

// ✅ But you can use only the if
if ((2 + 2) == 4) {
  System.out.println("Mathematics are right");
}

// ✅ You can omit the curly braces {} if you only have one line per statement
if (1 < 8)
  System.out.println("1 is less than 8");
else
  System.out.println("1 is not less than 8, it could be equals or bigger");


/**
 * ❌ Java compiler will detect an error here because se second System.out,println
 * is not part of the if statement and then it finds the else statement after something that is not
 * an if statement
 */
if (1 < 8)
  System.out.println("1 is less than 8");
  System.out.println("isn't ok?");
else
  System.out.println("1 is not less than 8, it could be equals or bigger");

// ✅ You can fix it in this way
if (1 < 8) {
  System.out.println("1 is less than 8");
  System.out.println("isn't ok?");
}
else
  System.out.println("1 is not less than 8, it could be equals or bigger");
```

### Classes
This is the more complex part. This is a **key feature of the Java Object Orientation implementation**. 

**A class is a data structure that wraps a set of functionalities as methods (behavior) and data as variables (state).** 

You can think about classes as a **blueprint** that allows you to define an object.

Supose we are creating a bot for telegram or facebook messenger to allow some users in a group to randomly choose a place to get a good time after work. How to program it? Where to start?

Well, first of all we have to **think what entities are really important**. In this case, the two main entities are the User and the Bot.

Nice, looks not very complicated. Let's **model** the Bot, let's make the **Bot blueprint** (Bot class).

```java
// The first step is to declare our blueprint (our class).
// In Java, all the classes name must be in PascalCase, the first letter must be capital
public class Bot {

}
```


Ok, now, our Bot needs some data to do some actions. Let's add some configuration data:

We want to allow to the group admin user to configure the day of the week and the hour, and allow to the rest of the users to propose a place the bot will choose from.

So, we have to declare the variables to store the **object data**, which **is know as object state**:

```java
public class Bot {
  /**
   * These variables are private because are for internal usage
   * we don't want and don't need to make them accesible.
   * Remember to expose just the very needed and useful data
   * and functionalities.
   */
  private String botName; // can store a single string: "Mr Bot"
  private ArrayList<String> proposedPlaces = new ArrayList<String>(); // can store a group of texts: ["Beerhole", "Sam's Bar and Wine", "Super Taco"]
  private String dayOfWeek; // can store a single string: "Friday"
  private String hour; // can store a single string: "5:00pm"

}
```

Nice! Now we have variables to store our data when the Bot is created.

Next step is to **define the behavior**. So, what do we need? I think we need to create a functionality to configure the Bot name, set the day and hour, save the proposed places, and randomly choose a place.

**There is a special method which allows us to do something when the object is created**. This method **is called constructor** because it's executed while the object construction process.

**How an object looks like?**  How do we create it? you might ask. Well, we create an object based on the class that defines it. To do so, we will write **something like this**:

`Bot ourSuperBot = new Bot();`

The above line is declaring a **variable of type Bot** that **will contain a new object  instance** of the Bot class (Bot type), which means that it's an object created and loaded in the memory of your computer based on the Bot class.

In other  words, the Bot **it's alive now!**  and we refer to it as `ourSuperBot`

You can create many objects based in the same class, and everyone will have different data. For example, you can create a bunch of bots of type Bot:
```java
Bot ourSuperBot = new Bot();
Bot superBotBrother = new Bot();
Bot kevinBot = new Bot();
```

I wanted to show you that in advance because I want you to understand how the constructor method works.

Check out this part with attention: `Bot();`. It looks like a **method**, right? Well, in fact, it is. When we create a new object instance of a given class we can pass data through the parenthesis `()`, and this data will be received and handled by the **constructor**.

Ok, let's go back to our Bot project to see the constructor in action. 

We want to configure our Bot **approaching the constructor**. The only configuration will be the Bot name, the day, and the time.


```java
public class Bot {
  private String botName;
  private ArrayList<String> proposedPlaces = new ArrayList<String>();
  private String dayOfWeek;
  private String hour;

  // This is the constructor. The constructor must have the
  // class name and must be public. Also, it has not a return type 
  public Bot(String botName, String dayOfWeek, String hour) {
    // the word "this" allows you to access to variables at class level
    this.botName = botName;
    this.dayOfWeek = dayOfWeek;
    this.hour = hour;
  }

}

```

Great! Now we can configure the Bot when we create the new object instance in this way:
`Bot ourSuperBot = new Bot("Mr Bot", "friday", "5:20pm");`

Now we need to create a method to save the proposed places:

```java
public class Bot {
  private String botName;
  private ArrayList<String> proposedPlaces = new ArrayList<String>();
  private String dayOfWeek;
  private String hour;
}

 public Bot(String botName, String dayOfWeek, String hour) {
    this.botName = botName;
    this.dayOfWeek = dayOfWeek;
    this.hour = hour;
  }

  // Must be public to allow to use it when the object 
  // instance is created. We don't need to return any value
  // so we declare it as void. We need to receive the place
  // as an string, and save it in the global variable
  public void proposeAPlace(String place) {
    // the add() method allows to add an item at the end of the list
    this.proposedPlaces.add(place);
  }
```

Lets add a method to get the randomly choosed place by the Bot:

```java
public class Bot {
  private String botName;
  private ArrayList<String> proposedPlaces = new ArrayList<String>();
  private String dayOfWeek;
  private String hour;

 public Bot(String botName, String dayOfWeek, String hour) {
    this.botName = botName;
    this.dayOfWeek = dayOfWeek;
    this.hour = hour;
  }

  public void proposeAPlace(String place) {
    this.proposedPlaces.add(place);
  }

  /**
   * We need to return a string (the randomly choosed place)
   * so we declare the method return type as String.
   * We don't need to receive anything so we don't specify 
   * anything in the params. And that's all.
   */
  public String chooseAPlace() {
    Random rand = new Random(); // this is an special object of Java to make random things
    return this.proposedPlaces.get(rand.nextInt(proposedPlaces.size()));
  }
```

The method `chooseAPlace()`will return just the name of a random place, but we want to decorate it with a nice message like `"Hi! This is Mr Bot. The winner this week is: Sam's Bar and Wine. Schedule this date to meet your friends: friday 5:20pm"`.

To do so, we need to add a new method to decorate the text before returning it, but this method will be for internal usage only, so should be private to avoid the users from using it.

It will receive a String (the place) via args, decorate the received String, and return it decorated.

#### Step 1: Declare the `private` method
```java
public class Bot {

  ... // this means that there are more code above but we don't want to write it again in this piece of example code

  private String decorateText(String textToDecorate){
    String decoratedText = "The winner this week is: " + textToDecorate;
    return decoratedText;
  }
```

#### Step 2: Use our new `private`  method
```java
public class Bot {
  private String botName;
  private ArrayList<String> proposedPlaces = new ArrayList<String>();
  private String dayOfWeek;
  private String hour;

  public Bot(String botName, String dayOfWeek, String hour) {
    this.botName = botName;
    this.dayOfWeek = dayOfWeek;
    this.hour = hour;
  }

  public void proposeAPlace(String place) {
    this.proposedPlaces.add(place);
  }

  /**
   * We need to update our method to implement the new
   * decorateText method in order to decorate the text before 
   * returning the choosed place;
   */
  public String chooseAPlace() {
    Random rand = new Random();

    /**
     * All the proposed places are stored in proposedPlaces
     * global variable.
     * proposedPlaces is a list of elements, each element has 
     * a number that defines its position (0, 1, 2, 3) 
     * starting from 0.
     * To select a place from the list, we need to specify 
     * its position number.
     * To randomly select a number, we will use the "rand" 
     * object instance to access to a method called 
     * "nextInt()".
     * We need to tell the "nextInt()" what is the maximum 
     * number of options (if you set 4, the method will 
     * choose a number between 0 and 4).
     * The maximum number of options is the number of items
     * in our proposedPlaces list.
     * To get the number of items in proposedPlaces, we use
     * the size() method which returns an Integer number with
     * the count of items in the list.
     */
    int countOfPlaces = proposedPlaces.size();
    int randomPlacePosition = rand.nextInt(countOfPlaces);

  
    String choosedPlace = this
                          .proposedPlaces
                          .get(randomPlacePosition);

    String decoratedText = decoratedText(choosedPlace);

    return decoratedText;
  }

  private String decorateText(String textToDecorate){
    String decoratedText = "Hi! This is " + this.botName + ". The winner this week is: " + textToDecorate + ". Schedule this date to meet your friends: " + this.dayOfWeek + " " + this.hour;

    return decoratedText;
  }
}
```


We are done! Now, we can use our bot in this way:

```java
// ✅ Create a bot instance and configure it
// Remember that the args we are passing through will be received by the constructor method
Bot ourSuperBot = new Bot("Mr Bot", "friday", "5:20pm");

// ✅ Execute the proposeAPlace method as many times you need
ourSuperBot.proposeAPlace("Beerhole"); // Peter propose "Beerhole"
ourSuperBot.proposeAPlace("Sam's Bar and Wine"); // Sara propose "Sam's Bar and Wine"
ourSuperBot.proposeAPlace("Super Taco"); // and you propose "Super Taco"

// ✅ Finally, we ask the ourSuperBot object to randomly choose 
// a place and store it in a new String type variable.
String choosedPlace = ourSuperBot.chooseAPlace();
```

If you try yo access to private members the Java will compiler stop you and throw an error:

```java
// ❌ Will throw an error because decorateText is for internal class usage only (private)
ourSuperBot.decorateText("Empanadas Juanita");

// ❌ Will throw an error because proposedPlaces is for internal class usage only (private)
ourSuperBot.proposedPlaces;
```

Great! You can see this code in action thanks to replit.com which allows us to edit and run Java online. Click on the Green Button to re-run the code and see how the place changes randomly.

{% replit @chemah/JavaExample %}

I hope this post was helpful for you. I know there are some redundant parts. I did so because repetition while learning helps me to remember. Sorry for that. If you have any question or feedback, feel free to leave a comment. I will read you as soon as possible to improve the post.

I'm writing it in Spanish too para la banda que habla español so when I finish I will update this post to add some illustrations. **_Thanks for reading!_**