CS 199 EMP

Hosted by Jackie Chan and Akhila Ashokan

Topics: JSON Serialization, Reverse Engineering, Interfaces

Today's Learning Objectives

  • JSON Serialization

  • Reverse Engineering

  • Interfaces

Write code on the homepage or any playground on the site!
https://cs125.cs.illinois.edu/

Slides are on the course site!
https://cs199emp.netlify.app/

Serialization and JSON

Allows us to store an object into our favorite format for reconstruction later. It's useful when we are trying to use the data stored in objects between two different programs.

There are several format options, but the most popular is probably JavaScript Object Notation (or JSON).

{
  "name": "Madame Uppercut",
  "age": 39,
  "secretIdentity": "Jane Wilson",
  "powers": [
    "Million tonne punch",
    "Damage resistance",
    "Superhuman reflexes"
  ]
}

Jackson

JSON serialization should never be something you have to do on your own. Instead, you have access to Jackson, the friendly serialization library for Java. Jackson has alot of uses, but we are mostly just concerned with its ObjectMapper class.

You'll use Jackson in the MP so let's look at how you can use it to serialize and deserialize objects.

Jackson

import com.fasterxml.jackson.databind.ObjectMapper;
public class SuperHero {
  private String name; 
  private String power;
  private int age; 
  
  public SuperHero() { }
  
  public SuperHero(String setName, String setPower, int setAge) {
    name = setName; 
    power = setPower; 
    age = setAge;
  }
  public String getName() {
    return name;
  }
  
  public String getPower() {
    return power;
  }
  
  public String toString() {
    return name + "'s power is " + power;
  }
}

// create an instance of the ObjectMapper class to access its methods
ObjectMapper mapper = new ObjectMapper(); 
SuperHero madameUpperCut = new SuperHero("Madame Uppercut", "Superhuman reflexes", 39);
// serialize the Superhero class into a String 
String json = mapper.writeValueAsString(madameUpperCut); 

Short Answer Questions - Serialization (5 minutes)

  1. What do we need to include in the class for Jackson to properly serialize a class? Why?

  2. What method do we need to use to deserialize the SuperHero object?

  3. What do we need to include in the class for Jackson to properly deserialize the json string back into the class? Why?

  4. Why is Jackson so useful?

Practice - Deserialization (5 minutes)

Deserialize the json String below back into a SuperHero object.

import com.fasterxml.jackson.databind.ObjectMapper;
public class SuperHero {
  private String name; 
  private String power;
  private int age; 
  
  public SuperHero(String setName, String setPower, int setAge) {
    name = setName; 
    power = setPower; 
    age = setAge;
  }
  public String getName() {
    return name;
  }
  
  public String getPower() {
    return power;
  }
  
  public String toString() {
    return name + "'s power is " + power;
  }
}

ObjectMapper mapper = new ObjectMapper(); 
SuperHero madameUpperCut = new SuperHero("Madame Uppercut", "Superhuman reflexes", 39);
String json = mapper.writeValueAsString(madameUpperCut); 

Reverse Engineering

Think taking apart a car to build it back together again. In software engineering, this is the process of analyzing a software to understand the design and implementation. We practiced this during our weekend homework.

Useful in detecting and neutralizing malware and exposing security flaws. Nowadays, there are tools available to "decompile" binary code back into human readable format. There are several legal and ethical disputes around reverse engineering in software engineering.

Reverse Engineering Clubhouse Article

Practice - Reverse Engineering (10 minutes)

Let's do a very easy reverse engineering exercise. Create a method called mystery using the code below. Make sure your method prints out the values correctly as seen in the comments.

public class Pet { }
public class Dog extends Pet { }
public class Cat extends Pet { }
public class Bird extends Pet { }
public class Hamster extends Pet { }

Pet d = new Dog();
mystery(d); // prints Doggie Grooming Session
Pet c = new Cat(); 
mystery(c); // prints Cat Wellness Exam
Pet h = new Hamster(); 
mystery(h); // prints Dental Care Visit
Pet b = new Bird();
mystery(b); // prints Uh oh, looks like we don't have any services for that animal.

abstract keyword

  • abstract class: CANNOT be instantiated but CAN be extended to create child classes
  • abstract method: CANNOT be implemented in the parent class, but requires all child classes to implement it

Why is this useful?
Can I have a abstract method in an non-abstract class? Why or why not?

Interfaces - Points of Connection or Boundaries

Idea is bigger than Java keyword: user interface, hardware interface, software interface.

// What are the interfaces in this class?
public class SuperHero {
  private String name; 
  private String power;
  private int age; 
  
  public SuperHero(String setName, String setPower, int setAge) {
    name = setName; 
    power = setPower; 
    age = setAge;
  }
  public String getName() {
    return name;
  }
  
  private String getPower() {
    return power;
  }
}

Interfaces in Java Programming

Programming structure or format that allows the computer to enforce certain properties on an object. A single class can implement more than one interface. Look at the example below. Will it run? If not, how do we fix it?

public interface Vehicle { 
  //Anything that wants to be a "Vehicle" must, implement this function 
  // startEngine should set the engineStatus to ON 
  void startEngine();
} 

public class Corvette implements Vehicle {
  String engineStatus;
}

