I have a project for my java programming course.
The instructions are that we have to create a simple class and a tester class, and the class must include a Default constructor; Parameterized constructor with three parameters (make, model and price); Accessor method called getMake( ) to return the make; Accessor method called getModel( ) to return the model; Accessor method called getPrice( ) to return the price; Mutator method setMake( String newMake) to set the make; Mutator method setModel( String newModel) to set the model; and a Mutator method setPrice( double newPrice ) to set the price..
I have created my class and tester program, and my class compiles perfectly. When I try to run it, though get the error that there is no main method. Now, I followed my professor's example for the tester program and I get several errors on that. If anyone could give me the a pointer in the right direction, I would appreciate it.
My question is this: How do I implement my tester program? Do I need to create a zip file? I've tried doing so and didn't seem to help much...
The following is my code for the class:
public class Automobile
{
private String make;
private String model;
private double price;
public Automobile()
{
make = "Lexus2017";
model = "RX";
}
public Automobile(String initMake, String initModel, double initPrice)
{
make = initMake;
model = initModel;
price = initPrice;
}
public String getMake()
{
return make;
}
public String getModel()
{
return model;
}
public double getPrice()
{
return price;
}
public void setMake(String newMake)
{
make = newMake;
}
public void setModel(String newModel)
{
model = newModel;
}
Also, the following is my tester class(the one that has a lot of errors):
public class AutomobileTester
{
public static void main(String[] args)
{
Automobile make = new Automobile("Lexus 2017");
System.out.println("The car is " + make.getMake());
Automobile model = new Automobile("RX");
System.out.println("The car is " + Automobile.getModel());
Automobile price = new Automobile("43020");
System.out.println("The car is " + Automobile.getPrice());
// Use the mutator to change the make variable
Automobile.setMake("Lexus 2017");
System.out.println("The car is " + backDoor.getState());
// Use the mutator to change the model variable
Automobile.setModel("RX");
System.out.println("The car is called " + backDoor.getName());
Automobile.setPrice("43020");
System.out.println("The car is " + price.getPrice());
}
}
This is my first time working with constructors, and I'm very new to Java, so I'm sorry for any obvious errors. Thank you ahead of time for your time and help.
One of the first problems is that you do not use the proper number of parameters for your calls to the constructor, in Java (and most programming languages) you have to supply all of the required parameters to a method/function/constructor in one call. The fix for your code would be to use:
Automobile car = new Automobile("Lexus 2017", "RX", 43020.0D);
Also when you print out the cars information you first use an instance call then you use a static call, I won't go to much into the difference between the two but basically an instance call requires you to instantiate an object while a static does not. The fix for this problem would be to do:
System.out.println("The car is a " + car.getMake() + ", the brand is " + car.getModel() + ", the price is $" + car.getPrice());
As for changing the variables you should be using:
car.setMake("My New Car Make");
instead of:
Automobile.setMake("My New Car Make");
For the difference between static and instance you can look here, here, and here.
You did this correctly. You accessed the method by using the make instance variable of an Automobile class.
(side note: make is a bad name for an automobile instance, rather call it car1, or something)
Automobile make = new Automobile("Lexus 2017");
System.out.println("The car is " + make.getMake());
Now, everywhere else that you use Automobile.someMethod(), that's not right, because you need to set or get the data on one instance of the class, not the entire class.
Then, finally, you need to test the constructor with three parameters that you have in that class.
You have an error in the constructor call.
Your constructor takes three parameters (make, model and price) but when you call the method only send one. That is an error.
By default, the Java class constructor takes no parameters (in your case, this would be "new Automobile ()").
To implement the tester you have two options.
First, create the car using the constructor without parameters and then set the parameters:
Automobile auto = new Automobile();
auto.setMake("Lexus 2017");
auto.setModel("RX");
auto.setPrice(43020);
Automobile Automobile make = new Automobile ();
Another option is to use your own builder and pass parameters:
Automobile auto2 = new Automobile("Lexus 2017", "RX", 43020);
Automobile.java:
public class Automobile {
private String make;
private String model;
private double price;
public Automobile() {
}
public Automobile(String make, String model, double price) {
this.make = make;
this.model = model;
this.price = price;
}
public String getMake() {
return make;
}
public void setMake(String make) {
this.make = make;
}
public String getModel() {
return model;
}
public void setModel(String model) {
this.model = model;
}
public double getPrice() {
return price;
}
public void setPrice(double price) {
this.price = price;
}
}
AutomobileTester.java:
public class AutomobileTester {
public static void main(String[] args) {
Automobile auto = new Automobile();
auto.setMake("Lexus 2017");
auto.setModel("RX");
auto.setPrice(43020);
System.out.println("The car1 is " + auto.getMake() + " " + auto.getModel() + " " + auto.getPrice());
Automobile auto2 = new Automobile("Lexus 2017", "RX", 43020);
System.out.println("The car2 is " + auto2.getMake() + " " + auto2.getModel() + " " + auto2.getPrice());
}
}
Related
I am doing an assignment requiring me to create a program to store information on tools. The initial class is used to test the results of other classes. The other 4 are made up of a super class called Equipment and has to be abstract, and then 3 child classes.
I have managed to get the equipment class sorted (I think), but can not work out how to override the replacementYear property which is private as the math to return the result changes for each class.
Math for the battery powered class is
Replacement Year = Length of Warranty + Purchase Year
Do I need to create an object to complete the math in each class and use a return statement with the replacementYear I am overriding?
Sorry if it not extremely clear but below is the code.
//Parent
abstract class Equipment {
private String make;
private String model;
private int purchaseYear;
private String replacementYear;
//Constructor for Equipment
public Equipment()
{
make = " ";
model = " ";
purchaseYear = 0;
}
abstract void replacementYear();
public String getMake()
{
return make;
}
public void setMake(String newMake) {
this.make = newMake;
}
public String getModel()
{
return model;
}
public void setModel(String newModel) {
this.model = newModel;
}
public int getPurchaseYear()
{
return this.purchaseYear;
}
}
The child class:
class BatteryPoweredEquipment extends Equipment {
private int warranty = 0;
//Constructor
public void BatteryPoweredEquipment()
{ }
//set & get warranty
public int getWarranty()
{
return warranty;
}
public void setWarranty(int newWarranty)
{
this.warranty = newWarranty;
}
//override
#Override
void replacementYear() {
System.out.println(warranty + this.getPurchaseYear());
}
}
yea, if replacement year needs to computed differently for each type of equipment, then make this method abstract in the abstract superclass so that each extending class can override this to have their custom logic
First of all, you need to create an Equipment constructor that actually accepts all its properties, otherwise, your subclasses would be a pain to use (you would need to call each setter to actually build the object). Talking about setters, that is something you don't really or want (I guess that make, model, purchaseYear do not really change after the Equipment is built and replacementYear should be computed while constructing the object the first time). Additionally, please make use of the new Java Time API (which includes Year and Period instead of modeling years and warranty period as int). After doing this your Equipment class would look as follows:
import java.time.Year;
abstract class Equipment {
private String make;
private String model;
private Year purchaseYear;
private Year replacementYear;
//Constructor for Equipment
public Equipment(String make, String model, Year purchaseYear, Year replacementYear) {
this.make = make;
this.model = model;
this.purchaseYear = purchaseYear;
this.replacementYear = replacementYear;
}
public String getMake() {
return make;
}
public String getModel() {
return model;
}
public Year getPurchaseYear() {
return this.purchaseYear;
}
public Year getReplacementYear() {
return replacementYear;
}
}
Now you also need to adjust your child classes. BatteryPoweredEquipment would look as follows:
import java.time.Period;
import java.time.Year;
class BatteryPoweredEquipment extends Equipment {
private Period warranty;
public BatteryPoweredEquipment(String make, String model, Year purchaseYear, Period warranty) {
super(make, model, purchaseYear, purchaseYear.plus(warranty));
this.warranty = warranty;
}
public Period getWarranty() {
return warranty;
}
}
I have an Object ArrayList and I need to use the toString() method of the Motor object, which is a parameter of the Vehicle object. My vehicle objects are in an ArrayList which is iterated through with a for-loop (I know a foreach loop would be easier, but this is part of the assignment)
Here is the code for the loop:
for (int i = 0; i < VehicleList.size(); i++) {
System.out.println();
String info = VehicleList.get(i).toString();
Motor m = VehicleList.get(i).motor;
String motorInfo = m.toString();
System.out.println(info);
System.out.println(m);
}
There is an error that says "motor cannot be resolved or is not a field".
All of the classes should allow this to work, unless of course there is a simple mistake I am missing.
Here is the Motor class:
public class Motor {
protected String name;
protected int cylinders;
protected int bhp;
protected double displacement;
public Motor(String name, int cylinders, int bhp, double displacement) {
this.name = name;
this.cylinders = cylinders;
this.bhp = bhp;
this.displacement = displacement;
}
public String toString() {
return "Motor name= " + name + ", cylinders= " + cylinders + ", bhp=
" + bhp + ", displacement= " + displacement;
}
}
Motors and Vehicles are intitialized here (In the TestVehicle class):
//Motors
Motor EcoBoost = new Motor("EcoBoost", 6, 310, 2.3);
Motor Hemi = new Motor("Hemi", 8, 707, 5.7);
Motor P90D = new Motor("P90D", 0, 762, 0.0);
//Vehicles
Vehicle v0 = new PassCar("Ford", "Mustang", 2016, 44500.0, 5, true, EcoBoost);
Vehicle v1 = new PassCar("Tesla", "Model S", 2016, 121000.0, 2, true, P90D);
Vehicle v2= new Truck("Dodge", "Ram", 2016, 46000.0, "pickup", 1500, Hemi);
PassCar and Truck are inherited classes of Vehicle with a few more attributes. I can post the PassCar or Truck class if needed but I do not think that is where the problem is arising from. I believe it is coming from the For-Loop, specifically the line Motor m = VehicleList.get(i).motor; but I am not sure of how to fix it.
Vehicle Class:
public class Vehicle {
protected String make;
protected String model;
protected int year;
protected double price;
public Vehicle(String make, String model, int year, double price) {
this.make = make;
this.model = model;
this.year = year;
this.price = price;
}
public void description() {
System.out.println("Description");
}
public String toString() {
return "make= " + make + ", model= " + model + ", year= " + year +
", price= " + price;
}
}
EDIT: There cannot be any Getters or Setters as per the assignment requirements, and it must be an ArrayList, not a regular List. When I switch to I get the error "Type mismatch: cannot convert from ArrayList to ArrayList
Here is an image of the classes:
ArrayList<Object> VehicleList = new ArrayList<>(Arrays.asList(vehicles));
VehicleList is declared to contain instances of Object, so the compiler will only let you access methods and fields it knows exist on all instances of Object.
Change it to ArrayList<Vehicle>.
First, mind the naming convention. Variables should be named in camcelCase e.g. vehicleListinstead ofVehicleList`
I have an Object ArrayList
I believe you mean declaration of vehicleList looks like ArrayList<Object> vehicleList
Then behavior is expected because compiler only knows that VehicleList.get(i) is going to return you an Object reference. It can be a Vehicle, but it can also be anything else. So it won't allow you to access the motor field, as there is simply no such field in Object.
Change your declaration to something like List<Vehicle> vehicleList
However, as mentioned in other answer, it is not a good idea to access the field directly because of various reason. A slightly less evil way is to have getter of motor. (A better way is to provide meaningful behaviors instead of providing access to internal data)
Create an interface IMotor which is used by Vehicle class and Implemented in PassCar and other implementation of vehicle.
IMotor.java
public interface IMotor {
public Motor getMotor();
}
Motor.java
public class Motor {
protected String name;
protected int cylinders;
protected int bhp;
protected double displacement;
public Motor(String name, int cylinders, int bhp, double displacement) {
this.name = name;
this.cylinders = cylinders;
this.bhp = bhp;
this.displacement = displacement;
}
public String toString() {
return "Motor name= " + name + ", cylinders= " + cylinders + ", bhp=" + bhp + ", displacement= " + displacement;
}
}
Vehicle.java
public abstract class Vehicle implements IMotor{
protected String make;
protected String model;
protected int year;
protected double price;
public Vehicle(String make, String model, int year, double price) {
this.make = make;
this.model = model;
this.year = year;
this.price = price;
}
public String toString() {
return "make= " + make + ", model= " + model + ", year= " + year +
", price= " + price;
}
}
PassCar
public class PassCar extends Vehicle{
protected Motor motor;
public PassCar(String make, String model, int year, double price, Motor motor) {
super(make, model, year, price);
this.motor = motor;
}
public Motor getMotor() {
return motor;
}
}
Test.java
import java.util.Arrays;
import java.util.List;
public class Test {
public static void main(String[] args) {
Motor EcoBoost = new Motor("EcoBoost", 6, 310, 2.3);
Vehicle v0 = new PassCar("Ford", "Mustang", 2016, 44500.0, EcoBoost);
List<Vehicle> vehicles = Arrays.asList(v0);
System.out.println(vehicles.get(0).getMotor());
}
}
Your problem is that motor is not a member of the Vehicle class, but you are trying to access it through an expression of type Vehicle - namely vehicleList.get(i). This is forbidden, because the compiler has no way of knowing that every possible kind of Vehicle has a motor. After all, what would happen if you added a Bicycle class?
To make this work, you should remove motor from the Truck and PassCar classes, and add it to the Vehicle class. That way, vehicleList.get(i).motor would actually make sense, since the Vehicle expression would be guaranteed to refer to a Vehicle with a Motor.
It would also be recommended to use a getter for the motor field - that is, have motor as a private field of the Vehicle class, and write a method getMotor() to return it. You could then write vehicleList.get(i).getMotor() to get the Motor object associated with one Vehicle in the list.
Thanks to the help of all of your comments and my Java textbook, I managed to piece it together. Here is how I got it to work:
for (int i = 0; i < vehicleList.size(); i++) {
String motorInfo = "";
String info = "";
System.out.println();
if (vehicleList.get(i) instanceof PassCar) {
info = ((PassCar)vehicleList.get(i)).toString();
**motorInfo = ((PassCar)vehicleList.get(i)).motor.toString();**
}
else if(vehicleList.get(i) instanceof Truck) {
info = ((Truck)vehicleList.get(i)).toString();
**motorInfo = ((Truck)vehicleList.get(i)).motor.toString();**
}
Basically I had to use a polymorphic call and check if it was an instance of a PassCar or Truck.
And as for the Array and ArrayList used during the Class, I edited them like this:
Vehicle [] vehicles = new Vehicle [3];
vehicles[0] = v0;
vehicles[1] = v1;
vehicles[2] = v2;
showVehicle(vehicles);
ArrayList<Vehicle> vehicleList = new ArrayList<Vehicle>(Arrays.asList(vehicles));
System.out.println();
System.out.println("Output from ArrayList in main: ");
Thank you for the help everyone!
I am new to java and learning basic concepts. I was learning abstraction and the most basic definitions i found was : Used to hide the complexity (hide how a process will be done and show what can we do?)
Fair enough. I got a basic idea of what is abstraction. But i am not clear in few things here:
Lets see the below example:
/* File name : Employee.java */
public abstract class Employee {
private String name;
private String address;
private int number;
public Employee(String name, String address, int number) {
System.out.println("Constructing an Employee");
this.name = name;
this.address = address;
this.number = number;
}
public double computePay() {
System.out.println("Inside Employee computePay");
return 0.0;
}
public void mailCheck() {
System.out.println("Mailing a check to " + this.name + " " + this.address);
}
public String toString() {
return name + " " + address + " " + number;
}
public String getName() {
return name;
}
public String getAddress() {
return address;
}
public void setAddress(String newAddress) {
address = newAddress;
}
public int getNumber() {
return number;
}
}
Salary.java
/* File name : Salary.java */
public class Salary extends Employee {
private double salary; // Annual salary
public Salary(String name, String address, int number, double salary) {
super(name, address, number);
setSalary(salary);
}
public void mailCheck() {
System.out.println("Within mailCheck of Salary class ");
System.out.println("Mailing check to " + getName() + " with salary " + salary);
}
public double getSalary() {
return salary;
}
public void setSalary(double newSalary) {
if(newSalary >= 0.0) {
salary = newSalary;
}
}
public double computePay() {
System.out.println("Computing salary pay for " + getName());
return salary/52;
}
}
Main.java
/* File name : AbstractDemo.java */
public class AbstractDemo {
public static void main(String [] args) {
Salary s = new Salary("Mohd Mohtashim", "Ambehta, UP", 3, 3600.00);
Employee e = new Salary("John Adams", "Boston, MA", 2, 2400.00);
System.out.println("Call mailCheck using Salary reference --");
s.mailCheck();
System.out.println("\n Call mailCheck using Employee reference--");
e.mailCheck();
}
}
My question here is , we cant even intsantiate an abstract class. So we have to extend it and overide the same method? When we override the abstract methos in the child class, the super class(abstract class method) is of no use. Also as we cant even intantiate , why cant we just write everything in one class instead of extending the abtsrcat class?
While extending the abstract class and overriding the same thing is it not a negative as the space will more for these waste abstract classes?
I know i dont have clarity and thats the reason i am confused. If anyone can clarify this (no stratight definions which are not useful for noobs like me) with explanation , i would really appreciate the time for that.
Aside of bad example you use, your understanding of Abstract class is not right:
So we have to extend it and overide the same method? When we override the abstract methos in the child class, the super class(abstract class method) is of no use
First: Abstract class and Interface both stay to provide abstract methods to be overridden by extending or implementing classes.
Second: Abstract class can have common methods implementation for all extending classes - then you do not need to implement or override them over and over again. Just use them. (Note: starting from Java 8 Interface also can have default implementation for methods)
Third: if you need another than common implementation - override needed method from super class.
Forth: if in your another implementation you need to run super method - do it at any time in the implementation by calling super.methodName(...)
I've been asked to program a small online sales aplication.
It sounds very simple in theory (but it's been a hell for me). I'm just supposed to have an arrayList with about 5 products and then have a client buy 1 to 5 products and print the sales total.
public class Product {
private String name;
private double price;
public Product(String name, double price) {
this.name = name;
this.price = price;
}
public String getName() {
return name;
}
public double getPrice() {
return price;
}
public String printInfo() {
return "Product: " + name + " Cost: " + price;
}
}
Then I have a client class:
public class Cliente {
private String name;
private int numPedido;
ArrayList<Producto> products = new ArrayList<Producto>();
public void listBuilder() {
Producto shirt = new Producto("Shirt", 30);
Producto tshirt = new Producto("T-Shirt", 40);
Producto sweater = new Producto("Sweater", 50);
}
public Cliente(String name, int numPedido) {
this.name = name;
this.numPedido = numPedido;
}
public Cliente() {
}
public String getName() {
return name;
}
public int getNumPedido() {
return (int) (Math.random() * 100);
}
public void addNewClient() {
name = JOptionPane.showInputDialog("Nombre: ");
}
public String printInfo() {
return "Nombre: " + name;
}
}
Right now I'm stuck thinking on how to make a client select a product and get that attached to him. I was thinking on making an arrayList of an arrayList but I'm sure that would complicate things. I know there is probably an easier way to connect them but I can't think of any. The option I have in mind is a method which shows numbers from 1 to 3(corresponding to each product) and when the user picks one it should return the price of the item.
Still not sure how to implement it in a way that the user can pick multiple products.
EDIT:
I also have an admin class that goes like this:
public class Admin {
private Client[] clientList;
public AdminPedidos() {
clientList = new Client[2];
}
public void AddContact() {
clienteList[0] = addProduct();
clienteList[1] = addProduct();
fillList();
}
public Cliente addProduct() {
String contactoString = JOptionPane.showInputDialog("Are you a new client? Press 1 if yes.");
if (contactoString.equals("1")) {
return new Cliente();
} else {
return new Cliente(); //just for testing
}
}
private void fillList() {
for (Client i : clientList) {
i.addNewClient();
}
}
public void printContact() {
for (Client i : clientList) {
System.out.println(i.printInfo());
}
}
}
You can have some purchaseProduct method attached to each Client.
public void purchaseProduct(Product product) { this.products.add(product); }
Then each Client you instantiate (Client client = new Client(name, id);) can add Products to his/her cart with the purchaseProduct method.
I'm assuming you are using some kind of user input method (Scanner). With that you can read the user's input of which Product they want and accordingly call the function with the right Product.
The listBuilder function doesn't quite make sense to me btw (and after your edit, it's really hard to make sense of what the Admin class should be/represent).
Edit: You would probably want to create an ArrayList<Product> which will be attached to each client, which you already have. I sense that you have a difficulty deciding where to put your actual Products. You should not put them inside your Client class for sure.
You should think about who/where they are going to be used. Probably in main right? So just instantiate them there first and then the Client could choose which one to purchase (via the method I introduced before):
client.purchaseProduct(product);
I have a Bread class and a Filling class which set the bread type and calories per slice as well as a filling class which sets the filling type and calories per serving... I can't seem to figure out how to pass them into the sandwich class correctly. My total calories doesn't work out
private class Sandwich {
private Bread bread;
private Filling filling;
private Bread caloriesPerSlice;
private Filling caloriesPerServing;
private Sandwich(String breadType, int caloriesPerSlice, String fillingType, int caloriesPerServing) {
setBread(bread);
setBread(caloriesPerSlice);
setFilling(caloriesPerServing);
setFilling(filling);
}
public Bread getBread() {
return bread;
}
public void setBread(Bread bread) {
this.bread = bread;
}
public Filling getFilling() {
return filling;
}
public void setFilling(Filling filling) {
this.filling = filling;
}
public int getTotalCalories(int caloriesPerSlice,int caloriesPerServing) {
(caloriesPerSlice) * 2 + caloriesPerServing = totalCalories;
return this.totalCalories;
}
}
You have your variable assignment backwards.
(caloriesPerSlice) * 2 + caloriesPerServing = totalCalories; is not valid. The variable being assigned to must be on the left.
Try:
totalCalories = (caloriesPerSlice) * 2 + caloriesPerServing;
(caloriesPerSlice) * 2 + caloriesPerServing = totalCalories; Doesn't do what you think it does.
Perhaps you mean
totalCalories = (caloriesPerSlice) * 2 + caloriesPerServing;
I see some problems in your code:
why does an instance of Sandwich should have two Bread object within? A sandwich is usually made by one type of bread.
the caloriesPerSlice and caloriesPerServing should be respectively attributes of Bread and Filling.
you can't pass a String parameter to setFilling(Filling filling) method.
(caloriesPerSlice) * 2 + caloriesPerServing is not a valid left-value and is not a valid expression because caloriesPerSlice and caloriesPerServing are objects.
This is a really basic implementation of your idea:
Bread.java
public class Bread
{
private String type;
private int caloriesPerSlice;
public Bread(String type, int caloriesPerSlice)
{
this.type = type;
this.caloriesPerSlice = caloriesPerSlice;
}
public String getType() { return type;}
public int getCaloriesPerSlice() { return caloriesPerSlice; }
public String toString()
{
return type + " (" + caloriesPerSlice + "cal)";
}
}
Filling.java
public class Filling
{
private String name;
private int caloriesPerServing;
public Filling(String name, int caloriesPerSlice)
{
this.name = name;
this.caloriesPerServing = caloriesPerSlice;
}
public String getName() { return name;}
public int getCaloriesPerServing() { return caloriesPerServing; }
public String toString()
{
return name + " (" + caloriesPerServing + "cal)";
}
}
Sandwich.java
public class Sandwich
{
private Bread bread;
private Filling filling;
public Sandwich(Bread bread, Filling filling)
{
this.bread = bread;
this.filling = filling;
}
public int getTotalCalories()
{
return 2 * bread.getCaloriesPerSlice() + filling.getCaloriesPerServing();
}
public String toString()
{
return "Bread: " + bread.toString() + "\nFilling: " + filling.toString();
}
}
Main.java
public class Main
{
public static void main(String args[])
{
Bread bread = new Bread("Baguette", 150);
System.out.println("I would like a " + bread.toString());
Filling filling = new Filling("Prosciutto di Parma", 75);
System.out.println("with " + filling.toString());
Sandwich sandwich = new Sandwich(bread, filling);
System.out.println("Your order is:");
System.out.println(sandwich.toString());
int totalCalories = sandwich.getTotalCalories();
System.out.println("The total calories are " + totalCalories);
}
}
This is the output:
I would like a Baguette (150cal)
with Prosciutto di Parma (75cal)
Your order is:
Bread: Baguette (150cal)
Filling: Prosciutto di Parma (75cal)
The total calories are 375
The class has a lot of errors:
You have a Bread caloriesPerSlice, but the constructor uses the same variable as int.
The same with the Filling caloriesPerServing and the int caloriesPerServing.
It has a private constructor. This constructor specify that the only way you can access a class of this type is through a static method in the class that returns an Sandwich object (like with the singleton pattern), which is not the case here.
The class is private: maybe I'm wrong, but a private class in java means that no one can access it.
The constructor: for example, breadType is a string object, and it's not used. You are trying to setBread with the private variable... what is that?
The constructor: caloriesPerSlice is an int type and you use it in the setBread() setter which receives a Bread type. You are mixing types.
The same with caloriesPerServing which is used in setFilling(), which receives a Filling object....
getTotalCalories: the assignment goes on the right, not the left.
I think you have a misunderstanding of OO. For example, let's see the Bread class:
If the bread class has the properties caloriesPerSlice and breadType they maybe are part of the bread type. Let's change the class to reflect those properties:
public class Bread {
private int caloriesPerSlice;
private String type;
public Bread(String type, int caloriesPerSlice)
{
this.type = type;
this.caloriesPerSlice = caloriesPerSlice;
}
public int getCaloriesPerSlice()
{
return this.caloriesPerSlice;
}
public String getType()
{
return this.type;
}
}
Here in this case the Bread is completely defined though his constructor. You can see that the class has no setter. That's because I decided it, but it's up to you if you want a parameterless constructor and setters in the class. Here in this case I only defined getters. Let's see the Filling class:
public class Filling {
private int caloriesPerServing;
private String type;
public Filling(String type, int caloriesPerServing) {
this.caloriesPerServing = caloriesPerServing;
}
public int getCaloriesPerServing()
{
return hits.caloriesPerServing;
}
public void setCaloriesPerServing(int calories)
{
this.caloriesPerServing = calories;
}
public String getType()
{
return this.type;
}
public void setType(String type)
{
this.type = type;
}
}
Here the Filling class has getters and setters. It's just for explanation purposes: in the Filling class you can set the properties through constructor or through the setters, whilst in the Bread you can only define the properties through the constructor.
Now the Sandwich maybe can receive all the properties that define a bread and a filling (like in your case), or maybe it can receive a bread and a filling). Let's see the first case:
public class Sandwich {
private Bread bread;
private Filling filling;
public Sandwich(String breadType, int caloriesPerSlice, String fillingType, int caloriesPerServing) {
this.bread = new Bread(breadType, caloriesPerSlice);
this.filling = new Filling(fillingType, caloriesPerServing);
}
public Bread getBread() {
return bread;
}
public void setBread(Bread bread) {
this.bread = bread;
}
public int getTotalCalories() {
return this.bread.getCaloriesPerSlice() * 2 + this.filling.getCaloriesPerServing();
}
}
As you can see, we received in the Sandwich constructor all the parameters which define a bread and a filling. Then, we created the Bread and Filling objects, passing their parameters. Finally, the getTotalCalories is nothing but a simple math of the bread and filling properties.
This code was just writen in a text editor. I did not checked if it's ok or not.
In this example, Sandwich becomes a class and a factory, a very important component of the class. As you can see, the construction of the Bread and Filling classes is made through the Sandwich. It has the advantage that the Sandwich controls the creation of objects, but the thing is: Is the sandwich responsible of that? Maybe not, because when you make a sandwich in your home you get the bread and the other ingredients and you just put them on the slices... the sandwich is not responsible of the creation of a bread slice... it does not make sense in the real life. Then, maybe it's a good idea to remove the object creation in the Sandwich constructor:
public Sandwich(Bread bread, Filling filling) {
this.bread = bread;
this.filling = filling
}
This case is more 'correct' because you're making a sandwich with the elements already generated in memory. It's the same when you make a sandwich in your home: you get the bread, the filling and then you make a sandwich.
I hope this can clarify a little more about OO.
Greetings!