Java for loop and nested if statement - java

I have trouble to figure out where is the problem in my code. I have an employee array list, and assignment array list. The goal is to add to availableEmpAry only those employees whose skill array contains all required skills and is available on the time of shift.
The problem is after I have found employee with required skills. When starting the second loop, it does not check if an employee is available on that time. It always jumps to the else and displays the message box.
for (int j = 0; j < empAry.size(); j++){
//Checking if employee skill array has an exact skill for cs
if (empAry.get(j).empSkillAry.containsAll(tempShift.Schedule.skillRequiredAry)){
for(int i = 0; i < assignmentAry.size(); i++){
if(assignmentAry.get(i).employee.equals(empAry.get(j))){
Date shiftStart= tempShift.Start;
Date shiftEnd=tempShift.End;
Date empAsStart=assignmentAry.get(i).Start;
Date empAsEnd=assignmentAry.get(i).End;
if(empAsStart.before(shiftEnd) && empAsEnd.after(shiftStart)){
JOptionPane.showMessageDialog(availableEmp, "No Available Employee!");
}else{
availableEmpAry.add(empAry.get(j));
availableEmp.setModel(
new DefaultComboBoxModel<Object>(availableEmpAry.toArray())
);
}
}else{
availableEmpAry.add(empAry.get(j));
availableEmp.setModel(
new DefaultComboBoxModel<Object>( availableEmpAry.toArray())
);
}
}//closing assignment loop
}else{
JOptionPane.showMessageDialog(availableEmp, "No employee with required skill!");
}
} // closing loop for employee

At the start of the second loop there is the following line of code:
if(assignmentAry.get(i).employee.equals(empAry.get(j)))..
It is not clear what type of object is employee, but in order for this condition to be TRUE and to enter the block where you check the availability,you need to properly implement the equals method for the JAva class associated with the employee objects.
It is also recommended that the type of assignmentAry.get(i).employee and the type of empAry.get(j) should be the same in order for the equals method to make sense. This is not a JAVA constraint but more like a design constraint.

Related

is there way to select everything from a list of model?

asnafList is my list and getIc_number is my getter below is my code
asnafList.get(0).getIc_number();
I am trying to make sort of an authenticating feature for my apps and I use the above code in my if statement for the button. That code only get the 0 position of the list. So my question is, is there a way to get all of the position is the list to compare with the input from the user using the if statement?
int number;
for(int i = 0; i < asnafList.size(); i++) {
number = asnafList.get(i).getIc_number();
if(number == YOUR_COMPARABLE_NUMBER) {
// Compare and do anything here
}
}
As Kushal answered, a for loop is useful for this. But I usually use a for each loop in this scenario. Not sure what type of objects are in the asnafList, but it will look something like this:
for(AsnafObject a : asnafList) {
if(a.getIc_number() == YOUR_COMPARABLE_NUMBER) {
// do stuff
}
}
When you do this for loop, you basically iterate through every object in the asnafList, where AsnafObject is the classtype of your asnafList and a is the object which you can use to call any non-static methods of AsnafObject (or however your class is called)

Add many element into list without instantiate too many object

I have a for loop like and an ArrayList as follow:
List<VehicleImpl> vehicles = new ArrayList<VehicleImpl>();
for(int i = 0; i < input.getNoVehicles(); i++) {
//Name vehicle by index
VehicleImpl vehicle = VehicleImpl.Builder.newInstance("vehicle " + String.valueOf(i+1))
//The first location - depot location is indexed as 0 in Matrices
.setStartLocation(Location.newInstance(i))
.setBreak(lunch)
.setLatestArrival(input.getOperating())
.setType(type)
.build();
vehicles.add(vehicle);
}
So, I want to ask: Is there any way I instantiate the VehicleImpl outside the loop and use the ONLY ONE instance. For each iteration, I modify the instance add the new version of instance to the list.
Yes but you have to clone the first intance at leat (By using BeanUtils for example).
Then you just update the startLocation attribute.
You could instantiate the builder outside the loop, which would halve the number of objects you're creating, but only if you were to change the builder's constructor to have zero arguments, moving the vehicle name into a setter. For example:
List<VehicleImpl> vehicles = new ArrayList<VehicleImpl>();
VehicleImpl.Builder builder = VehicleImpl.Builder.newInstance();
for(int i = 0; i < input.getNoVehicles(); i++) {
VehicleImpl vehicle = builder
//Name vehicle by index
.setName("vehicle " + String.valueOf(i+1))
//The first location - depot location is indexed as 0 in Matrices
.setStartLocation(Location.newInstance(i))
.setBreak(lunch)
.setLatestArrival(input.getOperating())
.setType(type)
.build();
vehicles.add(vehicle);
}
This is somewhat more error prone because values in the builder are not reset on each new iteration. That's not necessarily a problem for you right now, but if you were to add conditional logic, you'd probably start having a lot of problems. However, if your goal is to reduce the number of objects created, this will satisfy that.

