Created
May 15, 2019 02:41
-
-
Save jaohaohsuan/2e80baaf0311b143f2a1bb24d1af5fee to your computer and use it in GitHub Desktop.
week11 files I/O
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package comp601.week11; | |
import java.util.*; | |
import static java.lang.System.out; | |
import java.io.*; | |
import java.nio.file.*; | |
public class Main { | |
/* | |
* Create a folder at the top level of your Eclipse project named "data". In the | |
* folder create a text file named "boat_data.txt", with the following suggested | |
* content: | |
* | |
* | |
* AA11,2005,130.5 BB22,2010,40.34 CC33,1998,50.2 DD44,1978,54.5 EE55,1962,64.3 | |
* | |
*/ | |
public static void main(String[] args) { | |
try { | |
App app = new App("data/boat_data.txt"); | |
} catch (IOException ioe) { | |
ioe.printStackTrace(); | |
} | |
} | |
} | |
class App { | |
List<Boat> boats; | |
Scanner input = new Scanner(System.in); | |
public App(String filename) throws IOException { | |
run(filename); | |
} | |
public void run(String filename) throws IOException { | |
readData(filename); | |
displayMenu(); | |
int opt = 0; | |
String str = null; | |
while (true) { | |
out.print("\nSelect an option: "); | |
str = input.nextLine().trim(); | |
if (str.isEmpty() || str.chars().allMatch(Character::isDigit) == false) { | |
out.println("A number of 1-5 is expected."); | |
continue; | |
} | |
opt = Integer.parseInt(str); | |
if (opt < 0 || opt > 5) { | |
out.println("Invalid option. Must be 1 - 5 (or 0 for menu)."); | |
continue; | |
} | |
switch (opt) { | |
case 0: | |
displayMenu(); | |
break; | |
case 1: | |
handletravelOption(); | |
break; | |
case 2: | |
displayBoatWithMostFuel(); | |
break; | |
case 3: | |
out.println("Todo ..."); | |
break; | |
case 4: { | |
double total = getTotalFuelLeft(boats, 0); | |
out.printf("Total fuel: %.2f", total); | |
break; | |
} | |
case 5: | |
farewell(); | |
return; | |
} | |
} // end of while | |
} | |
public void farewell() { | |
out.println("\t Thanks for using the service. Bye!"); | |
} | |
public void displayMenu() { | |
out.println("\n\n*************************************"); | |
out.println("* Menu *"); | |
out.println("*************************************\n"); | |
out.println("1. Take a trip"); | |
out.println("2. Display boat with most fuel in tank"); | |
out.println("3. Display the boat that's travelled most"); | |
out.println("4. Display total fuel left in all boats"); | |
out.println("5. Exit"); | |
} | |
// step 8: find out which object has the most fuel in tank | |
public void displayBoatWithMostFuel() { | |
if(boats == null || boats.size() == 0) { | |
out.println("No boat left."); | |
} | |
Boat maxBoat = boats.get(0); | |
for(Boat b : boats) { | |
if(b.getFuelInTank() > maxBoat.getFuelInTank()) { | |
maxBoat = b; | |
} | |
} | |
out.printf("Max fuel boat rego: %s", maxBoat.getRegistration()); | |
} | |
// step 7: method getTotalFuelLeft (note, this is a recursive method) | |
public double getTotalFuelLeft(List<Boat> list, double accum) { | |
// Recursively calculate total fuel left in all boats. | |
if(list == null || list.size() == 0) { | |
return accum; | |
} else { | |
List<Boat> sublist = list.subList(1, list.size()); | |
accum += list.get(0).getFuelInTank(); | |
return getTotalFuelLeft(sublist, accum); | |
} | |
} | |
// step 6: method HandletravelOption | |
public void handletravelOption() { | |
// Read a registration from user to search for an existing boat | |
out.println("\t Take a trip ..."); | |
out.print("Enter a rego: "); | |
// Read a travel distance from user | |
String rego = input.nextLine(); | |
Boat boat = null; | |
for (Boat b : boats) { | |
if(b.getRegistration().equalsIgnoreCase(rego)) { | |
boat = b; | |
break; | |
} | |
} | |
if(boat == null) { | |
out.printf("Rego %s doesn't exist\n", rego); | |
return; // back to the menu | |
} | |
out.print("Enter a distance: "); | |
double dist = input.nextDouble(); | |
boolean result = boat.travel(dist); | |
if(result) { | |
out.println("Have a wonderful trip."); | |
} else { | |
out.println("Perhaps try another boat."); | |
} | |
// Pass the travel distance to travel() method of the existing boat object | |
// The returned value of travel() (boolean) determines whether there is enough | |
// fuel for the trip | |
} | |
// step 5: method readData | |
public void readData(String filename) throws IOException { | |
// Initialise the list "boats" | |
boats = new LinkedList<>(); | |
Path path = new File(filename).toPath(); | |
List<String> content = Files.readAllLines(path); | |
// Read from the file ("filename") and create objects in the list ("boats"). | |
for(String line: content) { | |
line = line.trim(); | |
if(line.isEmpty()) | |
continue; | |
String[] items = line.split(","); | |
String rego = items[0].trim(); | |
int yr = Integer.parseInt(items[1].trim()); | |
double fuel = Double.parseDouble(items[2].trim()); | |
Boat b = new Boat(rego, yr, fuel); | |
boats.add(b); | |
} | |
} | |
} | |
class Boat extends Watercraft { | |
// step 2: private fields with getter/setter: year (int), fuelInTank(double), | |
// fuelEco(double) | |
private int year; | |
private double fuelInTank; | |
private double fueEco; | |
// step 3 | |
// Constructor, with 3 parameters for assigning year, fuelInTank, | |
// and registration (rego is for the base class) | |
public Boat(String registration, int year, double fuelInTank) { | |
super(registration); | |
this.setYear(year); | |
this.setFuelInTank(fuelInTank); | |
this.fueEco = (this.year < 2000) ? 5 : 12; | |
} | |
// Hint: fuelEco property is not part of the parameters, rather, | |
// it is initialised inside the constructor body. | |
// fuelEco is the number of kilometers a boat can travel per litre fuel | |
// comsuption. | |
// It is determined based the year property: if the boat year is before 2000, | |
// fuelEco is 5; otherwise it's 12. | |
public int getYear() { | |
return year; | |
} | |
public void setYear(int year) { | |
this.year = year; | |
} | |
public double getFuelInTank() { | |
return fuelInTank; | |
} | |
public void setFuelInTank(double fuelInTank) { | |
this.fuelInTank = fuelInTank; | |
} | |
public double getFueEco() { | |
return fueEco; | |
} | |
public void setFueEco(double fueEco) { | |
this.fueEco = fueEco; | |
} | |
// step 4: Method travel | |
public boolean travel(double distance) { | |
// Calculate the fuel required to travel the "distance", | |
// which is calculated as: distance / fuelEco | |
double needOfFuel = distance / this.fueEco; | |
// Determine the feasibility of traveling the "distance" | |
// If fuel left in tank is not enough for the "distance", | |
// return false; otherwise, deduct consumed fuel, return true. | |
if(this.fuelInTank >= needOfFuel) { | |
this.fuelInTank = this.fuelInTank - needOfFuel; | |
return true; | |
} | |
return false; | |
} | |
} | |
class Watercraft { // step 1 | |
// private field with getter/setter: registration (String) | |
private String registration; | |
public String getRegistration() { | |
return registration; | |
} | |
public void setRegistration(String registration) { | |
this.registration = registration; | |
} | |
// A parameterised constructor | |
public Watercraft(String registration) { | |
this.setRegistration(registration); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment