Question: The invoice-printing system program has a flaw - it mixes application logic (the computation of total charges) and presentation (the visual appearance of the invoice)
The invoice-printing system program has a flaw - it mixes "application logic" (the computation of total charges) and presentation (the visual appearance of the invoice) . Reimplement the program, using a separate InvoiceFormatter class to format the invoice. That is, the Invoice and LineItem methods are no longer responsible for formatting. However, they will acquire other responsibilities (Please comment the new responsibilites they got), because the InvoiceFormatter class needs to query them for the values that it requires.
/**
This program demonstrates the invoice classes by printing
a sample invoice.
*/
public class InvoicePrinter
{
public static void main(String[] args)
{
Address samsAddress
= new Address("Sam's Small Appliances",
"100 Main Street", "Anytown", "CA", "98765");
Invoice samsInvoice = new Invoice(samsAddress);
samsInvoice.add(new Product("Toaster", 29.95), 3);
samsInvoice.add(new Product("Hair dryer", 24.95), 1);
samsInvoice.add(new Product("Car vacuum", 19.99), 2);
System.out.println(samsInvoice.format());
}
}
////////////////////////////////////////////////////////////////////////////////////////////
/**
Describes a mailing address.
*/
public class Address
{
private String name;
private String street;
private String city;
private String state;
private String zip;
/**
Constructs a mailing address.
@param aName the recipient name
@param aStreet the street
@param aCity the city
@param aState the two-letter state code
@param aZip the ZIP postal code
*/
public Address(String aName, String aStreet,
String aCity, String aState, String aZip)
{
name = aName;
street = aStreet;
city = aCity;
state = aState;
zip = aZip;
}
/**
Formats the address.
@return the address as a string with three lines
*/
public String format()
{
return name + " " + street + " "
+ city + ", " + state + " " + zip;
}
}
////////////////////////////////////////////////////////////////////////////////////////////
import java.util.ArrayList;
/**
Describes an invoice for a set of purchased products.
*/
public class Invoice
{
private Address billingAddress;
private ArrayList
/**
Constructs an invoice.
@param anAddress the billing address
*/
public Invoice(Address anAddress)
{
items = new ArrayList
billingAddress = anAddress;
}
/**
Adds a charge for a product to this invoice.
@param aProduct the product that the customer ordered
@param quantity the quantity of the product
*/
public void add(Product aProduct, int quantity)
{
LineItem anItem = new LineItem(aProduct, quantity);
items.add(anItem);
}
/**
Formats the invoice.
@return the formatted invoice
*/
public String format()
{
String r = " I N V O I C E "
+ billingAddress.format()
+ String.format(" %-30s%8s%5s%8s ",
"Description", "Price", "Qty", "Total");
for (LineItem item : items)
{
r = r + item.format() + " ";
}
r = r + String.format(" AMOUNT DUE: $%8.2f", getAmountDue());
return r;
}
/**
Computes the total amount due.
@return the amount due
*/
private double getAmountDue()
{
double amountDue = 0;
for (LineItem item : items)
{
amountDue = amountDue + item.getTotalPrice();
}
return amountDue;
}
}
////////////////////////////////////////////////////////////////////////////////////////////
/**
Describes a quantity of an article to purchase.
*/
public class LineItem
{
private int quantity;
private Product theProduct;
/**
Constructs an item from the product and quantity.
@param aProduct the product
@param aQuantity the item quantity
*/
public LineItem(Product aProduct, int aQuantity)
{
theProduct = aProduct;
quantity = aQuantity;
}
/**
Computes the total cost of this line item.
@return the total price
*/
public double getTotalPrice()
{
return theProduct.getPrice() * quantity;
}
/**
Formats this item.
@return a formatted string of this item
*/
public String format()
{
return String.format("%-30s%8.2f%5d%8.2f",
theProduct.getDescription(), theProduct.getPrice(),
quantity, getTotalPrice());
}
}
////////////////////////////////////////////////////////////////////////////////////////////
/**
Describes a product with a description and a price.
*/
public class Product
{
private String description;
private double price;
/**
Constructs a product from a description and a price.
@param aDescription the product description
@param aPrice the product price
*/
public Product(String aDescription, double aPrice)
{
description = aDescription;
price = aPrice;
}
/**
Gets the product description.
@return the description
*/
public String getDescription()
{
return description;
}
/**
Gets the product price.
@return the unit price
*/
public double getPrice()
{
return price;
}
}
Step by Step Solution
There are 3 Steps involved in it
Get step-by-step solutions from verified subject matter experts