How to search an array of objects and then update a part of the object in java?

I have an Array of objects. Each object is a customer record, which is the customer ID (int), first name (String), last name(String), and balance (double).
My problem is that i am not supposed to have duplicate customer records, so if they appear in the file twice, I have to just update their balance. I cannot figure out how to search the array to find out if i need to just update the balance or make a new record in the array.
I feel like i should do this in the get/setters, but i am not exactly sure.
edit: to clarify on "if they appear in the file twice, I have to just update their balance." I have a file i made in notepad which is supposed to be a customer list, which has all of their information. if the same customer shows up twice, say the following day to buy more stuff, i am not supposed to create a new object for them since they already have an object and a place in the array. instead, i am supposed to take the amount they spent, and add it to their already existing balance within their existing object.
edit2: i thought i would give you the bit of code i have already where i read in the values into the array. i based this off of the example we did in class, but we didn't have to update anything, just store information into an array and print it if needed.
public CustomerList(){
data = new CustomerRecord[100]; //i'm only allowed 100 unique customers
try {
Scanner input = new Scanner(new File("Records.txt"));
for(int i = 0; i < 100; ++i){
data[i] = new CustomerRecord();
data[i].setcustomerNumber(input.nextInt());
data[i].setfirstName(input.next());
data[i].setlastName(input.next());
data[i].setTransactionAmount(input.nextDouble());
}
} catch (FileNotFoundException e) {
e.printStackTrace();
}
}
You shouldn't be using arrays in that case. A Set would be much more suitable as it, by definition, does not have duplicate entries.
What you need to do is to implement the equals() and hashCode() methods in your Customer class so they only use id (or id and name fields) but not balance.
If for some reason you need to use arrays you have two options:
sort the array and use binary search to find if the customer is there, this is nice if the array doesn't change much but you're doing a lot of updates
simply do a linear scan of the array, checking each entry to see if a given customer is already there, if so then update the balance, otherwise add it as a new entry
It would be something like:
public void updateOrAdd(Customer cst) {
boolean exists = false;
for(Customer existing : array) {
// !!! You need to implement your own equals method in the
// customer so it doesn't take into account the balance !!!
if(existing.equals(cst)) {
exists = true;
existing.updateBalance(cst.getBalance());
break;
}
}
if(!exists) {
// add the cst to the array
}
}
The difference is in runtime, the set solution will be constant O(1) on average (unless you incorrectly implement your hashCode() method).
Suppose you have a Customer array:
Customer[] customers = new Customer[size];
... // fill the array with data
Then you get a new customer object called newCustomer. You need to search for newCustomer in your array and, update it if it is already there, or add it if it's not. So you can do something like this:
// Return, if it exists, a customer with id equal to newCustomer.getId()
Optional<Customer> existingCustomer =
Arrays.stream(customers)
.filter(c -> newCustomer.getId().equals(c.getId()))
.findFirst();
if (existingCustomer.isPresent()) {
// update the customer object with newCustomer information as appropriate
Customer customer = existingCustomer.get();
// assuming you have an updateBalance() method
customer.updateBalance(newCustomer.amountSpent());
} else {
// if the customer is not in the array already, add them to the current position
customers[currentIndex] = newCustomer;
}

