Programming Tools & Computer Science I

CSC 185 & 201, Spring 2013, Northern Virginia Community College

Due:

Mar 8, 11:59PM

To submit:

Send an email to me at jal2016@email.vccs.edu with subject CSC 201 HW5, containing your your answers attached in a zip file.

Directions:

The course materials have a project set up in homework/201/hw5 that you can start with if you want.

  1. Statistic interface

    The following code defines a simple interface that keeps track of a statistic about a stream of numbers (i.e. it should keep something like a running total or current estimate after observing each new number).

    package csc201.hw5; 
    
    /**
     * Defines an interface that keeps track of a statistic
     * about a stream of numbers.
     */
    public interface Statistic {
        /**
         * Provide a name describing the statistic.
         * @return the name of this statistic
         */
        String getName();
        /**
         * Provide the current statistic value.
         * @return the current statistic value.
         */
        double getValue();
        /**
         * Update the statistic value given a new observation.
         * @param x a new observation
         */
        void update(double x);
    }
    

    Create at least 2 classes that implement the Statistic interface, and test them using a program like the one shown below. A few possibilities (in roughly increasing order of complexity) include:

    package csc201.hw5; 
    
    
    import java.util.ArrayList;
    import java.util.Scanner;
    
    
    public class StatTest {
        public static void main(String[] args) {
            Scanner input = new Scanner(System.in);
            
            ArrayList stats = new ArrayList();
            // Add all the statistics you implemented; for example:
            // stats.add(new Mean());
            // stats.add(new Max());
            
            // Read input and update all statistics with each new value.
            while (input.hasNextDouble()) {
                double value = input.nextDouble();
                for (Statistic s : stats)
                    s.update(value);
            }
            
            for (Statistic s : stats)
                System.out.println(s.getName() + ": " + s.getValue());
        }
    }
    

  2. Stopwatch

    Implement the two ActionListeners required to implement a graphical stopwatch, using the template shown below. You'll probably have to add additional instance variables to keep track of the state of the stopwatch.

    The program should work by displaying the current elapsed time, and clicking the button should alternate between pausing and restarting the timer. The System.currentTimeMillis method may be useful for measuring time.

    package csc201.hw5; 
    
    import java.awt.Dimension;
    import java.awt.event.ActionEvent;
    import java.awt.event.ActionListener;
    import javax.swing.*;
    
    /**
     * Graphical stopwatch display.
     * Should display total time elapsed, with button used to pause timer.
     */
    public class StopWatch extends JPanel {
        // Time display.
        JTextField timeField;
        // Pause/restart button.
        JButton button;
    
        // Track total elapsed time (in seconds).
        double totalTime = 0.0;
        
        public StopWatch() {
            // Create graphical elements and hook up event handlers.
            timeField = new JTextField("0.00");
            // Set time display to be wider than the default.
            timeField.setPreferredSize(
                    new Dimension(200, timeField.getPreferredSize().height));
            button = new JButton("Start");
            add(button);
            add(timeField);
            // Hook up button click handler.
            button.addActionListener(new ButtonHandler());
            // Create timer that fires 10 times per second, 
            // used to update elapsed time display.
            // Second constructor argument defines the event handler for 
            // the timer firing events.
            Timer timer = new Timer(100, new TimerUpdate());
            timer.start();
        }
        
        // Handle button clicks.
        private class ButtonHandler implements ActionListener {
            public void actionPerformed(ActionEvent ae) {
                // Fill in logic to pause/restart timer.
            }
        }
    
        // Handles timer events that are set to occur 10 times per second.
        private class TimerUpdate implements ActionListener {
    
            public void actionPerformed(ActionEvent ae) {
                // Fill in any logic needed to ensure totalTime is correct.
                
                // Update displayed totalTime value (showing 2 decimal places).
                timeField.setText(String.format("%.2f", totalTime));
            }
            
        }
    
        // Set up main window and add our components.
        public static void buildGUI() {
            JFrame frame = new JFrame();
            frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            frame.setContentPane(new StopWatch());
            frame.pack();
            frame.setVisible(true);
        }
        
        public static void main(String[] args) {
            // A thread is a single sequence of logic within a program.  A single
            // program can have multiple threads executing concurrently.  The Swing
            // library is not thread safe, meaning that we can't work with it in
            // multiple concurrent threads.  Almost all Swing code must execute in a
            // special thread called the event dispatch thread.  The invokeLater
            // method allows us to run code on that thread, to make sure that no
            // errors can occur due to threading issues (even though for our simple
            // program such an error is very unlikely to happen).  The input makes
            // use of the Runnable interface, which we're creating an anonymous
            // class to implement.
            SwingUtilities.invokeLater(new Runnable() {
                @Override
                public void run() {
                    buildGUI();
                }
            });
        }
    
    }
    

    Optional: add a reset button that resets the elapsed time to 0.