diff --git a/MV3302ClassCode/src/mv3302/Customer.java b/MV3302ClassCode/src/mv3302/Customer.java index 6a4b4db1d986d39c76faad4b08ea9bfd06873fc7..6aeeb8decbf6392ebe0953238fe9a55ecc7805a8 100644 --- a/MV3302ClassCode/src/mv3302/Customer.java +++ b/MV3302ClassCode/src/mv3302/Customer.java @@ -18,6 +18,8 @@ public class Customer extends Entity { /** * constructor method that assigns values of serviceTime and renegeTime to each customer + * @param serviceTime + * @param renegeTime */ public Customer(double serviceTime, double renegeTime) { super("Customer"); diff --git a/MV3302ClassCode/src/mv3302/CustomerArrivalProcess.java b/MV3302ClassCode/src/mv3302/CustomerArrivalProcess.java index 6d53bebe48b985e7e5e4708953a970a9aa0b322b..4957d31451f1363ece3facb4e55f1c95a4cf7ef5 100644 --- a/MV3302ClassCode/src/mv3302/CustomerArrivalProcess.java +++ b/MV3302ClassCode/src/mv3302/CustomerArrivalProcess.java @@ -4,6 +4,7 @@ */ package mv3302; +import simkit.Entity; import simkit.random.RandomVariate; /** @@ -21,6 +22,13 @@ public final class CustomerArrivalProcess extends ArrivalProcess { private int numberofArrivals; + /** + * Zero-argument constructor + */ + public CustomerArrivalProcess() { + super(); + } + /** * Constructor method that instantiates renege times and service times for * each customer arrival @@ -47,7 +55,13 @@ public final class CustomerArrivalProcess extends ArrivalProcess { waitDelay("Arrival", 0.0, customer); numberofArrivals += 1; } +/** + * Does nothing, since this is only to be "heard" + * @param customer + */ + public void doArrival(Customer customer) { + } /** * @return the serviceTimeGenerator */ diff --git a/MV3302ClassCode/src/mv3302/Part.java b/MV3302ClassCode/src/mv3302/Part.java new file mode 100644 index 0000000000000000000000000000000000000000..412151c5916f8438ddfbb79b8711775f816408a1 --- /dev/null +++ b/MV3302ClassCode/src/mv3302/Part.java @@ -0,0 +1,39 @@ +/* + * Click nbfs://nbhost/SystemFileSystem/Templates/Licenses/license-default.txt to change this license + * Click nbfs://nbhost/SystemFileSystem/Templates/Classes/Class.java to edit this template + */ +package mv3302; + +import simkit.Entity; + +/** + * + * @author dansl + */ +public class Part extends Entity{ + private double totalDelayInQueue; + private int next; + + public Part(){ + super(); + } + + public Part(int next){ + super(); + this.next = next; + this.totalDelayInQueue = 0.0; + } + + public double getTotalDelayInQueue() { + return this.totalDelayInQueue; + } + + public void advance() { + this.next += 1; + } + + public void incrementDelayInQueue(double incrementDelay) { + this.totalDelayInQueue += incrementDelay; + } +} + diff --git a/MV3302ClassCode/src/mv3302/PartArrivalProcess.java b/MV3302ClassCode/src/mv3302/PartArrivalProcess.java new file mode 100644 index 0000000000000000000000000000000000000000..1fb80816777baa609d1305b20494c5235d05e3f5 --- /dev/null +++ b/MV3302ClassCode/src/mv3302/PartArrivalProcess.java @@ -0,0 +1,42 @@ +/* + * Click nbfs://nbhost/SystemFileSystem/Templates/Licenses/license-default.txt to change this license + * Click nbfs://nbhost/SystemFileSystem/Templates/Classes/Class.java to edit this template + */ +package mv3302; + +import simkit.random.RandomVariate; + +/** + * + * @author dansl + */ +public class PartArrivalProcess extends ArrivalProcess{ + + /** + * Zero-argument constructor + */ + public PartArrivalProcess() { + super(); + } + + /** + * Instantiate with the given parameters + * + * @param interarrivalTimes Given inter arrival times + */ + public PartArrivalProcess(RandomVariate interarrivalTimes) { + super(interarrivalTimes); + } + + /** + * Schedule next Arrival<br> + * Schedule Arrival(index) + */ + @Override + public void doArrival() { + super.doArrival(); + Part part = new Part(); + waitDelay("Arrival", 0.0, part, 0); + } + +} diff --git a/MV3302ClassCode/src/mv3302/ServerWithReneges.java b/MV3302ClassCode/src/mv3302/ServerWithReneges.java index b097e6c223d24e6f49c178e95de09c667d354d0e..6c7d6e1131293018fc6d680ef806f9e99638a7fc 100644 --- a/MV3302ClassCode/src/mv3302/ServerWithReneges.java +++ b/MV3302ClassCode/src/mv3302/ServerWithReneges.java @@ -133,13 +133,14 @@ public final class ServerWithReneges extends SimEntityBase { public void doStartService() { Customer customer = queue.first(); SortedSet<Customer> oldQueue = getQueue(); + queue.remove(customer); firePropertyChange("queue", oldQueue, getQueue()); int oldNumberAvailableServers = getNumberAvailableServers(); numberAvailableServers -= 1; firePropertyChange("numberAvailableServers", oldNumberAvailableServers, getNumberAvailableServers()); - interrupt("renege", customer); delayInQueueServed = customer.getElapsedTime(); firePropertyChange("delayInQueueServed", getDelayInQueueServed()); + interrupt("Renege", customer); waitDelay("EndService", serviceTimeGenerator, customer); } @@ -149,12 +150,15 @@ public final class ServerWithReneges extends SimEntityBase { * delayInQueueReneged values as elapsedTime */ public void doRenege(Customer customer) { + delayInQueueReneged = customer.getElapsedTime(); + firePropertyChange("delayInQueueReneged", getDelayInQueueReneged()); + SortedSet<Customer> oldQueue = getQueue(); queue.remove(customer); + firePropertyChange("queue", oldQueue, getQueue()); double oldNumberReneges = getNumberReneges(); numberReneges += 1; firePropertyChange("numberReneges", oldNumberReneges, getNumberReneges()); - delayInQueueReneged = customer.getElapsedTime(); - firePropertyChange("delayInQueueReneged", getDelayInQueueReneged()); + } /** diff --git a/MV3302ClassCode/src/mv3302/TransferLineComponent.java b/MV3302ClassCode/src/mv3302/TransferLineComponent.java new file mode 100644 index 0000000000000000000000000000000000000000..cd9b445bdc8a336a3466ff6e973611529c25b373 --- /dev/null +++ b/MV3302ClassCode/src/mv3302/TransferLineComponent.java @@ -0,0 +1,215 @@ +package mv3302; + +import simkit.*; +import java.util.*; +import static simkit.Priority.HIGHER; +import simkit.random.RandomVariate; + +public class TransferLineComponent extends SimEntityBase { + + private int[] totalNumberMachines; + private RandomVariate[] processingTimeGenerator; + protected int[] numberAvailableMachines; + protected List<SortedSet<Part>> queue; + protected double[] delayInQueue; + protected double[] timeAtStation; + protected double totalDelayInQueue; + protected double totalTimeInSystem; + + /** + * Instantiate an EntityServer with the given titalNumberServers and + * serviceTimeGenerator. Note: should call <code>this()</code> to ensure + * that <code>queue</code> is instantiated + * + * @param processingTimeGenerator + * @param totalNumberMachines + */ + public TransferLineComponent(RandomVariate[] processingTimeGenerator, int[] totalNumberMachines) { + + this(); + this.setProcessingTimeGenerator(processingTimeGenerator); + this.setTotalNumberMachines(totalNumberMachines); + numberAvailableMachines = totalNumberMachines.clone(); + delayInQueue = new double[totalNumberMachines.length]; + timeAtStation = new double[totalNumberMachines.length]; + queue = new ArrayList<SortedSet<Part>>(); + for (int station = 0; station < totalNumberMachines.length; ++station) { + queue.add(new TreeSet<>()); + } + } + + public TransferLineComponent() { + super(); + + } + + @Override + public void reset() { + super.reset(); + numberAvailableMachines = getTotalNumberMachines().clone(); + Arrays.fill(delayInQueue, Double.NaN); + Arrays.fill(timeAtStation, Double.NaN); + //queue.clear(); + } + + public void doRun() { + totalDelayInQueue = Double.NaN; + totalTimeInSystem = Double.NaN; + firePropertyChange("totalDelayInQueue", getTotalDelayInQueue()); + firePropertyChange("totalDelayInSystem", getTotalTimeInSystem()); + firePropertyChange("numberAvailableMachines", getNumberAvailableMachines()); + waitDelay("Init", 0.0, HIGHER, 0); + } + + public void doInit(int i) { + this.numberAvailableMachines[i] = totalNumberMachines[i]; + fireIndexedPropertyChange(i, "numberAvailableMachines", getNumberAvailableMachines(i)); + queue.get(i).clear(); + fireIndexedPropertyChange(i, "queue", getQueue(i)); + double[] oldDelayInQueue = getDelayInQueue().clone(); + delayInQueue[i] = Double.NaN; + firePropertyChange("delayInQueue", oldDelayInQueue, getDelayInQueue()); + double[] oldTimeAtStation = getTimeAtStation().clone(); + timeAtStation[i] = Double.NaN; + firePropertyChange("timeAtStation", oldTimeAtStation, getTimeAtStation()); + if (i < totalNumberMachines.length - 1) { + waitDelay("Init", 0.0, HIGHER, i + 1); + } + } + + public void doArrival(Part part, int station) { + part.stampTime(); + SortedSet<Part> oldQueue = getQueue(station); + queue.get(station).add(part); + fireIndexedPropertyChange(station, "queue", oldQueue, getQueue(station)); + if (numberAvailableMachines[station] > 0) { + waitDelay("StartService", 0.0, Priority.HIGH, station); + } + } + + public void doStartProcessing(int station) { + SortedSet<Part> oldQueue = queue.get(station); + Part part = oldQueue.first(); + //fireIndexedPropertyChange(station, "queue", oldQueue, getQueue(station)); + int[] oldNumberAvailableMachines = getNumberAvailableMachines().clone(); + oldNumberAvailableMachines[station]--; + fireIndexedPropertyChange(station, "numberAvailableMachines", oldNumberAvailableMachines[station], getNumberAvailableMachines()[station]); + double[] oldDelayInQueue = getDelayInQueue().clone(); + delayInQueue[station] = part.getElapsedTime(); + firePropertyChange("delayInQueue", oldDelayInQueue, getDelayInQueue()); + part.incrementDelayInQueue(oldDelayInQueue[station]); + waitDelay("EndProcessing", getProcessingTimeGenerator()[station].generate(), Priority.HIGH, part, station); + //add state condition changes + } + + public void doEndProcessing(Part part, int station) { + int[] oldNumberAvailableMachines = getNumberAvailableMachines().clone(); + getNumberAvailableMachines()[station]++; + fireIndexedPropertyChange(station, "numberAvailableMachines", oldNumberAvailableMachines[station], getNumberAvailableMachines()[station]); + double[] oldTimeAtStation = getTimeAtStation().clone(); + timeAtStation[station] = part.getElapsedTime(); + firePropertyChange("timeAtStation", oldTimeAtStation, getTimeAtStation()); + if (station < totalNumberMachines.length) { + waitDelay("Arrival", 0.0, part, station + 1); + } + if (station == totalNumberMachines.length - 1) { + waitDelay("PartComplete", 0.0, part); + } + if (!queue.get(station).isEmpty()) { + waitDelay("StartProcessing", 0.0, station); + } + //add property changes portions + } + + public void doPartComplete(Part part) { + totalTimeInSystem = part.getAge(); + totalDelayInQueue = part.getTotalDelayInQueue(); + } + + /** + * @return the totalNumberMachines + */ + public int[] getTotalNumberMachines() { + return totalNumberMachines.clone(); + } + + public int getTotalNumberMachines(int station){ + return totalNumberMachines[station]; + } + + /** + * @return the processingTimeGenerator + */ + public RandomVariate[] getProcessingTimeGenerator() { + return processingTimeGenerator.clone(); + } + + public RandomVariate getProcessingTimeGenerator(int station){ + return processingTimeGenerator[station]; + } + + /** + * @return the numberAvailableMachines + */ + public int[] getNumberAvailableMachines() { + return numberAvailableMachines.clone(); + } + + public int getNumberAvailableMachines(int station) { + return numberAvailableMachines[station]; + } + + public SortedSet<Part> getQueue(int station) { + return new TreeSet<>(queue.get(station)); + } + + public List<SortedSet<Part>> getQueue() { + List<SortedSet<Part>> queueListCopy = new ArrayList<>(); + for (int station = 0; station < queue.size(); ++station) { + queueListCopy.add(getQueue(station)); + } + return queueListCopy; + } + + public double[] getDelayInQueue() { + return delayInQueue.clone(); + } + + public double getDelayInQueue(int station) { + return delayInQueue[station]; + } + + /** + * @return the timeAtStation + */ + public double[] getTimeAtStation() { + return timeAtStation.clone(); + } + + public double getTimeAtStation(int station) { + return timeAtStation[station]; + } + + /** + * @return the totalDelayInQueue + */ + public double getTotalDelayInQueue() { + return totalDelayInQueue; + } + + /** + * @return the totalTimeInSystem + */ + public double getTotalTimeInSystem() { + return totalTimeInSystem; + } + + private void setTotalNumberMachines(int[] totalNumberMachines) { + this.totalNumberMachines = totalNumberMachines; + } + + private void setProcessingTimeGenerator(RandomVariate[] processingTimeGenerator) { + this.processingTimeGenerator = processingTimeGenerator; + } + +} diff --git a/MV3302ClassCode/src/mv3302/run/RunTransferLineComponent.java b/MV3302ClassCode/src/mv3302/run/RunTransferLineComponent.java new file mode 100644 index 0000000000000000000000000000000000000000..1f35f203f45b11b999c857e4627f017eb7b3241d --- /dev/null +++ b/MV3302ClassCode/src/mv3302/run/RunTransferLineComponent.java @@ -0,0 +1,76 @@ +/* + * Click nbfs://nbhost/SystemFileSystem/Templates/Licenses/license-default.txt to change this license + * Click nbfs://nbhost/SystemFileSystem/Templates/Classes/Main.java to edit this template + */ +package mv3302.run; + +import mv3302.PartArrivalProcess; +import mv3302.TransferLineComponent; +import simkit.Schedule; +import simkit.random.RandomVariate; +import simkit.random.RandomVariateFactory; +import simkit.stat.MultipleSimpleStatsTimeVarying; +import simkit.stat.SimpleStatsTimeVarying; +import simkit.util.SimplePropertyDumper; + +/** + * + * @author dansl + */ +public class RunTransferLineComponent { + + /** + * @param args the command line arguments + */ + public static void main(String[] args) { + int[] totalNumberMachines = {5, 4, 2}; + RandomVariate[] processingTimeGenerator = {RandomVariateFactory.getInstance("Gamma", 3.2, 2.3), + RandomVariateFactory.getInstance("Uniform", 4.5, 6.7), + RandomVariateFactory.getInstance("Exponential", 3.0)}; + RandomVariate interarrivalTimeGenerator = RandomVariateFactory.getInstance("Exponential", 1.7); + TransferLineComponent transferLineComponent = new TransferLineComponent(processingTimeGenerator, totalNumberMachines); + PartArrivalProcess arrivalProcess = new PartArrivalProcess(interarrivalTimeGenerator); + +// Part part = new Part(); +// System.out.println(part); +// part.incrementDelayInQueue(10); +// System.out.println(part.getTotalDelayInQueue()); + + System.out.println(arrivalProcess); + + System.out.println(transferLineComponent.getQueue().size()); + System.out.println(transferLineComponent); + +// for (IntArrivalProcess intArrivalProcess : arrivalProcess) { +// intArrivalProcess.addSimEventListener(twoCustomerTypes); +// } + +// SimplePropertyDumper simplePropertyDumper = new SimplePropertyDumper(); +//// twoCustomerTypes.addPropertyChangeListener(simplePropertyDumper); +// +// MultipleSimpleStatsTimeVarying delayInQueueStat = new MultipleSimpleStatsTimeVarying("delayInQueue"); +// SimpleStatsTimeVarying numberAvailableMachinesStat = new SimpleStatsTimeVarying("numberAvailableMachines"); +// +//// transferLineComponent.addPropertyChangeListener(numberInQueueStat); +// transferLineComponent.addPropertyChangeListener(numberAvailableMachinesStat); +// +// Schedule.setVerbose(false); +// +// Schedule.stopOnEvent(10000, "EndProcessing"); +// +// Schedule.reset(); +//// twoCustomerTypes.waitDelay("Arrival", 1.2, LOW, 0); +//// twoCustomerTypes.waitDelay("Arrival", 1.2, 1); +// Schedule.startSimulation(); +// +// System.out.printf("%nSimulation ended at time %,.2f%n%n", Schedule.getSimTime()); +// +// for (int i = 0; i < 2; ++i) { +// System.out.printf("Avg # in queue type %d: %,.4f%n", i, +// delayInQueueStat.getMean(i)); +// } +// double utilization = 1.0 - numberAvailableMachinesStat.getMean();// / transferLineComponent.getTotalNumberServers(); +// System.out.printf("Avg utilization: %,.4f%n", utilization); + } + } +