How to find the number of times a specific element occurs in an Array list in Java

I have written a method with the aim to count the number of times a specific flavour of crisps appears in a snack machine in blueJ
public int countPacks(String flavour){
int n = 0;
int nrFlavour = 0;
while( n < packets.size()) {
if( packets.get(n).equals(flavour)){
nrFlavour++;
n++;
}
else n++;
}
return nrFlavour;
}
I have an Arraylist 'packets' which holds PackOfCrisps objects which have a specific flavour. However when I have added say three packets of "salt" flavour crisps and I run this method, inputting "salt" as the flavour, it just returns 0 as though there are no PackOfCrisps objects with flavour "salt".
Sorry if this doesn't make sense. I am very new to Java and I have tried to explain my problem the best I can. :)
The list packets holds PackOfCrisps objects, and the method takes a String parameter. So the statement packets.get(n).equals(flavour) is comparing a PackOfCrisps object to a String, hence the count variable will never increase.
You need to compare the flavour string to the specific field of the object, something like:
if(packets.get(n).getFlavour().equals(flavour)){
On a side note, you can replace the while loop with a simple for loop and remove the increment of n.
There is a built-in solution to your problem, you can use this method
You can rewrite your countPacks method like this :
public int countPacks(String flavour){
return Collections.frequency(packets, flavour);
}

Java is not assigning values to my variables correctly, with linked lists

public void returnRental(Customer cust){
Rental toDelete = null; //Rental to be removed from list.
LinkedList<Video> toReturn = null; //List of videos to be added to inventory.
//Find appropriate rental according to customer name.
for(int i = 0; i < rentals.size(); i++){
if(cust.getName() == rentals.get(i).getRentee().getName()){
toReturn = rentals.get(i).getRented();
toDelete = rentals.get(i);
}
}
here is the snippet of code that is giving me problems. I've debugged it in eclipse quite a bit which ended up just confusing me more. It hits the if, and passes the condition. But once it gets to assigning values to "toReturn" it assigns it an empty list with size 0. Where as I check my rentals Linked list and the correct value are there, but for some reason it is not getting assigned to my variables correctly :( The same happens to "toDelete" but this isn't a list, it is one instance of my class Rental. (The linked list is a list of rentals, which contains a linked list of videos)
No errors are thrown...
Its a little difficult to explain, if you need more information please let me know and i'll clarify.
I'm at a loss, possibly because I'm not iterating through my linked list correctly?
Replace
if (cust.getName() == rentals.get(i).getRentee().getName()){
by
if (cust.getName().equals(rentals.get(i).getRentee().getName())){
You can't compare strings with == (except if your algorithm can ensure this is the same instance, which is almost never the case).
But the missing equals is not the only bug. It may be inside getRented() or elsewhere (you don't show what you do with toReturn and toDelete, so it's not clear if you don't have problems here).
Now, to go on chasing your bugs, you should either
debug, and put a breakpoint in your loop to check the state of rentals.get(i) and the execution at this point
if you can't debug, put a lot of System.println, so that you know what you have...
I've upvoted dystroy's answer because incorrect string comparison is always wrong.
But because that would fail differently (customer names not matching rentee names), I'm wondering if your issue is really caused by either of the following:
a problem in getRented(); or
cust having a null name on call, which would match a Rentee with a null name.
Possibly, your if condition is being hit more than once. First of all, check if this is actually happening. If so, check your logic and determine if you want to stop at the first occurence or at the last (this case seems to be the latter).
If you want to stop at the first occurence, break the iteration:
for(int i = 0; i < rentals.size(); i++){
if(cust.getName() == rentals.get(i).getRentee().getName()){
toReturn = rentals.get(i).getRented();
toDelete = rentals.get(i);
break;
}
}
for(int i = 0; i < rentals.size(); i++){
if(cust.getName().equals( rentals.get(i).getRentee().getName())){
toReturn.addAll(rentals.get(i).getRented());
//assumming it returns the list of Video object
toDelete = rentals.get(i);
}
}

Categories