Short Answer Questions - Interface (5 minutes)

  1. What is the purpose of the interface keyword in Java?

  2. True/False: A class an implement multiple interfaces.

  3. True/False: A class can extend multiple classes.

  4. Can a class implement a interface and extend a class?

  5. What is an example of an interface outside Java?

Questions continue on the next slide.

Short Answer Questions - Interfaces (cont.)

  1. Look at the code below. Will the compiler throw an error?
public interface Vehicle { 
  // startEngine should set the engineStatus to on 
  void startEngine();
} 

public class Corvette implements Vehicle {
  String engineStatus;
  public void startEngine() {
    engineStatus = "idle";
  }
}

Practice - Interfaces

A local resturant has hired you to be their technical consultant. The resturant's online ordering system currently has a class for Pizza, Burgers, and Salads. They are defined on the next slide. The resturant wants to add a new feature to their site for special items on their menu. In order to properly connect with specials page they are designing, the menu items must implement the following methods:

  1. void setDealPrice() - sets the price of the item to be half the original price

  2. void removeAllToppings() - removes all the toppings on the items (i.e. sets it to null)

  3. void setSpecialName() - sets the name of the special to be special + name (e.g. specialPizza)

Help the resturant design the correct interface and implement it in all their existing menu items.

Interfaces Starter Code

public interface Special {
  // create your interface here 
  // made the modifications to the classes below so that they implement the interface properly
}
public class Pizza {
  String name;
  double price;
  String[] toppings; 
}

public class Burgers {
  String name; 
  double price; 
  String[] toppings;
}

public class Salads {
  String name; 
  double price; 
  String[] toppings; 
}

Have a great week!

We're at a good halfway point in the semester to collect some feedback. As always, let us know how we're doing in the anonymous feedback forms on the course website. Bye, y'all!

Solutions Section

Solution - Serialization Short Answer Questions

  1. You need to include getter methods in the conventional format so Jackson knows what to include in its serialization.

  2. You can use the readValue() method and pass in the json String and the class.

  3. There are many way to do this, but one way is to include an empty constructor because Jackson is not smart enough to find and use any other constructors.

  4. It's easy to use and faster than manually serializing something. Jackson allows us to serialize and deserialize quickly (3 additional lines of code).

Solution - Deserialization Practice

import com.fasterxml.jackson.databind.ObjectMapper;
public class SuperHero {
  private String name; 
  private String power;
  private int age; 
  
  public SuperHero() { }
  
  public SuperHero(String setName, String setPower, int setAge) {
    name = setName; 
    power = setPower; 
    age = setAge;
  }
  public String getName() {
    return name;
  }
  
  public String getPower() {
    return power;
  }
  
  public String toString() {
    return name + "'s power is " + power;
  }
}

// create an instance of the ObjectMapper class to access its methods
ObjectMapper mapper = new ObjectMapper(); 
SuperHero madameUpperCut = new SuperHero("Madame Uppercut", "Superhuman reflexes", 39);
// serialize the Superhero class into a String 
String json = mapper.writeValueAsString(madameUpperCut); 
SuperHero anotherUpperCut = mapper.readValue(json, SuperHero.class);
System.out.println(anotherUpperCut.toString());

Solution - Reverse Engineering Practice

public class Pet { }
public class Dog extends Pet { }
public class Cat extends Pet { }
public class Bird extends Pet { }
public class Hamster extends Pet { }

public void mystery(Pet p) {
  if (p instanceof Dog) {
    System.out.println("Doggie Grooming Session");
  } else if (p instanceof Cat) {
    System.out.println("Cat Wellness Exam");
  } else if (p instanceof Hamster) {
    System.out.println("Dental Care Visit");
  } else {
    System.out.println("Uh oh, looks like we don't have any services for that animal.");
  }
}

Pet d = new Dog();
mystery(d); 
Pet c = new Cat(); 
mystery(c);
Pet h = new Hamster(); 
mystery(h);
Pet b = new Bird();
mystery(b);

Solution - Interfaces Short Answer Questions

  1. The use of the interface keyword in Java allows the compiler to enforce what constitutes the proper implementation of an interface. The compiler will throw an error if the class does not define all the methods required by the interface.

  2. True

  3. False

  4. Yes

  5. Several answers. User interface is a good example.

  6. No the compiler will not throw an error. The compiler does not know if the class correctly implemented the interface. It only checks to see whether or not the required methods are implemented.

Solution - Interfaces Practice

public interface Special {
  // create your interface here 
  // made the modifications to the classes below so that they implement the interface properly

  void setDealPrice();
  void removeAllToppings();
  void setSpecialName(); 
}
public class Pizza implements Special {
  String name;
  double price;
  String[] toppings; 
  //duplicate in Burgers and Salads
  public void setDealPrice() {
    price = price * .5;
  }
  //duplicate in Burgers and Salads
  public void removeAllToppings() {
    for (int i = 0; i < toppings.length; i++) {
      toppings[i] = null;
    }
  }
  //duplicate in Burgers and Salads
  public void setSpecialName() { 
    name = "special" + name;
  }
}

public class Burgers {
  String name; 
  double price; 
  String[] toppings;
}

public class Salads {
  String name; 
  double price; 
  String[] toppings; 
}