diff --git a/InvalidResult.ts b/InvalidResult.ts
new file mode 100644
index 0000000..62f626d
--- /dev/null
+++ b/InvalidResult.ts
@@ -0,0 +1,33 @@
+//typescriptClasses/InvalidResult.ts
+//Matthew Ellison
+// Created: 10-18-20
+//Modified: 10-18-20
+//This file contains a class that is used to time the execution time of other programs
+/*
+Copyright (C) 2020 Matthew Ellison
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU Lesser General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General Public License
+ along with this program. If not, see .
+*/
+
+
+export class InvalidResult{
+ private message: string;
+ public constructor(message: string){
+ this.message = message;
+
+ }
+ public getMessage(): string{
+ return this.message;
+ }
+}
diff --git a/Stopwatch.ts b/Stopwatch.ts
new file mode 100644
index 0000000..967af2c
--- /dev/null
+++ b/Stopwatch.ts
@@ -0,0 +1,143 @@
+//typescriptClasses/Stopwatch.ts
+//Matthew Ellison
+// Created: 10-18-20
+//Modified: 10-18-20
+//This file contains a class that is used to time the execution time of other programs
+/*
+Copyright (C) 2020 Matthew Ellison
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU Lesser General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General Public License
+ along with this program. If not, see .
+*/
+
+
+import {InvalidResult} from "./InvalidResult";
+import {performance} from "perf_hooks";
+
+
+//An enum that helps keep track of how many times the time has been reduced in the getStr function
+enum TIME_RESOLUTION{ NANOSECOND, MICROSECOND, MILLISECOND, SECOND, MINUTE, HOUR, ERROR };
+
+export class Stopwatch{
+ private startTime: number;
+ private stopTime: number;
+ //Constructor makes sure all values are set to defaults
+ public constructor(){
+ //Make sure both values are null so it is easier to detect incorrect function calling order
+ this.startTime = null;
+ this.stopTime = null;
+ }
+ //Returns a long with the elapsed time in milliseconds. Used by other functions to get the time before converting it to the correct resolution
+ private getTime(): number{
+ if(this.startTime == null){
+ return 0;
+ }
+ else if(this.stopTime == null){
+ return performance.now() - this.startTime;
+ }
+ else{
+ return this.stopTime - this.startTime;
+ }
+ }
+ //Simultates starting a stopwatch by saving the time
+ public start(): void{
+ //Make sure the stop time is reset
+ this.stopTime = null;
+ //Get the time as close to returning from the function as possible
+ this.startTime = performance.now();
+ }
+ //Simulates stopping a stopwatch by saving the time
+ public stop(): void{
+ //Set the stopTime as close to call time as possible
+ this.stopTime = performance.now();
+ //If the startTime has not been set then reset stopTime
+ if(this.startTime == null){
+ this.stopTime = null;
+ }
+ }
+ //Resets all variables in the stopwatch
+ public reset(): void{
+ //Make sure all variables are reset correctly
+ this.startTime = null;
+ this.stopTime = null;
+ }
+ //Returns the time in nanoseconds
+ public getNano(): number{
+ return this.getTime() * 1000000;
+ }
+ //Returns the time in microseconds
+ public getMicro(): number{
+ return this.getTime() * 1000;
+ }
+ //Returns the time in milliseconds
+ public getMilli(): number{
+ return this.getTime();
+ }
+ //Returns the time in seconds
+ public getSecond(): number{
+ return this.getTime() / 1000;
+ }
+ //Returns the time in minutes
+ public getMinute(): number{
+ return this.getTime() / 60000;
+ }
+ //Returns the time in hours
+ public getHour(): number{
+ return this.getTime() / 3600000;
+ }
+ //Returns the time as a string at the 'best' resolution. (Goal is xxx.xxx)
+ public getStr(): string{
+ //Get the current duraction from time
+ return Stopwatch.getStr(this.getNano());
+ }
+
+ public static getStr(nanoseconds: number): string{
+ let duration: number = nanoseconds;
+ //Reduce the num,ber to the appropriate number of digits. (xxx.x).
+ //This loop works down to seconds
+ let resolution: TIME_RESOLUTION;
+ for(resolution = TIME_RESOLUTION.NANOSECOND;(resolution < TIME_RESOLUTION.SECOND) && (duration >= 1000);++resolution){
+ duration /= 1000;
+ }
+ //Check if the duration needs reduced to minutes
+ if((duration >= 120) && (resolution == TIME_RESOLUTION.SECOND)){
+ //Reduce to minutes
+ duration /= 60;
+ ++resolution;
+
+ //Check if the duration needs reduced to hours
+ if(duration >= 60){
+ //Reduce to hours
+ duration /= 60;
+ ++resolution;
+ }
+ }
+
+ //Turn the number into a string
+ let time: string = duration.toFixed(3);
+
+ //Tack on the appropriate suffix for resolution
+ switch(resolution){
+ case TIME_RESOLUTION.NANOSECOND: time += " nanoseconds"; break;
+ case TIME_RESOLUTION.MICROSECOND: time += " microseconds"; break;
+ case TIME_RESOLUTION.MILLISECOND: time += " milliseconds"; break;
+ case TIME_RESOLUTION.SECOND: time += " seconds"; break;
+ case TIME_RESOLUTION.MINUTE: time += " minutes"; break;
+ case TIME_RESOLUTION.HOUR: time += " hours"; break;
+ case TIME_RESOLUTION.ERROR:
+ default: throw new InvalidResult("timeResolution was invalid");
+ }
+ //Return the string
+ return time;
+ }
+}
diff --git a/TestStopwatch.ts b/TestStopwatch.ts
new file mode 100644
index 0000000..f138c17
--- /dev/null
+++ b/TestStopwatch.ts
@@ -0,0 +1,99 @@
+//typescriptClasses/TestStopwatch.ts
+//Matthew Ellison
+// Created: 10-18-20
+//Modified: 10-18-20
+//This file contains a class that is used to time the execution time of other programs
+/*
+Copyright (C) 2020 Matthew Ellison
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU Lesser General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General Public License
+ along with this program. If not, see .
+*/
+
+
+import assert = require("assert");
+import {Stopwatch} from "./Stopwatch";
+
+
+let NUM_TO_RUN = 100000;
+
+function testStartStop(): void{
+ let timer: Stopwatch = new Stopwatch();
+ timer.start();
+ timer.stop();
+ //If it gets to here without throwing an exception everything went well
+ console.log("start/stop passed");
+}
+function testConversion(): void{
+ let timer: Stopwatch = new Stopwatch();
+ let sum: number = 0;
+ //Start the timer
+ timer.start();
+ //Do something to run some time
+ for(let cnt: number = 0;cnt < NUM_TO_RUN;++cnt){
+ sum += cnt;
+ }
+ //Stop the timer
+ timer.stop();
+ //Assert something so the sum isn't ignored during compile
+ assert.notStrictEqual(sum, 0, "You really messed up");
+ //Check that the different resolutions work out correctly
+ let nano: number = timer.getNano();
+ assert.strictEqual(timer.getMicro(), nano / 1000, "Micro resolution test failed");
+ assert.strictEqual(timer.getMilli(), nano / 1000000, "Milli resolution test failed");
+ assert.strictEqual(timer.getSecond(), nano / 1000000000, "Minute resolution test failed");
+ assert.strictEqual(timer.getMinute(), nano / 60000000000, "Minute resolution test failed");
+ assert.strictEqual(timer.getHour(), nano / 3600000000000, "Hour resolution test failed");
+ console.log("conversion passed");
+}
+function testStringConversion(): void{
+ //Test nanoseconds
+ let results: string = Stopwatch.getStr(1.0);
+ assert.strictEqual(results, "1.000 nanoseconds", "String conversion to nanoseconds failed");
+ //Test microseconds
+ results = Stopwatch.getStr(1.0e3);
+ assert.strictEqual(results, "1.000 microseconds", "String conversion to microseconds failed");
+ //Test milliseconds
+ results = Stopwatch.getStr(1.0e6);
+ assert.strictEqual(results, "1.000 milliseconds", "String conversion to milliseconds failed");
+ //Test seconds
+ results = Stopwatch.getStr(1.0e9);
+ assert.strictEqual(results, "1.000 seconds", "String conversion to seconds failed");
+ //Test mintues
+ results = Stopwatch.getStr(1.0e12);
+ assert.strictEqual(results, "16.667 minutes", "String conversion to minutes failed");
+ //Rest hours
+ results = Stopwatch.getStr(1.0e13);
+ assert.strictEqual(results, "2.778 hours", "String conversion to hours failed");
+ console.log("string conversion passed");
+}
+
+//Run the functions
+try{
+ testStartStop();
+}
+catch(error){
+ console.error("start/stop test failed!");
+}
+try{
+ testConversion();
+}
+catch(error){
+ console.error("conversion test failed!");
+}
+try{
+ testStringConversion();
+}
+catch(error){
+ console.error("string conversion test failed!");
+}